Django:slug 中的点在 DetailView 中不起作用

Django: Dots in slug don't work in DetailView

我正在对名称通常包含点 (.) 我写了一个 DetailView,它 适用于不带点的名称 但不适用于带点的名称。我收到此错误:

404 - Using the URLconf defined in genomeDBmanager.urls, Django tried these URL patterns, in this order: ...

我的模特:

class Assembly(models.Model):
    ...
    identifier = models.SlugField('unique identifier', max_length=50, unique=True)
    ...

我的view.py:

class AssemblyDetailView(DetailView):
    slug_field = 'identifier'
    template_name = 'overview/assembly.html'
    model = Assembly
    context_object_name = 'assembly'

我的overview/urls.py:

app_name = 'overview'
urlpatterns = [
...
    path('assembly/<slug>/', views.AssemblyDetailView.as_view(), name='assembly-detail')
]

这个 URL 有效:127.0.0.1:8000/strain/SomeAssembly-1,这个无效:127.0.0.1:8000/strain/SomeAssembly.2.

问题是默认 slug-regex 不接受点。解决方案是使用 re_path 指定一个,如下所示:

re_path(r'^assembly/(?P<slug>[0-9a-zA-Z.\-_ ]+)/$', views.AssemblyDetailView.as_view(), name='assembly-detail')

其他一切都一样。

简答:这是鼻涕虫的正确行为,因为鼻涕虫不应该有点。

A slug 根本不允许在 slug 中有点。事实上,如果我们 slugify(..) [Django-doc] 例如 'foo.bar',我们得到:

>>> from django.utils.text import slugify
>>> slugify('foo.bar')
'foobar'

因此接受点是绝对有效的。因此,这意味着您模型的 SlugField 可能不会正确地标记标题(或任何 "slugified")。

您可以使用 strpath 路径转换器接受 strings 和 paths,如 documentation on path converters [Django-doc] 中指定:

  • str - Matches any non-empty string, excluding the path separator, '/'. This is the default if a converter isn’t included in the expression.

(..)

  • path - Matches any non-empty string, including the path separator, '/'. This allows you to match against a complete URL path rather than just a segment of a URL path as with str.

因此您可以指定例如:

path('assembly/<b><str:slug></b>/', views.AssemblyDetailView.as_view(), name='assembly-detail')

不过,这 不是 鼻涕虫。