Django 模型管理器
Django Model Manager
我有一个 Django 模型,用户可以在其中创建对象并将它们保密一段时间。
class MyModel(models.Model):
creator = models.ForeignKey(User, null=True, on_delete=models.SET_NULL)
private_until = models.DateField(null=True, default=None, blank=True)
objects = MyModelManager()
在我的 ListView 中,我希望访问者只显示“非私人”对象,而对于经过身份验证的用户,“非私人”对象加上他们自己的私人对象。所以我的经理看起来像这样:
class MyModelManager(models.Manager):
def include_his_private(self, user):
if user.is_authenticated:
include_his_private = super().get_queryset().filter(~Q(private_until__gt=datetime.date.today()))
include_his_private |= super().get_queryset().filter(Q(creator=user))
return include_his_private
else:
return super().get_queryset().filter(~Q(private_until__gt=datetime.date.today()))
def get_queryset(self):
return super().get_queryset().filter(~Q(private_until__gt=datetime.date.today()))
对于我的 ListView
这很好用。但是,当我单击一个对象以获取其 DetailView
时,我在“URL-Level”上收到 404 错误。在我的 URL 中,我有:
path('<slug:slug>', MyModelDetailView.as_view(), name='mymodel_detail'),
...不知何故,在我有机会让用户进入之前,Django 已经提前检查了每个管理器允许的 slug 的整个 slug。解决我的问题的方法是什么?任何帮助表示赞赏。提前致谢!
编辑:
我的 DetailView 看起来像这样:
class MyModelDetailView(DetailView):
model = MyModel
template_name = 'mymodel_detail.html'
def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
slug = self.kwargs['slug']
if self.request.user.is_authenticated:
obj = MyModel.objects.include_his_private(self.request.user).get(slug=slug)
else:
obj = MyModel.objects.get(slug=slug)
A DetailView
[Django-doc] will use the .get_queryset(…)
[Django-doc] to obtain a queryset and in the .get_object(…)
method [Django-doc],如果路径包含这样的 URL 参数,它将自动过滤 pk
and/or slug
。因此,在 您 运行 get_context_data
.
中的自定义逻辑之前完成了此操作
因此您应该覆盖 get_queryset
方法:
class MyModelDetailView(DetailView):
model = MyModel
template_name = 'mymodel_detail.html'
def <b>get_queryset</b>(self, *args, **kwargs):
return MyModel.objects.include_his_private(
self.request.user
)
我有一个 Django 模型,用户可以在其中创建对象并将它们保密一段时间。
class MyModel(models.Model):
creator = models.ForeignKey(User, null=True, on_delete=models.SET_NULL)
private_until = models.DateField(null=True, default=None, blank=True)
objects = MyModelManager()
在我的 ListView 中,我希望访问者只显示“非私人”对象,而对于经过身份验证的用户,“非私人”对象加上他们自己的私人对象。所以我的经理看起来像这样:
class MyModelManager(models.Manager):
def include_his_private(self, user):
if user.is_authenticated:
include_his_private = super().get_queryset().filter(~Q(private_until__gt=datetime.date.today()))
include_his_private |= super().get_queryset().filter(Q(creator=user))
return include_his_private
else:
return super().get_queryset().filter(~Q(private_until__gt=datetime.date.today()))
def get_queryset(self):
return super().get_queryset().filter(~Q(private_until__gt=datetime.date.today()))
对于我的 ListView
这很好用。但是,当我单击一个对象以获取其 DetailView
时,我在“URL-Level”上收到 404 错误。在我的 URL 中,我有:
path('<slug:slug>', MyModelDetailView.as_view(), name='mymodel_detail'),
...不知何故,在我有机会让用户进入之前,Django 已经提前检查了每个管理器允许的 slug 的整个 slug。解决我的问题的方法是什么?任何帮助表示赞赏。提前致谢!
编辑: 我的 DetailView 看起来像这样:
class MyModelDetailView(DetailView):
model = MyModel
template_name = 'mymodel_detail.html'
def get_context_data(self, **kwargs):
context = super().get_context_data(**kwargs)
slug = self.kwargs['slug']
if self.request.user.is_authenticated:
obj = MyModel.objects.include_his_private(self.request.user).get(slug=slug)
else:
obj = MyModel.objects.get(slug=slug)
A DetailView
[Django-doc] will use the .get_queryset(…)
[Django-doc] to obtain a queryset and in the .get_object(…)
method [Django-doc],如果路径包含这样的 URL 参数,它将自动过滤 pk
and/or slug
。因此,在 您 运行 get_context_data
.
因此您应该覆盖 get_queryset
方法:
class MyModelDetailView(DetailView):
model = MyModel
template_name = 'mymodel_detail.html'
def <b>get_queryset</b>(self, *args, **kwargs):
return MyModel.objects.include_his_private(
self.request.user
)