У меня есть модель, поддерживаемая представлением базы данных.
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, а затем вернуть Meta: db_table после syncdb.
Есть ли способ предотвратить создание ограничений внешнего ключа для определенных моделей или полей?
Обновление: Я добавил статический метод в связанную модель, указывая, что это представление
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
Затем переопределите DatabaseCreation.sql_for_inline_foreign_key_references в django_mssql creation.py:
.
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)
Сгенерированный sql из syncdb оставляет ограничение:
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 ...