Django,自定义管理器会影响保存方法吗?

syb*_*tic 5 django django-models django-admin django-managers

我正在使用Django 1.7.我有一个默认的自定义管理器,可以过滤"活动"布尔字段.根据文档,它需要是使用相关字段的默认管理器(即访问User.story_set仅显示活动的Story对象).我保留了管理员和shell访问的标准管理器,但我无法保存对象的更改,我猜测因为save()方法在某些时候通过默认管理器.

class Story(models.Model):
    active = models.BooleanField(default=True)
    ....

    objects = ActiveStoryManager()
    full_set = models.Manager()

class ActiveStoryManager(models.Manager):
    def get_query_set(self):
        return super(ActiveStoryManager, self).get_query_set().filter(active=True)
    use_for_related_fields = True
Run Code Online (Sandbox Code Playgroud)

这适用于所有面向公众的用途.但是,在admin和shell中,我无法影响非活动对象,包括将它们恢复为活动状态.

story = Story.full_set.get(id=#)将获取一个故事active=False,但在设置后active=True我无法保存,得到一个

django.db.utils.IntegrityError: duplicate key value violates unique constraint "stories_story_pkey" DETAIL: Key (id)=(#) already exists.

致电save.(force_update=True)回报django.db.utils.DatabaseError: Forced update did not affect any rows.

因此,虽然save()是一个模型方法,但它似乎依赖于保存过程中某个时刻的默认管理器.

解决方法是使用Queryset API,例如Story.full_set.filter(id=#).update(active=True),但只能在shell中使用,并且需要手动键入每个更改,仍然无法在管理中保存非活动实例.

对此有何帮助?

syb*_*tic 5

它无法完成!正如inancsevinc指出的那样,save()调用默认管理器.在Django文档提到get_query_set不应默认经理进行修改,我也伤心地找到了原因.希望将来可以指定/控制相关管理器,但是现在这种方法对我来说不起作用.在Django IRC聊天确认.

相反,我将一个普通的Manager方法和一些模型的模型方法放在一起,以获得相同的功能.还需要更改related_set模板中的所有调用以包含新方法,因此这很痛苦,但没有其他方法.