基于 Django 类的“method_splitter” - 分别传递 2 个 slug 作为模型名称和字段值
Posted
技术标签:
【中文标题】基于 Django 类的“method_splitter” - 分别传递 2 个 slug 作为模型名称和字段值【英文标题】:Django class-based "method_splitter" - passing 2 slugs as model name and field value, respectively 【发布时间】:2013-03-18 17:19:15 【问题描述】:我想使用基于类的视图创建一个 "method_splitter" 等效项,以删除我的 URL 配置中的一些硬编码。
我想要以下网址:
ListView: http://mysite.com/<model_name>/
DetailView: http://mysite.com/<model_name>/<field_value>/
ListView 的查询位置:
<model_name>.objects.all()
DetailView 的查询集将是:
<model_name>.objects.get(<field>=<field_Value>)
目前,由于 url conf 中的一些硬编码,我的视图有效,但我想找到一个可以扩展的优雅解决方案。
我的解决方案没有给出 404,但什么也不显示:
views.py
class ListOrDetailView(View):
def __init__(self, **kwargs):
for key, value in kwargs.iteritems():
setattr(self, key, value)
try: #If/Else instead?
def goToDetailView(self, **kwargs):
m = get_list_or_404(self.kwargs['model']) #Is this even needed?
return DetailView(model=self.kwargs['model'], slug=self.kwargs['slug'], template_name='detail.html', context_object_name='object')
except: #If/Else instead?
def goToListView(self, **kwargs):
q = get_object_or_404(self.kwargs['model'], slug=self.kwargs['slug']) #Is this even needed?
return ListView(model=self.kwargs['model'], template_name='list.html', context_object_name='object_list',)
MyApp 的 urls.py
url(r'^(?P<model>[\w]+)/?(?P<slug>[-_\w]+)/$', ListOrDetailView.as_view()),
【问题讨论】:
我会将这个视图分成两个视图。在我看来,这是糟糕的设计。这种紧密联系有原因吗? 我愿意将其拆分。您能否发布一个如何将 slug 传递给 ListView/DetailView 的示例?我可以测试它并接受它是否有效。 您打算如何限制人们可以访问的模型?任何人都可以通过任何领域查找任何模型吗? @Thomas - 这是一个很好的观点。在可管理的应用程序中,仅在 urlconf 中进行限制可能是值得的。你会怎么做? 【参考方案1】:正如聚光灯所说,这是一种可怕的设计模式; Django 的重点是模型和视图的分离。如果您担心可能不得不编写大量重复代码来覆盖所有不同的模型,请相信我,这对于基于类的视图来说不是什么大问题。本质上,您需要为您希望公开的每个模型编写以下代码:
网址.py:
urlpatterns = patterns('',
url(r'^my_model/$', MyModelListView.as_view(), name="mymodel_list"),
url(r'^my_model/(?P<field_value>\w+)/$', MyModelDetailView.as_view(), name="mymodel_detail"),
)
views.py:
from django.views.generic import ListView, DetailView
class MyModelListView(ListView):
model = MyModel
class MyModelDetailView(DetailView):
model = MyModel
def get_queryset(self):
field_value = self.kwargs.get("field_value")
return self.model.objects.filter(field=field_value)
【讨论】:
以上是关于基于 Django 类的“method_splitter” - 分别传递 2 个 slug 作为模型名称和字段值的主要内容,如果未能解决你的问题,请参考以下文章