我尝试使用callable创建一个带有选项字段的模型,这样当选项列表发生变化时,Django就不会创建迁移,如this问题所示。
class Quote(models.Model):
severity = models.IntegerField(choices=get_severity_choices)
...
class get_severity_choices(object):
def __iter__(self):
for item in SEVERITY_CHOICES:
yield item
其中
SEVERITY_CHOICES = (
(1, 'Low'),
(2, 'Medium'),
(3, 'High'),
)
但是,我收到了错误消息:
quoting.Quote.severity: (fields.E004) 'choices' must be an iterable (e.g., a list or tuple).
答案 0 :(得分:4)
我认为您在choices
字段上混淆了Model
参数,而在forms.ChoiceField
字段上混淆了choices
参数。在model中,choices
必须是可互换的 - 您无法传递可调用的内容:
get_severity_choices
:一个可迭代的(例如,一个列表或元组),由迭代的迭代组成 恰好两个项目(例如[(A,B),(A,B)...])用作选项 这个领域。
您的__iter__
类未被识别为可迭代类,因为Django希望它继承collections.Iterable
而不是仅公开FormField
方法。
你可以将a callable传递给choices
:
Model
:可以使用2元组的可迭代(例如,列表或元组)作为此字段的选项,或者是用于返回此类可迭代的可调用字段。
对于choices
字段,您必须事先指定您的选择。同样来自文档:
请注意,
choices
可以是任何可迭代对象 - 不一定是列表 或元组。这使您可以动态构造选择。但如果你找到了 自己黑客choices
是动态的,你可能会更好 使用带有ForeignKey的正确数据库表。compileSdkVersion 23, buildToolsVersion '23.0.1',
是为了 静态数据,如果有的话,变化不大。
关于为什么Django创建看似无用的迁移,在this ticket中有一些讨论:
这是设计的。有几个原因,尤其是......历史上的点数据需要完整 准确表示模型,包括所有选项,而不是 只是影响数据库的那些。