コアモデルに触れることなく、継承せずにそれを達成する方法がありますが、それは間違いなくハックであり、私は特別な注意を払ってそれを使用します。
シグナルに関するDjangoのドキュメントを見ると、と呼ばれるものがあることがわかります。class_prepared
これは基本的に、メタクラスによって実際のモデルクラスが作成されると送信されます。その瞬間が、魔法が発生する前にモデルを変更する最後のチャンスです(つまり、、、、ModelForm
などModelAdmin
)syncdb
。
したがって、計画は単純です。そのシグナルを、User
モデルに対して呼び出されたときに検出するハンドラーに登録してから、フィールドのmax_length
プロパティを変更するだけです。username
ここで問題となるのは、このコードはどこにあるべきかということです。User
モデルをロードする前に実行する必要があるため、多くの場合、非常に早い段階を意味します。残念ながら、そこにインポートすると問題が発生するため、(django 1.1.1、別のバージョンで確認していない)それを入れることはできません。settings
signals
より良い選択は、それをダミーアプリのモデルモジュールに配置し、そのアプリをリスト/タプルの一番上にINSTALLED_APPS
配置することです(したがって、他の何よりも先にインポートされます)。これがあなたが持つことができるものの例ですmyhackishfix_app/models.py
:
from django.db.models.signals import class_prepared
def longer_username(sender, *args, **kwargs):
# You can't just do `if sender == django.contrib.auth.models.User`
# because you would have to import the model
# You have to test using __name__ and __module__
if sender.__name__ == "User" and sender.__module__ == "django.contrib.auth.models":
sender._meta.get_field("username").max_length = 75
class_prepared.connect(longer_username)
それでうまくいきます。
ただし、いくつかの注意事項:
help_text
新しい最大長を反映するために、フィールドのも変更することをお勧めします
- 自動管理を使用する場合は、サブクラス化する必要があります
UserChangeForm
。UserCreationForm
最大AuthenticationForm
長はモデルフィールドから推定されるのではなく、フォームフィールド宣言で直接推定されるためです。
Southを使用している場合は、次の移行を作成して、基になるデータベースの列を変更できます。
import datetime
from south.db import db
from south.v2 import SchemaMigration
from django.db import models
class Migration(SchemaMigration):
def forwards(self, orm):
# Changing field 'User.username'
db.alter_column('auth_user', 'username', models.CharField(max_length=75))
def backwards(self, orm):
# Changing field 'User.username'
db.alter_column('auth_user', 'username', models.CharField(max_length=35))
models = {
# ... Copy the remainder of the file from the previous migration, being sure
# to change the value for auth.user / usename / maxlength