zoukankan      html  css  js  c++  java
  • Django框架之路由层,本地虚拟环境搭建

    路由层

    路由即请求地址与视图函数的映射关系,如果把网站比喻成一本书,那路由就是这本书的目录,在django中默认把路由配置在urls.py中

    路由配置

    # urls.py
    from django.conf.urls import url
    from django.contrib import admin
    from app01 import views
    
    urlpatterns = [
        url(r'^admin/', admin.site.urls),
        url(r^test/[0-9]{4})/$,views.test  # 数字组加量字的组合(限制四位数)
        url(r'^test/(d+)/$',views.test),  # 无名分组:数字贪婪匹配
        url(r'^testadd/(?P<id>d+)/$',views.testadd), # 有名分组
        url(r'^test2/(d+)/(d+)/$',views.test2),  # 无名分组多个
        url(r'^test2/(?P<id>d+)/(?P<id1>d+)/$',views.test2)   # 有名分组多个
    ]
    

    路由的简单配置示例

    #urls.py
    from django.conf.urls import url
    from django.contrib import admin
    from app01 import views  # 导入模块views.py
    """
    由一条条映射关系组成的urlpatterns列表称之为路由表
    url()方法
    ^xxxx/$ :第一个参数其实是正则表达式,用来匹配url地址的路径部分
    view.xxxx :一旦第一个参数匹配到了内容则直接结束匹配,执行对应的视图函数,
    		   来处理业务逻辑
    """
    
    urlpatterns= [
        url(r'^admin/',admin.site.urls),
        # 写我们自己的路由与视图函数对应关系
        url(r'^index/$',views.index) # 新增一条
    ]
    
    
    #views.py
    from django.shortcuts import render,HttpResponse
    
    def index(request):
        return HttpResponse('holle word')
    
    # settings.py
    
    # APPEND_SLASH = False   # 控制是否加斜杠再次请求 
    # 改参数默认就是True  一般情况下无需修改
    

    注意:用上面这个示例运行djongo项目,在浏览器中输入http://127.0.01:8080/index/会看到hello word,因为r'^index/$'正则表达式匹配成功了,但是在浏览器中输入http://127.0.01:8080/index,理应不会匹配成功任何正则表达式,但是还是会看到hello word因为在配置文件settings.py中有一个默认参数APPEND_SLASH,该参数有两个值(True或False,如果没有设置就默认为True),当为True时 ,Django会在路径后面自动加上/,再去匹配

    路由匹配规律

    先不加/匹配一次,如果匹配不上,浏览器进行重定向,自动加一个/再匹配一次,如果还匹配不上就会报错

    无名分组:

    执行视图函数的时候会将分组(括号)内正则表达式匹配到的内容当做位置参数传递给对应的视图函数,视图函数加一个形参接收,再通过reverse进行反向解析得完整的请求地址,这样就可以知道用户访问的是什么资源,进行针对性返回

    # 路由urls.py
    url(r'^test/d+/$',views.test)
    # 正则表达式分组:给正则表达式前后加一个小括号
    url(r'^test/(d+)/$',views.test)
    
    # 视图views.py
    def test(request,xxx):
        print(xxx)
        return HttpResponse('from test')
    

    有名分组

    执行视图函数的时候会将分组(括号)内正则表达式匹配到的内容当做关键字参数传递给对应的视图函数

    # 路由
    url(r'^testadd/(?P<id>d+)/$',views.testadd)  # 给正则表达式起个别名
    
    # 视图
    def test(request,id):
        print(id)
        return HttpResponse('from testadd')
    

    是否可以结合使用

    利用有名分组和无名分组 我们就可以在调用视图函数之前给函数传递额外的参数

    注意:无名分组和有名分组不能混合使用

    但是同一种分组的情况下可以使用多次,
    无名可以有多个

    有名可以有多个

    # 第一个是无名,第二个是有名
    url(r'^test1/(d+)/(?P<id>d+)/$',views.test1) # 报错,不能混用
    
    # 可以无名分组多个使用
    url(r'^test2/(d+)/(d+)/$',views.test2),
    # 可以有名分组多个使用
    url(r'^test2/(?P<id>d+)/(?P<id1>d+)/$',views.test2)
    

    反向解析

    当路由频繁变化的时候,html界面上的连接地址如何做到动态解析?

    根据自己设置的一个别名,动态解析出一个结果,该结果可以直接访问对应的url

    1.给路由与视图函数对应关系添加一个别名(名字自己指定 只要不冲突即可)
    # 路由	
        url(r'^index/',views.index,name='index_name')
         
    2.根据该别名动态解析出一个结果,该结果可以直接访问到对应的路由
    # 前端模板文件中使用
        <a href="{% url 'index_name' %}">111</a>
        
    # 后端视图函数中使用
    from django.shortcuts import reverse # 需要导一个反向解析模块
    reverse('index_name')
    	ps:redirect括号内也可以直接写别名
    

    无名分组反向解析

    当路由出现无名有名分组反向解析需要传递额外的参数

    # 路由
    	url(r'^index/(d+)/',views.index,name='index_name') 
        
    # 前端模板文件中使用
    	<a href="{% url 'index_name' 1 %}"></a>  # 只要给个数字即可
        
    # 后端视图函数中使用
    	reverse('index_name',args=(1,))  # 只要给个数字即可
    

    有名分组反向解析

    # 路由
    	url(r'^index/(?P<id>d+)/',views.index,name='index_name')
        
    # 前端模板文件中使用
    	<a href="{% url 'index_name' id=666 %}"></a>  # 只要给个数字即可
       
    # 后端视图函数中使用
    	reverse('index_name',kwargs={'id':123})  # 只要给个数字即可
    
    

    总结

    ​ 针对无名分组有名分组都可以使用一种(无名)反向解析的形式

    反向解析的本质: 就是获取到一个能够访问名字所对应的视图函数

    路由分发

    简介

    ​ django是专注于开发应用的,当一个django项目特别庞大的时候,所有的路由与视图函数映射关系全部写在项目名下urls.py(总路由层),很明显太冗余也不便于管理

    其实在django中的每一个(app)应用都可以有自己独立的urls.py路由层,static文件夹,templates文件夹。

    基于上述特点,使用django做分组开发非常的简便。每个人只需要写自己的应用即可,互不干扰。最后由组长统一汇总到一个空的django项目中然后使用路由分发将多个应用关联到一起,即可完成大项目的拼接

    • 路由分发解决的就是项目的总路由匹配关系过多的情况
    • 使用路由分发 会将总路由不再做匹配的活
    • 而仅仅是做任务分发(请求来了之后 总路由不做对应关系 只询问你要访问哪个app的功能 然后将请求转发给对应的app去处理 )

    1.路由分发,复杂版本

    # 需要导入一个include模块
    from django.conf.urls import url,include 
    
    # 导入子路由的uls
    from app01 import urls as app01_urls
    from app02 import urls as app02_urls
    
    # 路由分发,复杂版本
    url(r'^app01/',include(app01_urls))
    url(r'^app02/',include(app02_urls))
    '''总路由最后千万不能加$'''
    
    

    2.路由分发,进阶版本

    from django.conf.urls import url,include
    
    url(r'^app01/',include('app01.urls')),
    url(r'^app02/',include('app02.urls'))
    '''总路由最后千万不能加$'''
    # app01.urls就相当于于from app01 import urls as app01_urls
    

    名称空间

    """
    当多个应用在反向解析的时候如果出现了别名冲突的情况,那么无法自动识别
    """
    解决方式1>>>:名称空间
        总路由
    	 url(r'^app01/',include('app01.urls',namespace='app01'))
             url(r'^app02/',include('app02.urls',namespace='app02'))
        
             reverse('app01:index_name')
             reverse('app02:index_name')
        
             <a href="{% url 'app01:index_name' %}">app01</a>
    	 <a href="{% url 'app02:index_name' %}">app02</a>
            
    解决方式2>>>:别名不能冲突(加上自己应用名作为前缀)
        url(r'^index/',views.index,name='app01_index_name')
        url(r'^index/',views.index,name='app02_index_name')
    

    伪静态

    原来是动态页面/login 做成/login.html

    将url地址模拟成html结尾的样子,看上去像是一个静态文件

    目的是为了增加搜索引擎收藏我们网站的概率以及seo查询几率

    ps:再怎么优化都不如RMB玩家!!!

    本地虚拟环境

    在实际的开发过程中,我们会给不同的项目配备不同的环境,项目用到什么就装什,用不到的一概不装,不同的项目解释器环境都不一样

    • 创建虚拟环境类似于你重新下载了一个纯净的python解释器
    • 如果反复创建类似于反复下载,会消耗一定的硬盘空间
      ps:我们目前不推荐你使用虚拟环境,所有的模块统一全部下载到本地

    了解知识:项目依赖 requirements.txt

    python语言算是比较早提出包管理概念的, 使用pip安装依赖的确是非常方便. 对于一些简单的脚本或爬虫, 我们一般直接使用
    系统python环境安装相关依赖. 稍微大一点的项目, 比如使用了Django, 那么所需要的依赖就非常多, 这个时候使用venv隔离
    环境就非常好(建议python项目多使用venv环境). 但我们的问题是, 当我们将项目移到另一个环境中时, 这些依赖怎么安装, 
    还是一个一个去对比执行? 
    解决方法:
    1. 导出原项目的依赖
    pip freeze > requirements.txt
    
    2. 在新项目中一次性安装依赖
    pip install -r requirements.txt
    

    在pycharm窗口选择file----->settings

    选择Project Interpreter----->设置按钮选择Add
    image-20210401175142964
    根据自身需求进行选项,最好将虚拟环境放在指定的文件夹内,方便后面的项目使用
    image-20210401175700828
    在虚拟环境下创建新的django项目需要注意的:
    image-20210401181408288

    django版本区别

    django1.X与2.X、3.X之间路由的区别
    
    urls.py中的路由匹配方法:
        1.X第一个参数正则表达式
            url()
        2.X和3.X第一个参数不支持正则表达式,写什么就匹配什么,100%精准匹配
            path()
        如果想要使用正则,那么2.X与3.X也有响应的方法
            from django.urls import path,re_path
            re_path 等价于 1.X里面的url方法
     
    虽然django1.X与2.X里面的path不支持正则表达式,但是它提供五个默认的转换器
    
       str,匹配除了路径分隔符(/)之外的非空字符串,这是默认的形式
       int,匹配正整数,包含0。
       slug,匹配字母、数字以及横杠、下划线组成的字符串。
       uuid,匹配格式化的uuid,如 075194d3-6885-417e-a8a8-6c931e272f00。
       path,匹配任何非空字符串,包含了路径分隔符(/)(不能用?)
        
    自定义转换器(了解):
    class MonthConverter:
        regex='d{2}' # 属性名必须为regex
    
        def to_python(self, value):
            return int(value)
        
        def to_url(self, value):
            return value # 匹配的regex是两个数字,返回的结果也必须是两个数字
            
    from django.urls import path,register_converter
    from app01.path_converts import MonthConverter
    
    register_converter(MonthConverter,'mon')
    
    from app01 import views
    
    urlpatterns = [
            path('articles/<int:year>/<mon:month>/<slug:other>/', views.article_detail, name='aaa'),
    ]
    
    从来就没有正确的选择,我们只不过是要努力奋斗,使当初的选择变得正确。
  • 相关阅读:
    ASP.NET存储Session的StateServer
    EasyUI中DataGrid构建复合表头
    EasyUI使用DataGrid向服务器传参
    CentOS 7 U盘安装问题解决
    对指定表的某一列数据合并单元格
    常用的一些sql
    Oracle数据库表空间常用操作
    修改Oracle redo.log文件的大小
    UOJ 非传统题配置手册
    UOJ552 【UNR #4】同构判定鸭【线性代数,哈希】
  • 原文地址:https://www.cnblogs.com/gfeng/p/14550606.html
Copyright © 2011-2022 走看看