ほとんどの場合、1 つのサイトに (サイト フレームワークから) フラットページを使用します。作成されたすべてのフラットページに対して既存のサイトのデフォルトをマークするにはどうすればよいですか? 作成するページごとに同じサイトを毎回選択するのは時間の無駄です。モデルまたは保存方法でこれをオーバーライドする方法はありますか?
4 に答える
サイト フィールド (models.py -> FlatPage.sites) で空白を許可し、これをモデル フォーム (admin.py -> FlatPageForm) に入れます。
def clean_sites(self):
sites = self.cleaned_data.get('sites')
print sites
return [Site.objects.get(id=settings.SITE_ID)]
編集:
より良い解決策を思いつきました。
これにより、現在のサイトは既に ManyToMany サイト フィールドにフォーカスされます。flatpages/admin.py を編集します。from django.contrib.sites.models import Site
ファイルの先頭に : を追加し、次のコードをclass FlatPageAdmin
:
def formfield_for_manytomany(self, db_field, request=None, **kwargs):
if db_field.name == "sites":
kwargs["initial"] = [Site.objects.get_current()]
return super(FlatPageAdmin, self).formfield_for_foreignkey(db_field, request, **kwargs)
FlatPage モデルのサイト フィールドで空白を許可する必要はありません
これが私のコードです、それは動作します:
class CustomFlatPage(FlatPage):
def save(self):
super(CustomFlatPage, self).save()
self.sites = [Site.objects.get(pk=1)]
super(CustomFlatPage, self).save()
私は別のアプローチを取り、FlatpageForm メタにモンキー パッチを適用して、サイトのカスタム ウィジェットを使用しました。
from django.forms import SelectMultiple
from django.conf import settings
from django.contrib.flatpages.forms import FlatpageForm
class PreSelectDefaultSiteOnCreateSelectMultiple(SelectMultiple):
def render(self, name, value, attrs=None, choices=()):
if value is None:
# None in the add form, a list, possibly empty, in
# the edit form. So we're adding a new instance here.
value = [settings.SITE_ID]
return super(PreSelectDefaultSiteOnCreateSelectMultiple, self
).render(name, value, attrs, choices)
def flatpages():
"""Hack the sites field widget.
"""
fpafm = FlatpageForm.Meta
if getattr(fpafm, 'widgets', None) is None:
fpafm.widgets = {}
fpafm.widgets['sites'] = PreSelectDefaultSiteOnCreateSelectMultiple
admin を使用する前に、どこかから flatpages() を呼び出す必要があります。上記のコードをパッケージmonkey_patchesのモジュールadmin.pyに入れ、次にリクエストが初めて入ったときにインポートされるルートurls.pyに入れました。
from monkey_patches.admin import flatpages
flatpages()
これは Django 1.4 と python 2.7.3 の下にありますが、古いバージョンでも動作するはずです。
ああ、本当に空のサイトの関連付けが必要な場合は、意図的に選択を解除できます。これは単なるウィジェットの初期化であるためです。後続の編集では、値としてレンダリングする空のリストが渡されますが、これは None ではありません。
ビル、KE1G
これは、元の問題を解決する完全に機能するコードです(作成されたすべてのフラットページの既存のサイトのデフォルトをマークするため):
from django.conf import settings
from django.contrib.flatpages.models import FlatPage
from django.contrib.sites.models import Site
class CustomFlatPage(FlatPage):
class Meta:
proxy = True
def save(self):
self.sites = [Site.objects.get(pk=settings.SITE_ID)]
super(CustomFlatPage, self).save()
また、このソリューション:
- DB で 1 つの INSERT または 1 つの UPDATE のみを実行します。以前のものは、1 つの INSERT と 1 つの UPDATE、または 2 つの UPDATE で DB にアクセスしていました。
- モデル用の追加テーブルを作成するためにsyncbd
proxy = True
を実行する必要はありません。CustomFlatPage