我为Django模型创建了一个自定义管理器,它返回一个包含objects.all()子集的QuerySet。我需要将它作为模型的默认管理器,因为我还创建了一个自定义标记,它将从任何模型(由参数指定)检索内容,并且需要使用指定模型的默认管理器。一切正常,除了 - Django Admin也使用此特定模型的默认管理器,这意味着并非所有模型实例都出现在管理员中。
Django文档无济于事:
如果您使用自定义管理器对象,请注意第一个管理器Django遇到(在 它们在模型中定义的顺序)具有特殊状态。 Django将类中定义的第一个Manager解释为“默认”管理器,Django的几个部分(虽然不是管理员应用程序)将专门为该模型使用该Manager。 (Django Managers documentation)
管理员不应该使用默认的管理器,但它似乎在我的情况下。请注意,我还明确添加了默认管理器objects
:
subset = CustomManager() # the default manager
objects = models.Manager() # the one I want admin to use
如何指定管理员应使用哪个Manager?
答案 0 :(得分:47)
您可以通过覆盖ModelAdmin子类中的queryset
方法来选择管理器。
def get_queryset(self, request):
# use our manager, rather than the default one
qs = self.model.objects.get_queryset()
# we need this from the superclass method
ordering = self.ordering or () # otherwise we might try to *None, which is bad ;)
if ordering:
qs = qs.order_by(*ordering)
return qs
答案 1 :(得分:8)
更新的代码:
def get_queryset(self, request):
"""
Returns a QuerySet of all model instances that can be edited by the
admin site. This is used by changelist_view.
"""
qs = self.model._default_manager.get_queryset()
# TODO: this should be handled by some parameter to the ChangeList.
ordering = self.get_ordering(request)
if ordering:
qs = qs.order_by(*ordering)
return qs
_default_manager可以替换......
答案 2 :(得分:1)
由于我们希望objects
成为唯一的管理员,因此管理员将使用manager
中的self.Admin.manager
。
来自troy.simpson打开的门票https://code.djangoproject.com/ticket/4754
class filterManager(models.Manager):
def get_query_set(self):
return super(filterManager, self).get_query_set().filter(name='troy')
class Blah(models.Model):
name = models.CharField(maxlength=100)
objects = filterManager()
class Admin:
manager = filterManager()
使用Django 1.11进行测试
答案 3 :(得分:0)
您定义经理的顺序很重要。管理员采用模型中定义的第一个经理。
如果你喜欢这样:
subset = CustomManager() # the default manager
objects = models.Manager() # the one I want admin to use
默认经理将是 subset
如果你喜欢这样:
objects = models.Manager() # the default manager
subset = CustomManager() # your own manager
那么默认管理器将是 objects
。