zoukankan      html  css  js  c++  java
  • django基础01

    创建项目

    1. 通过命令行的方式:首先要进入到安装了django的虚拟环境中。然后执行命令:

      django-admin startproject [项目的名称]
      

      这样就可以在当前目录下创建一个项目了。

    2. 通过pycharm的方式:文件->新建项目->选择django。然后指定项目所在的路径,以及Python解释器,再点击Create就可以创建项目了。

    运行项目

    1. 终端:进入到项目文件夹中,然后执行以下命令即可运行:

      python manage.py runserver
      
    2. pycharm:直接点击右上角的绿色三角箭头按钮就可以了。注意:用pycharm运行项目,要避免一个项目运行多次。。在项目配置中,把“只用单一实例”那个选项勾选上,避免以上的问题。

    改变端口号

    1. 在终端:运行的时候加上一个端口号就可以了。命令为:python manage.py runserver 9000
    2. 在pycharm中:右上角->项目配置->port。改成你想要的端口号,重新运行。

    让同局域网中的其他电脑访问本机的项目

    1. 让项目运行到额时候,host为0.0.0.0。

      • 在终端,使用命令:python manage.py runserver 0.0.0.0:8000
      • 在pycharm,右上角->项目配置->host。改成0.0.0.0
    2. settings.py文件中,配置ALLOWED_HOSTS,将本机的ip地址添加进去。示例代码如下:

      ALLOWED_HOSTS = ['192.168.0.103']
      

      注意:要关闭自己电脑的防火墙才行。

    项目结构分析

    1. manange.py:以后和项目交互基本上都是基于这个文件。一般都是在终端输入python manage.py [子命令]。可以输入python manage.py help看下能做什么事情。除非你知道你自己在做什么,一般情况下不应该编辑这个文件。
    2. settings.py:保存项目所有的配置信息。
    3. urls.py:用来做url与视图函数映射的。以后来了一个请求,就会从这个文件中找到匹配的视图函数。
    4. wsig.py:专门用来做部署的。不需要修改。

    django推荐的项目规范

    按照功能或者模块进行分层,分成一个个app。所有和某个模块相关的视图都写在对应的app的views.py中,并且模型和其他的也是类似。然后django已经提供了一个比较方便创建app的命令叫做python manage.py startapp [app的名称]。把所有的代码写在各自的app中。

    DEBUG模式

    1. 如果开启了DEBUG模式,那么以后我们修改了Django项目的代码,然后按下ctrl+s,那么Django就会自动的给我们重启项目,不需要手动重启。
    2. 如果开启了DEBUG模式,那么以后Django项目中的代码出现bug了,那么在浏览器中和控制台会打印出错信息。
    3. 在生产环境中,禁止开启DEBUG模式,不然有很大的安全隐患。
    4. 如果将DEBUG设置为False,那么必须要设置ALLOWED_HOSTS.

    ALLOWED_HOSTS

    这个变量是用来设置以后别人只能通过这个变量中的ip地址或者域名来进行访问。

    前端参数传递

    • 采用url路径中使用PATH的方式传递参数,采用<int:id>的方式来传递,一定要在视图函数中的参数中对参数进行接收,否则报错

    • 采用查询字符串的方式,在url后面加上?xxx=xxx的方式来传递参数,后端接收参数使用request.GET.get("xxx")的方式来获取参数

    • 使用表单的方式来传递,在后端使用request.POST.get(“xxx”)来获取前端传递的参数

    • 使用json的方式进行传递,在后端使用data = request.body.decode("utf-8")json.loads(data)来获取json格式的数据

    url转换器

    使用格式/<int:id>/的格式来使用转换器,如果不指定转换器类型,默认使用的是str转换器

    django默认的转换器

    DEFAULT_CONVERTERS = {
        'int': IntConverter(),
        'path': PathConverter(),
        'slug': SlugConverter(),
        'str': StringConverter(),
        'uuid': UUIDConverter(),
    }
    
    class IntConverter:
        regex = '[0-9]+'
    
        def to_python(self, value):
            return int(value)
    
        def to_url(self, value):
            return str(value)
    
    def register_converter(converter, type_name):
        REGISTERED_CONVERTERS[type_name] = converter()
        get_converters.cache_clear()
    
    • 自定义url转换器

    参照官方的转换器写法定义一个转换器类,将这个转换器类注册到DEFAULT_CONVERTERS中
    1、定义一个类,直接继承自object就可以
    2、在类中定义一个属性regex,这个属性是用来限制url转换器规则的正则表达式。
    3、实现to_python(self,value)方法,这个方法是将url中的值转换下,然后传给视图函数的。
    4、实现to_url(self,value)方法,这个方法是在做url反转的时候,将传进来的参数转换后拼接成一个正确的url。
    5、将定义好的转换器,使用'django.urls.converters.register_converter'方法注册到django中。

    from django.urls import register_converter
    
    
    class CategoryConverter(object):
        regex = r'w+|(w++w+)+'
    
        def to_python(self, value):
            # 将url里的'python+django+pandas'转换成:['python', 'django', 'pandas']传给视图函数
            result = value.split('+')
            return result
    
        def to_url(self, value):
            if isinstance(value, list):
                # 将视图函数里的['python', 'django', 'pandas']转换成'python+django+pandas'传给URL
                result = '+'.join(value)
                return result
            else:
                raise RuntimeError('转换url的时候,分类参数必须为列表')
    
    # register_converter(上面自己定义的类名,自定义的类型名(在urls.py文件中使用))
    register_converter(CategoryConverter, 'cate')
    

    在app根目录下的__init__.py中添加:

    from . import converters
    

    在urls.py中使用即可,如:

    path('article/<cate:classify>',views.article_classify_list,name='article_classify'),
    

    urls模块化

    如果项目变得越来越大。那么url会变得越来越多。如果都放在主urls.py文件中,那么将不太好管理。因此我们可以将每个app自己的urls放到自己的app中进行管理。一般我们会在app中新建一个urls.py文件用来存储所有和这个app相关的子url。
    需要注意的地方:

    1. 应该使用include函数包含子urls.py,并且这个urls.py的路径是相对于项目的路径。示例代码如下:
      urlpatterns = [
          path('admin/', admin.site.urls),
          path('book',include('book.urls'))
      ]
      
    2. appurls.py中,所有的url匹配也要放在一个叫做urlpatterns的变量中,否则找不到。
    3. url是会根据主urls.py和app中的urls.py进行拼接的,因此注意不要多加斜杠。

    include函数的用法

    1. include(module,namespace=None):
      • module:子url的模块字符串。
      • namespace:实例命名空间。这个地方需要注意一点。如果指定实例命名空间,那么前提必须要先指定应用命名空间。也就是在子urls.py中添加app_name变量。
    2. include((pattern_list, app_namespace), namespace=None):include函数的第一个参数既可以为一个字符串,也可以为一个元组,如果是元组,那么元组的第一个参数是子urls.py模块的字符串,元组的第二个参数是应用命名空间。也就是说,应用命名空间既可以在子urls.py中通过app_name指定,也可以在include函数中指定。
    3. include(pattern_list):pattern_list是一个列表。这个列表中装的是path或者re_path函数。实例代码如下:
      path('movie/',include([
          path('',views.movie),
          path('list/',views.movie_list),
      ]))
      

    url反转和重定向

    需要用到i的函数from django.shortcuts import redirect,resolve_url

    url反转需要在url定义的时候给url取个名字,在urls.py记得使用app_name指定应用命名空间,以后在做反转的时候front:index来反转index对应的的url

    重定向直接调用redirect(args) 参数可以是一个模型,或者是url字符串或者视图函数的名字

    reverse用法

    1. 如果在反转url的时候,需要添加参数,那么可以传递kwargs参数到revers函数中。示例代码如下:

      detail_url = reverse('detail',kwargs={"article_id":1,'page':2})
      
    2. 如果想要添加查询字符串的参数,则必须手动的进行拼接。示例代码如下:

      login_url = reverse('login') + "?next=/"
      

    偏函数

    在Python中的functools中partial来实现 ,这个函数的作用是给有固定参数的函数一个简单的封装

    def _index(arg1,arg2,arg3=None):
        print(arg1)
        print(arg2)
        print(arg3)
    
    from functools import partial
    
    index = partial(_index,2,arg3=4)
    index(3)
    >>>
    2
    3
    4
    

    URL映射的时候指定默认参数

    使用path或者是re_path的后,在route中都可以包含参数,而有时候想指定默认的参数,这时候可以通过以下方式来完成。示例代码如下:

    from django.urls import path
    
    from . import views
    
    urlpatterns = [
        path('blog/', views.page),
        path('blog/page<int:num>/', views.page),
    ]
    
    # View (in blog/views.py)
    def page(request, num=1):
        # Output the appropriate page of blog entries, according to num.
        ...
    

    当在访问blog/的时候,因为没有传递num参数,所以会匹配到第一个url,这时候就执行view.page这个视图函数,而在page函数中,又有num=1这个默认参数。因此这时候就可以不用传递参数。而如果访问blog/1的时候,因为在传递参数的时候传递了num,因此会匹配到第二个url,这时候也会执行views.page,然后把传递进来的参数传给page函数中的num。

    re_path用法

    1. re_path和path的作用都是一样的。只不过re_path是在写url的时候可以用正则表达式,功能更加强大。
    2. 写正则表达式都推荐使用原生字符串。也就是以r开头的字符串。
    3. 在正则表达式中定义变量,需要使用圆括号括起来。这个参数是有名字的,那么需要使用?P<参数的名字>。然后在后面添加正则表达式的规则。示例代码如下:
      from django.urls import re_path
      from . import views
      
      urlpatterns = [
          # r"":代表的是原生字符串(raw)
          re_path(r'^$',views.article),
          # /article/list/<year>/
          re_path(r"^list/(?P<year>d{4})/$",views.article_list),
          re_path(r"^list/(?P<month>d{2})/$",views.article_list_month)
      ]
      
    4. 如果不是特别要求。直接使用path就够了,省的把代码搞的很麻烦(因为正则表达式其实是非常晦涩的,特别是一些比较复杂的正则表达式,今天写的明天可能就不记得了)。除非是url中确实是需要使用正则表达式来解决才使用re_path

    为什么需要url命名?

    因为url是经常变化的。如果在代码中写死可能会经常改代码。给url取个名字,以后使用url的时候就使用他的名字进行反转就可以了,就不需要写死url了。

    如何给一个url指定名称?

    path函数中,传递一个name参数就可以指定。示例代码如下:

    urlpatterns = [
        path('',views.index,name='index'),
        path('login/',views.login,name='login')
    ]
    

    应用命名空间

    在多个app之间,有可能产生同名的url。这时候为了避免反转url的时候产生混淆,可以使用应用命名空间,来做区分。定义应用命名空间非常简单,只要在appurls.py中定义一个叫做app_name的变量,来指定这个应用的命名空间即可。示例代码如下:

    # 应用命名空间
    app_name = 'front'
    
    urlpatterns = [
        path('',views.index,name='index'),
        path('login/',views.login,name='login')
    ]
    

    以后在做反转的时候就可以使用应用命名空间:url名称的方式进行反转。示例代码如下:

    login_url = reverse('front:login')
    

    应用(app)命名空间和实例命名空间

    一个app,可以创建多个实例。可以使用多个url映射同一个app。所以这就会产生一个问题。以后在做反转的时候,如果使用应用命名空间,那么就会发生混淆。为了避免这个问题。我们可以使用实例命名空间。实例命名空间也是非常简单,只要在include函数中传递一个namespace变量即可。示例代码如下:

    urlpatterns = [
        path('',include('front.urls')),
        # 同一个app下有两个实例
        path('cms1/',include('cms.urls',namespace='cms1')),
        path('cms2/',include('cms.urls',namespace='cms2')),
    ]
    

    以后在做反转的时候,就可以根据实例命名空间来指定具体的url。示例代码如下:

    def index(request):
        username = request.GET.get("username")
        if username:
            return HttpResponse('CMS首页')
        else:
            # 获取当前的命名空间
            current_namespace = request.resolver_match.namespace
            return redirect(reverse("%s:login"%current_namespace))
    

    视图函数

    1. 视图函数的第一个参数必须是request。这个参数绝对不能少。
    2. 视图函数的返回值必须是django.http.response.HttpResponseBase的子类的对象。
  • 相关阅读:
    LeetCode15 3Sum
    LeetCode10 Regular Expression Matching
    LeetCode20 Valid Parentheses
    LeetCode21 Merge Two Sorted Lists
    LeetCode13 Roman to Integer
    LeetCode12 Integer to Roman
    LeetCode11 Container With Most Water
    LeetCode19 Remove Nth Node From End of List
    LeetCode14 Longest Common Prefix
    LeetCode9 Palindrome Number
  • 原文地址:https://www.cnblogs.com/huameixiao/p/13513393.html
Copyright © 2011-2022 走看看