【问题标题】:How to use same ListView class for different model?如何为不同的模型使用相同的 ListView 类?
【发布时间】:2023-03-25 09:29:01
【问题描述】:

有 3 个模型(公司、部门和员工组)显示为列表。

我正在尝试创建一个从 ListView 扩展的类基础视图,以通过在 URLpatterns 中传递模型名称来列出各种模型。

我为每个模型创建了单独的类视图,但本质上是复制粘贴代码。有没有办法将代码简化为一个类并从 urlpath 获取模型。

models.py

from django.db import models
...
class Company(models.Model):
    id = models.CharField(max_length=5, primary_key=True)
    name = models.CharField(max_length=100)
    is_active = models.BooleanField()
...
class Division(models.Model):
    id = models.CharField(max_length=5, primary_key=True)
    name = models.CharField(max_length=100)
    is_active = models.BooleanField()
...
class StaffGroup(models.Model):
    name = models.CharField(max_length=20)
    is_active = models.BooleanField()
...

urls.py

from django.urls import path
from srrp.views import srrpIndexView, srrpListView

app_name = 'srrp'

urlpatterns = [
    path('', srrpIndexView.as_view(), name='srrp_index'),
    path('<str:modelname>', srrpListView.as_view(), name='srrp_list'),   
] 

views.py

class srrpListView(ListView):
    template_name = 'srrp/srrplist.html'
    model = self.kwargs['modelname'] # I know this is wrong, this is just placeholder for the right solution
    paginate_by = 10 

【问题讨论】:

  • 使用 model = None,然后在 dispatch 或其他早期方法中执行 model = self.kwargs['modelname']

标签: python-3.x django


【解决方案1】:

子类get_queryset。 (书签Classy Class-based views)

def get_queryset(self):
     model = self.kwargs['modelname']
     if model == 'foo':
          return Foo.objects.all()
     if model == 'bar':
          return Bar.objects.all()
     if model == 'green_bar':
          return Bar.objects.filter( colour='green' )
     ...
     raise ValueError(
          f'This shouldn't be possible: model = "{model}"'

如果您不想要任何“特殊”模型,您可以在类字典中查找正确的模型:

klass = MODEL_CLASSES[model] # KeyError if bad model in URL 
return klass.objects.all()

或者您可以使用我忘记了名称的 Django 函数,通过应用程序和模型名称获取模型类。

【讨论】:

【解决方案2】:

解决了。

views.py

class srrpListView(ListView):
    template_name = 'srrp/srrplist.html'
    paginate_by = 10 
    
    def get_queryset(self):
        modelname = self.kwargs['modelname']
        ctype = ContentType.objects.get(app_label='srrp', model=modelname)
        model = ctype.model_class()
        return model.objects.all()

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2021-12-18
    • 1970-01-01
    • 2021-05-25
    • 2023-04-01
    • 2016-12-23
    • 2020-01-08
    • 1970-01-01
    • 2020-09-23
    相关资源
    最近更新 更多