0

我对 Django 比较陌生。我以这种方式在我的 core/urls.py 文件中设置了我的 URL,当我localhost:8000/posts/在浏览器上打开时确实收到 404 错误。代码显示在这里

urlpatterns = [
    path('', views.IndexView.as_view(), name='index'),
    path('<slug:slug>/', views.SingleView.as_view(), name='single'),
    path('posts/', views.PostsView.as_view(), name='posts'),
]

但是,当我将slugand反posts/转到.posts之前,一切正常slug。像这样:

urlpatterns = [
    path('', views.IndexView.as_view(), name='index'),
    path('posts/', views.PostsView.as_view(), name='posts'),
    path('<slug:slug>/', views.SingleView.as_view(), name='single'),
]

请帮我弄清楚。

4

1 回答 1

0

这就是 Django(和大多数其他框架)的工作方式。当请求进来时,Django 将检查您指定的路由,并使用您指定的相同顺序。所以在你的第一个例子中,''是第一个,然后是'<slug:slug>/'之后'posts/'。这意味着每次有请求进来时,Django 都会按该顺序检查路由。基本上 for 循环是如何工作的:

示例网址:yoursite.com/posts/

小路:"posts/"

routes = ["", "<slug:slug>/", "posts/"]
path = "posts/"
for route in routes:
    if route == path:
        # use view for this route
        return

所以在这种情况下,它将与索引 1 匹配<slug:slug>/,并返回为其指定的视图。

现在要了解为什么<slug:slug>/ == "posts/"返回True,您需要了解slugDjango 中的含义:

slug - 匹配任何由 ASCII 字母或数字以及连字符和下划线字符组成的 slug 字符串。https://docs.djangoproject.com/en/3.1/topics/http/urls/#example

因此,它将接受任何符合这些要求并posts/实际符合这些要求的路径。如果找到匹配项,Django 不会检查任何其他路由,因此它永远不会到达,path('posts/', views.PostsView.as_view(), name='posts')因为'<slug:slug>/'在较小的索引中具有更高的优先级'posts/'。而且您可能会检查模型中不存在的 slug,因此它将返回 404。

通过更改路线顺序,您可以将路线更改为["", "posts/", "<slug:slug>/"]。现在"posts/"具有更高的优先级,django 将使用PostsView.

于 2021-03-10T13:49:15.890 回答