zoukankan      html  css  js  c++  java
  • Django学习---Web框架及基础知识

    Django学习---Web框架

     web框架的本质

    我们在学socket,我们创建一个socketserver,然后运行起来,有一个client客户端要连接socket服务端,连接上之后,如果两边都没有close,就一直不断开,可以不断的进行请求。

    我们下面写一个socket服务端:

     1 import socket
     2 
     3 def handle_request(client):
     4     buf = client.recv(1024)
     5     client.send(bytes("HTTP/1.1 200 ok
    
    ",encoding="utf-8"))
     6     client.send(bytes("Hello,Charles",encoding="utf-8"))
     7 
     8 
     9 def main():
    10     sock = socket.socket(socket.AF_INET,socket.SOCK_STREAM)
    11     sock.bind(('localhost',8000))
    12     sock.listen(5)
    13 
    14     while True:
    15         connection,addr = sock.accept()
    16         handle_request(connection)
    17         connection.close()
    18 
    19 if __name__ == '__main__':
    20     main()

     运行之后主程序运行main(),main中创建了socket,监听了8000端口,最多排队五个,只要有来连接就获得这个链接,然后调用handle_requset方法处理请求。处理完之后关掉连接。

    处理请求:接受一下客户端端发过来的值,send值。

    所有的web框架的本质就是上述20行代码!!!

    在python中还提供一个其他的模块,帮我们封装socket,即wsgiref:

     1 from wsgiref.simple_server import make_server
     2  
     3  
     4 def RunServer(environ, start_response):
     5     start_response('200 OK', [('Content-Type', 'text/html')])
     6     return [bytes('<h1>Hello, web!</h1>', encoding='utf-8'), ]#返回的内容
     7  
     8  
     9 if __name__ == '__main__':
    10     httpd = make_server('', 8000, RunServer)
    11     print("Serving HTTP on port 8000...")
    12     httpd.serve_forever()

     只要有请求,就会触发RunServer函数,

    environ封装了客户端发来的所有数据,
    start_response封装要返回给用户的数据,比如:响应头,状态等

    现在我们访问localhost:8000,显示出来的都是hello,web,一般的网站的url都会有什么/data,/index等,用来显示不同的页面内容,那我们应该怎么做呢?

    我们设置断点,进入调试模式,在运行浏览器可以看到:

    environ中有很多的参数,我们找到一个叫做PATH_INFO的参数,那个就是显示我们url后面有什么。

    这样我们就能够通过url进行判断,然后进入相应的页面:

    from wsgiref.simple_server import make_server
    
    def handle_index():
        return [bytes('<h1>Hello, Index!</h1>', encoding='utf-8'), ]
    def hanle_date():
        return [bytes('<h1>Hello, Date!</h1>', encoding='utf-8'), ]
    
    def RunServer(environ, start_response):
        start_response('200 OK', [('Content-Type', 'text/html')])
        currnet_url = environ['PATH_INFO'];
        if currnet_url =='/index':
            return handle_index()
        elif currnet_url =='/date':
            return hanle_date()
        else:
            return [bytes('<h1>404,error!</h1>', encoding='utf-8'), ]
    
    
    if __name__ == '__main__':
        httpd = make_server('', 8000, RunServer)
        print("Serving HTTP on port 8000...")
        httpd.serve_forever()

     

    通过这个我们完成了一些基本的操作。

    那如果说url很多,我们不可能一个一个去判断吧,那我们应该怎么做呢?python中几乎所以的web框架都是把所有的url放在一个列表中: 然后一类的url可以通过正则表达式进行匹配

    URL_DICT = {
        "/index":handle_index,
        "/date":handle_date,
    }
    def RunServer(environ, start_response):
        start_response('200 OK', [('Content-Type', 'text/html')])
        currnet_url = environ['PATH_INFO'];
        func = None
        if currnet_url in URL_DICT:
            func = URL_DICT[currnet_url]
        if func:
            return func()
        else:
            return [bytes('<h1>404,error!</h1>', encoding='utf-8'), ]

     我们看上面的代码,如果我们把return里的html放在一个html文件中,并放在View文件夹中;把handle_index等处理业务逻辑的函数写在一个py文件中并放在Controller文件夹中。从数据库读取的方法放在Model文件夹中。

    我们需要html的时候就打开html文件f=open("html文件",mode="rb")然后read读取就可以了。

    我们需要用函数的时候就直接from Controller import 文件名,然后用文件名.函数名就可以了。

    我们在html中想要用一些特殊的符号,数据从数据库中获取替换,也只要引入model文件家中的方法,读出数据之后用replace函数替换符号和函数就可以了。

    MVC:

      Model数据库    View模板文件    Controller业务处理

    MTV:(Django是基于MTV的框架)

      Model数据库    Template模板文件    View业务处理

     Django

    安装:pip install django;

    安装完之后就多了一个可执行文件

    创建django程序:

     

    运行着个Django程序:python manage.py runserver (127.0.0.1:8001),默认端口号为8000

    django就算创建完了!!

    工程目录:

    mysite

      - mysite      #对整个程序进行配置

        -__init__.py:

        -setting.py:   #配置文件

        -url.py     #url对应关系

        -wsgi.py       #遵循WSGI规范

      -manage.py      #管理Django程序

     pycharm创建django程序:

     1.新建django

    2.运行django

    要注意要运行你的项目名称,而不是manage.py或者是其他的文件

    如果要改运行的url和端口名:

    直接在host和port中设置就可以了

    创建app:

    例如抽屉网:

      -chouti

        -配置

      -主站  app

      -后台管理 app

    创建app:

    python manage.py startapp cmdb

    app目录:

    cmdb

      -migrations:数据库操作的记录(修改表记录的操作)

      -__init__.py:

      -admin.py:django为我们提供的后台管理

      -apps.py:配置当前app

      -models.py:orm,写指定的类,通过命令可以创建数据库结构

      -tests.py:单元测试

      -views.py:业务代码

    下面我们写一个登陆页面:

    1.首先创建一个login.html页面:放在templates文件夹下面:

     1 <!DOCTYPE html>
     2 <html lang="en">
     3 <head>
     4     <meta charset="UTF-8">
     5     <title>Title</title>
     6     <link rel="stylesheet" href="/static/commons.css" />
     7     <style>
     8         label{
     9             80px;
    10             text-align: right;
    11             display: inline-block;
    12         }
    13     </style>
    14 </head>
    15 <body>
    16     <form action="/login/" method="post">
    17         <p>
    18             <label for="username">用户名:</label>
    19             <input id="username" type="text" />
    20         </p>
    21         <p>
    22             <label for="password">密码:</label>
    23             <input id="password" type="password" />
    24             <input type="submit" value="提交"/>
    25         </p>
    26 
    27     </form>
    28     <script src="/static/jquery.min.js"></script>
    29 </body>
    30 </html>
    View Code

    2.在url文件中设置login页面的路径:

    3.在cmdb这个app的view下写业务代码:

    这里django中有render模块直接封装了文件的打开读取关闭的过程。传入的login.html的路径名是由django_study下面的setting中的templates决定的:

    配置模板的目录:

    配置静态目录:

     

    <link rel="stylesheet" href="/static/commons.css" />
    <script src="/static/jquery.min.js"></script>  

     我们现在没有做数据处理,我们点击提交:出现了CSRF的错误

    如果我们不想要这个错误的话可以把settings中的代码注释了:

    知识点整理:

    1.创建django工程

      django-admin startproject 工程名

    2.创建app

      cd 工程名

      python manage.py startapp cmdb

    3.静态文件

      project.setting.py

        STATICFILES_DIRS = (os.path.join(BASE_DIR,"static"),)

    4.模板路径

      DIRS ==>os.path.join(BASE_DIR,"templates"),

    5.setting中找middleware 注释csrf

    6.定义路由规则

      url.py

        "login/"->函数名

    7.写视图函数

      app下的view.py

        def func(request):

          #request.method==POST/GET

          #request.POST.get('  ',None)     request.GET.get('  ',None)

          #返回数据:HttpResponse("str")       return render(request,"html文件路径","html中要替换的变量":USER_LIST)            return redirect("/只能填URL路径")        

    8.模板渲染

     模板语言:

      

    --{{变量名}}
        def func(request):
          return render(request,'index.html',{'current_user':"alex"})
        index.html中
        <html>
        ........
          <body>
            <div>{{current_user}}</div>#这样用alex替换了current_user
          </body>
        </html>
      --For循环
        def func(request):
          return render(request,'index.html',{
                   'current_user':"alex",
                   'user_list':{'k1':'v1','k2':'v2'}})     index.html中     <html>     ........       <body>         <div>{{current_user}}</div>#这样用alex替换了current_user         <ul>           {%for row in user_list %}           <li>{{row.k1}}</li>           {%endfor%}         </ul>       </body>     </html>
      --索引
        def func(request):
          return render(request,'index.html',{
                   'current_user':"alex",
                   'user_list':['xiaoming','liangliang']
                   'user_dict':{'k1':'v1','k2':'v2'}})     index.html中     <html>     ........       <body>         <a>{user_list.0/1}</a>
          </body>     </html>
      --条件
        {%if age %}
          <a>有年龄</a>
        {% else %}
          <a>无年龄</a>
        {% endif %}
      --循环字典
        {%for k,row in dict.items%}#同时获得key和value
          <li>{{k}}-{{row}}</li>
        {%endfor%}
        {%for row in dict.keys%}#获得字典中的key
          <li>{{row}}</li>
        {%endfor%}
        {%for row in dict.values%}#获得字典中的value
          <li>{{row}}</li>
        {%endfor%}
  • 相关阅读:
    Oracle查询中将结果列按分组用逗号隔开,拼接成一行(listagg函数)
    Oracle SQL获取每个分组中日期最大的一条数据
    oracle字段根据字符串拆分,用subStr()和inStr()进行拆分
    javascript求最大公约数
    javascript单链表
    防input required属性的提示框
    css3绘制三色字
    js和php时间戳的问题
    ajax使用的一些错误
    浏览器js文件未及时更新问题
  • 原文地址:https://www.cnblogs.com/charles8866/p/8605911.html
Copyright © 2011-2022 走看看