Django 路由模型

基于 Django 1.11
Django 默认会创建后台管理的 url url('admin/', admin.site.urls)。之后可以自定义 url。
url 分类

  • 普通 url 映射,直接写 url,然后引入对应函数即可
  • 动态 url 映射,需要自己写正则表达式那种,即参数里面有变量,如 url(r'^bookinfo/(\d+)/$', views.xxx)
  • 两级 url 映射,Django 为了分层,可以在每个 app 下新建自己的 url 文件,然后在项目主 url.py 中使用 include 即可

Django 默认会找 settings.py 文件中定义的 ROOT_URLCONF,找到根 url 之后,开始解析 url。
url 函数源码:

def url(regex, view, kwargs=None, name=None):
    if isinstance(view, (list, tuple)):
        # For include(...) processing.
        urlconf_module, app_name, namespace = view
        return RegexURLResolver(regex, urlconf_module, kwargs, app_name=app_name, namespace=namespace)
    elif callable(view):
        return RegexURLPattern(regex, view, kwargs, name)
    else:
        raise TypeError('view must be a callable or a list/tuple in the case of include().')

在 url 函数中如果直接跟一个函数对象或者类的 as_view()方法,那么会返回 RegexURLPattern 对象。如果是一个列表或者元组,那么返回一个 RegexURLResolver ,这种情况就是包含 include 的情况,否则抛出异常。

RegexURLPatternRegexURLResolver 都返回一个 ResolverMatch 对象,它里面会调用对应的函数。
RegexURLResolver 首先会匹配根 url 中定义的 url 前缀,然后去 include 对应的文件中去找,可以去看看它的 resolve 函数实现,找不到会抛出一个 Resolver404 异常。

来看一看具体的调度过程:


url 调度过程

从图中我们也可以发现一个问题,Django 项目不适合做 url 非常多的项目,因为匹配 url 是扫描一个列表的,当 url 规模达到一定量级的时候,扫描这样的一个列表是非常耗时的。
改进方法:利用 lru 在系统中维护一个 url 的缓存系统。可以将 url 做哈希之后与对应的 view 函数对应。

最后编辑于
©著作权归作者所有,转载或内容合作请联系作者
【社区内容提示】社区部分内容疑似由AI辅助生成,浏览时请结合常识与多方信息审慎甄别。
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

相关阅读更多精彩内容

友情链接更多精彩内容