如何调用具有许多参数的视图

时间:2019-07-24 18:32:09

标签: django django-rest-framework django-views

我正在尝试为我的应用程序创建一个非常简单的自定义视图。 假设我有一个简单的模型:

class Person(models.Model):
    Name = models.CharField(max_length = 255)
    pass

class Company(models.Model):
    Title = models.CharField(max_length = 255)
    pass

我想显示一个对象列表。在一个网址上-人员列表,在另一个网址上-公司列表。因此,我只创建视图:

def PersonListView (request):
    _persons = Person.objects.all()
    context = {
        "object_list": _persons
    }
    return render (request, "PersonListView.html", context)

def CompanyListView (request):
    _companies = Person.objects.all()
    context = {
        "object_list": _companies
    }
    return render (request, "CompanyListView.html", context)

然后将路径添加到网址-/人员用于人员列表,//公司用于公司列表。

urlpatterns = [
    path('/Person', PersonListView), 
    path('/Company', CompanyListView)
]

一切正常。但是我已经有一个问题:

  1. 为什么我的视图函数有一个 request 变量,但是我可以从url调用此函数而无需定义此变量?

  2. 为什么我不能使用这种语法path('/Person', PersonListView())?这个括号有什么问题?

还有我的问题的另一部分。 但是后来我决定进行一些重构-我打算对个人和公司使用一个视图,因此我必须传递变量 context 来查看功能。而且我基本上知道该怎么做:

def ObjectList (request, _context):
    _objects = _context.objects.all()
    data = {
        "object_list": _objects
    }
    return render (request, "ListView.html", data)

此处_context-具体类(人员或公司)。

我的问题出在urls.py中,我必须调用ObjectList并传递2个变量:

_context-在这里没有问题,我知道该怎么做

请求

在这里我遇到了墙,因为我不知道如何将其传递给我的功能。如果我将其留空,则会出现错误 “ ObjectList()缺少1个必需的位置参数:'request'”

  1. 那么我该如何解决?我应该以某种方式从我的网址中传递它吗?有没有办法使用带有多个参数的视图函数?

这是回溯:

Internal Server Error: /Entities/Person/
Traceback (most recent call last):
  File "D:\Work\Python\virtualenvs\TestProject\lib\site-packages\django\core\handlers\exception.py", line 34, in inner
    response = get_response(request)
  File "D:\Work\Python\virtualenvs\TestProject\lib\site-packages\django\core\handlers\base.py", line 115, in _get_response
    response = self.process_exception_by_middleware(e, request)
  File "D:\Work\Python\virtualenvs\TestProject\lib\site-packages\django\core\handlers\base.py", line 113, in _get_response
    response = wrapped_callback(request, *callback_args, **callback_kwargs)
TypeError: ObjectList() got multiple values for argument '_context'
[25/Jul/2019 00:25:37] "GET /Entities/Person/ HTTP/1.1" 500 62910

1 个答案:

答案 0 :(得分:1)

您的第二个问题回答您的第一个问题。您不会从URL 调用视图; Django在遇到匹配请求时会在内部执行此操作。如果您尝试从那里调用它,则会看到错误消息。

我不明白为什么您认为您需要在第三个问题中传递来自URL的请求。不,这就是问题1和2的重点。

您的URL模式应该捕获视图的参数,或者将它们作为第三个参数传递给path。因此,在您的情况下,可以使用捕获变量的单个模式:

path('/<str:object_type>/', object_list, name='object_list')

然后:

def object_list(request, object_type):
    types = {'Person': models.Person, 'Company': models.Company}
    if object_type not in types:
        raise Http404
    objects = types[object_type].objects.all()

或者,使用两个单独的URL模式并将类型明确地传递为the third parameter

urlpatterns = [
    path('/Person', object_list_view, {'object_type': Person}, name='person_list'), 
    path('/Company', object_list_view, {'object_type': Company}, name='company_list'),
]

您的视图可以是:

def object_list(request, object_type):
    objects = object_type.objects.all()

最后,对于这个非常简单的用例,您应该考虑使用generic list view;那么您根本不需要定义任何视图:

from django.views.generic import ListView
urlpatterns = [
    path('/Person', ListView.as_view(model=Person)), 
    path('/Company', ListView.as_view(model=Company))
]