Skip to main content
 首页 » 编程设计

python之有效管理日益复杂的 Django URL View (网址.py)

2024年09月03日33lexus

因此,我有了这个 Django 应用程序,并且我不断添加新功能以提供更精细的数据 View 。为了快速了解问题,这里是 urls.py 的一个子集:

# Simple enough . . . 
(r'^$', 'index'), 
(r'^date/(?P<year>\d{4})$', 'index'), 
(r'^date/(?P<year>\d{4})-(?P<month>\d{2})$', 'index'), 
(r'^date/(?P<year>\d{4})-(?P<month>\d{2})-(?P<day>\d{2})$', 'index'), 
(r'^page/(?P<page>\d+)$', 'index'), 

所以,是的,默认 View 、日期 View 、分页 View ,然后是针对用户特定 URL 的类似设置:

# user 
(r'^user/(?P<username>\w+)$', 'index_username'), 
(r'^user/(?P<username>\w+)/date/(?P<year>\d{4})$', 'index_username'), 
(r'^user/(?P<username>\w+)/date/(?P<year>\d{4})-(?P<month>\d{2})$', 'index_username'), 
(r'^user/(?P<username>\w+)/date/(?P<year>\d{4})-(?P<month>\d{2})-(?P<day>\d{2})$', 'index_username'), 
(r'^user/(?P<username>\w+)/page/(?P<page>\d+)$', 'index_username'), 

然后,Teams 再次类似。 . .

# Team View 
(r'^team/(?P<team>\w+)$', 'index'), 
(r'^team/(?P<team>\w+)/date/(?P<year>\d{4})$', 'index'), 
(r'^team/(?P<team>\w+)/date/(?P<year>\d{4})-(?P<month>\d{2})$', 'index'), 
(r'^team/(?P<team>\w+)/date/(?P<year>\d{4})-(?P<month>\d{2})-(?P<day>\d{2})$', 'index'), 
(r'^team/(?P<team>\w+)/page/(?P<page>\d+)$', 'index'), 

现在,我想添加一个“搜索” View ,我真的认为将其添加到上述许多 URL 的末尾会很好,这样我就可以点击:

/search/foo
/user/fred/date/2010-01/search/baz

然后我可以将搜索参数传递给 View ,这可以适本地限制结果。

但是,如果我想将其应用到用户、团队和按日期 View ,我已将 12 行新行添加到 urls.py。每次我添加另一个潜在的 View 选项(比如,分页搜索结果?)。 . .感觉应该有更好的方法。

根据我的研究,答案似乎是:
1) 在 urls.py 中进行更广泛的匹配,并让 View 函数解析查询字符串。
2) urls.py 中可能有一些更强大的正则表达式逻辑,可以多次说“如果此模式匹配,则在传递给 View 函数时包含参数”。但这可能是噩梦般的维持。

有没有人想出一个更明智的解决方案来优雅地管理复杂的 URL?我在想,在某个时候,最简单的方法是将参数匹配逻辑传递给 View 本身,从查询字符串中解析参数。因此,在 View 顶部附近,我可能有一些代码如下所示:

# Date Queries 
re_ymd = re.compile('date/(?P<year>\d{4})-(?P<month>\d{2})-(?P<day>\d{2})') 
re_ym = re.compile('date/(?P<year>\d{4})-(?P<month>\d{2})') 
re_y = re.compile('date/(?P<year>\d{4})') 
if( re_ymd.search(qs) ): 
    year = re_ymd.search(qs).group('year') 
    month = re_ymd.search(qs).group('month') 
    day = re_ymd.search(qs).group('day') 
elif( re_ym.search(qs) ): 
    year = re_ym.search(qs).group('year') 
    month = re_ym.search(qs).group('month') 
elif( re_y.search(qs) ): 
    year = re_y.search(qs).group('year') 
 
# Pagination queries 
re_p = re.compile('page/(?P<page>\d+)') 
if( re_p.search(qs) ): 
    page = re_p.search(qs).group('page') 
 
# Search queries 
re_s = re.compile('search/(?P<search>\w+)') 
if( re_s.search(qs) ): 
    search = re_s.search(qs).group('search') 

那么,这就是我一直在向 urls.py 中引入的减少重复复杂性的巧妙方法吗?

请您参考如下方法:

为什么不使用 GET 参数,或者 django-filter ,如果您所做的只是对结果进行不同的过滤/分组?

我看到使用 GET 的原因是它更容易实现,而且看起来更简洁:在 URL 解决方案中/search/foo/user/bar/和/user/bar/search/foo/是 2 个名称完全相同的内容。在 GET 参数解决方案中,所有页面都是相同的。