Djangoモデルインスタンス、フォームが表示される前に追加するために、自動生成されたフォームのフィールドの初期値を設定するにはどうすればよいですか?Django 1.3.1。
私のモデルは次のとおりです:
class Foo(models.Model):
title = models.CharField(max_length=50)
description = models.TextField()
現在の管理フォームは特別なものではありません
class FooAdmin(admin.ModelAdmin):
ordering = ('title',)
管理ページを使用してFooの新しいインスタンスを追加すると、タイトルと説明のフィールドが空のNiceフォームが表示されます。説明フィールドに、関数を呼び出して取得したテンプレートが設定されていることを望みます。
そこに着くための私の現在の最善の試みはこれです:
def get_default_content():
return 'this is a template for a Foo description'
class FooAdminForm(Django.forms.ModelForm):
class Meta:
model = Foo
def __init__(self, *args, **kwargs):
kwargs['initial'].update({'description': get_default_content()})
super(FooAdminForm, self).__init__(self, *args, **kwargs)
class FooAdmin(admin.ModelAdmin):
ordering = ('title',)
form = FooAdminForm
しかし、これを試すと、Djangoエラーが発生します。
AttributeError at /admin/bar/foo/add/
'FooForm' object has no attribute 'get'
Request Method: GET
Request URL: http://localhost:8000/admin/bar/foo/add/
Django Version: 1.3.1
Exception Type: AttributeError
Exception Value: 'FooForm' object has no attribute 'get'
Exception Location: /www/Django-site/venv/lib/python2.6/site-packages/Django/forms/widgets.py in value_from_datadict, line 178
ここで何が間違っているのか、それを機能させるために何をすべきかわかりません。このエラーについて私が奇妙に思うのは(まったく表示されるという事実は別として)、コードにFooFormがまったくないということです。
__init__
メソッド定義の最初の引数としてself
を含める必要がありますが、スーパークラスのメソッドを呼び出すときにそれを含めないでください。
def __init__(self, *args, **kwargs):
# We can't assume that kwargs['initial'] exists!
if 'initial' not in kwargs:
kwargs['initial'] = {}
kwargs['initial'].update({'description': get_default_content()})
super(FooAdminForm, self).__init__(*args, **kwargs)
そうは言っても、モデルフィールドは default の呼び出し可能オブジェクトを取ることができるため、カスタム管理フォームを定義する必要がない場合もあります。
class Foo(models.Model):
title = models.CharField(max_length=50)
description = models.TextField(default=get_default_content)
Alasdairのアプローチはいいですが時代遅れです。 Radevのアプローチは非常に見栄えがよく、コメントで述べたように、ドキュメントにはこれについて何も記載されていません。
これらとは別に、Django 1.7なので、関数 get_changeform_initial_data
初期フォーム値を設定するModelAdmin内:
def get_changeform_initial_data(self, request):
return {'name': 'custom_initial_value'}
3年以上経ってから、実際には、次のようにadmin.ModelAdmin formfield_for_dbfieldをオーバーライドする必要があります。
class FooAdmin(admin.ModelAdmin):
def formfield_for_dbfield(self, db_field, **kwargs):
field = super(FooAdmin, self).formfield_for_dbfield(db_field, **kwargs)
if db_field.name == 'description':
field.initial = 'My initial description'
Elif db_field.name == 'counter':
field.initial = get_counter() + 1
return field
乾杯;