在我的应用程序中,可以将许多不同类型的Record
s 映射到Person
. 在我最初的实现中,我让每条记录都继承自一个抽象基类,并使用GenericRelation
s 来管理整个事情。代码有点复杂,但它可以工作:
模型.py
class Person(models.Model):
...
class PersonRecordMapping(models.Model):
person = models.ForeignKey(Person)
content_type = models.ForeignKey(ContentType)
object_id = models.PositiveIntegerField()
content_object = GenericForeignKey('content_type', 'object_id')
class RecordParent(models.Model):
people = GenericRelation(PersonRecordMapping)
class Meta:
abstract = True
class RecordA(RecordParent):
w = ...
x = ...
class RecordB(RecordParent):
y = ...
z = ...
等等。(正如我试图指出的那样,每种类型Record
都与其他类型完全不同,每种模型的字段都非常不同。)
当我围绕这些模型构建应用程序时,我开始怀疑这种方法是否可以扩展,因为我最终将拥有许多RecordX
-type 类。我开始考虑如何将所有Record
s 放在一个表中,并用一列指示Record
每个表是哪一种,最终发现了 new-ish JSONField
。乍一看,这似乎正是我想要简化整个事情的方法。
class PersonRecordMapping(models.Model):
person = models.ForeignKey(Person)
record = models.ForeignKey(Record)
class Record(models.Model):
type = models.ForeignKey(RecordType) # New model to identify whether a RecordA, RecordB, &c.
data = JSONField()
所有这一切似乎都很好,直到我意识到通过将模型字段转换为 JSON 属性而失去了多少功能,鉴于 JSON 中的数据是用户输入的,这一功能很重要。
- 我无法轻松验证 JSON 中的数据条目。显然我可以这样
data = JSONField(validators=[something???])
,但据我所知,这个实现并不适合validator
依赖于值的情况Record.type
。 - 即使我能弄清楚这一点,我也会失去各个字段的干净管理界面。是的,我想我可以使用自定义保存功能制作自定义表单,但这似乎相当麻烦。
所以——我正在寻找这种情况下最好的架构的洞察力,在不使代码库不必要地复杂化的情况下平衡性能。或者,对于这种情况我不知道还有其他方法吗?
(我知道这不是理想的 StackOverflow 问题,但我希望根据性能和可维护性评估这些(或其他)代码示例使这个问题可以回答,而不仅仅是可以讨论?)
谢谢!