11

データベース ビューに基づくモデルがあります。

class OrgCode(models.Model):
    org_code                = models.CharField(db_column=u'code',max_length=15) 
    org_description         = models.CharField(max_length=250)
    org_level_num           = models.IntegerField()

    class Meta:
        db_table = u'view_FSS_ORG_PROFILE'

これを別のモデルで参照する必要がある

class AssessmentLocation(models.Model):
    name                = models.CharField(max_length=150)
    org                 = models.ForeignKey(OrgCode)

ビューを参照して外部キー制約を作成できないため、syncdb を実行できません。

 u"Foreign key 'FK__main_asse__org__1D114BD1' 
 references object 'view_FSS_ORG_PROFILE' 
 which is not a user table.", None, 0, -214
7217900), None)
Command:
CREATE TABLE [main_assessmentlocation] (
    [id] int IDENTITY (1, 1) NOT NULL PRIMARY KEY,
    [name] nvarchar(150) NOT NULL,
    [org] int NOT NULL REFERENCES [view_FSS_ORG_PROFILE] ([id]),
)

回避策は、ビューを指す Meta:db_table を取り出し、sync db に OrgCode テーブルを作成させてから、syncdb の後に Meta:db_table を戻すことです。

特定のモデルまたはフィールドに対して外部キー制約が作成されないようにする方法はありますか?

更新:ビューであることを示す静的メソッドを関連モデルに追加しました

class OrgCode(models.Model):
    org_code                = models.CharField(max_length=15)
    org_description         = models.CharField(max_length=250)

    @staticmethod
    def is_backend_view():
        return True

次に、django_mssql creation.py の DatabaseCreation.sql_for_inline_foreign_key_references をオーバーライドします。

def sql_for_inline_foreign_key_references(self, field, known_models, style):
    try: 
        field.rel.to.is_backend_view()
        return "", False
    except:
        return super(DatabaseCreation,self).sql_for_inline_foreign_key_references(field, known_models, style)    

syncdb から生成された sql は、制約を除外します。

CREATE TABLE [main_assessmentlocation] (
    [id] int IDENTITY (1, 1) NOT NULL PRIMARY KEY,
    [name] nvarchar(150) NOT NULL,
    [org] int, -- NO FK CONSTRAINT ANYMORE --
);

django_mssql をハッキングする必要があるので、引き続き試してみます。おそらく django.db.backends.signals.connection_created シグナルにフックするとうまくいくでしょう...

4

2 に答える 2

21

django 開発バージョンには、モデル フィールド - docsdb_constraintのフィールドがあります。ForeignKey

于 2013-05-03T13:29:27.663 に答える
4

モデルのクラスでmanaged=False( Django docs )を設定Metaすると、syncdb の実行時に Django はテーブルを作成しません。

class AssessmentLocation(models.Model):
    name = models.CharField(max_length=150)
    org  = models.ForeignKey(OrgCode)

    class Meta:
        managed = False

Django には、初期 SQL データを提供するためのフックがあります。これを (ab?) 使用して、syncdb を実行した直後に Django にテーブルを作成させることができます。

myapp/sql/assessmentlocation.sqlcreate table ステートメントを含むファイルを作成します。

CREATE TABLE [main_assessmentlocation] (
    [id] int IDENTITY (1, 1) NOT NULL PRIMARY KEY,
    [name] nvarchar(150) NOT NULL,
    [org] int, -- NO FK CONSTRAINT ANYMORE --
);

モデルへの外部キーを持つ他のモデルがAssessmentLocationある場合、カスタム sql を実行してテーブルを作成する前に Django が外部キー制約を適用しようとすると、問題が発生する可能性があります。そうでなければ、このアプローチはうまくいくと思います。

于 2011-11-09T00:42:08.567 に答える