在django中设置ManyToMany字段默认值的正确方法

时间:2015-08-18 09:43:06

标签: python django many-to-many

设置many2many字段的默认值的正确方法是什么?这是我在下面尝试过的,但它没有用。我知道我可以覆盖save方法,但每次模型更新时都不会调用它?我想只在每次创建实例时设置模型的初始值。

def default_values():
     return [c.id for c in SomeOtherModel.objects.filter(otherfield__isnull = True)]


class SomeModel(models.Model):
    somefield = models.ManyToManyField('SomeField', default=default_values)
    semeotherfield = models.ForeignKey('SomeOtherField')

我正在使用django 1.8

3 个答案:

答案 0 :(得分:2)

该问题中提到的方法不起作用,因为ManyToManyField在保存时不能有值(值必须与RelatedManager相加)。因此,default的{​​{1}}选项在保存对象时(调用ManyToManyField或其他对象时)不会使用:即使已设置(例如,返回到对象列表的可调用对象) ,保存时该字段将被设置为空列表。

根据this ticket

<object>.save()选项值在Django Form设置中用于编辑此值 目的。特别是在Django Admin中,多值下拉列表将 包含为该字段,它将包含由返回的所有对象 可调用项定义为默认值-它们将全部 已选择。如果用户保存对象而未进行任何编辑(通过按 表单的“保存”按钮),则该字段实际上将设置为全部 值。

答案 1 :(得分:1)

您可以覆盖保存方法,并在其中插入检查主键是否为空。如果它是空的 - 这是对象的创建。

你也可以连接到保存信号 - 有一个属性告诉你这是否是对象的创建。

答案 2 :(得分:0)

您可以覆盖模型的 init 方法,但不允许您设置m2m。

您可以像这样覆盖模型表单的初始化:

def __init__(self, *args, **kwargs):
    if 'initial' not in kwargs:
        kwargs['initial'] = {}
    kwargs['initial'].update(product_template_admin_initial_values())
    super(ProductTemplateAdminForm, self).__init__(*args, **kwargs)

但这将不允许使用该请求。

如果您依赖请求,则可以使用管理员get_changeform_initial_data

def get_changeform_initial_data(self, request):
    return {'name': 'custom_initial_value'}

您可以调用以请求为参数的方法并返回字典。 m2m默认值应为列表