• flask框架(五)——支持正则写法、模板用法、请求响应、session


    如果用正则的话,我们要用自定义的路由。

    1导入from werkzeug.routing import BaseConverter
    2我先要写一个类,然后继承BaseConverter,然后实现__init__, to_python(self, value),to_url(self, value)  这三个方法
    3 app.url_map.converters['随便写'] = RegexConverter
    4 我们在路由里面@app.route('/index/<regex1("d+"):nid>'),regex1是随便写,regex1("正则表达式")
    5 regex1("正则表达式")匹配出来的结果,返回to_python,一定要return  (视图函数的参数能接收到to_python的返回值)
    6 当我们做反向解析的解析的时候,传递的参数,会传递给to_url,return的结果是拼接到我们路由上

    代码示例:

    from flask import Flask,url_for
    from werkzeug.routing import BaseConverter
    
    app = Flask(import_name=__name__)
    
    class RegexConverter(BaseConverter):
        """
        自定义URL匹配正则表达式
        """
        def __init__(self, map, regex):
            super(RegexConverter, self).__init__(map)
            self.regex = regex
    
        def to_python(self, value):
            """
            路由匹配时,匹配成功后传递给视图函数中参数nid
            """
            #value就正则匹配出来的结果
            print('value',value,type(value))
            return "asdasdasd"  #返回值返回给视图函数中的参数
    
        def to_url(self, value):
            """
            使用url_for反向生成URL时,传递的参数经过该方法处理,返回的值用于生成URL中的参数
            """
            val = super(RegexConverter, self).to_url(value)
            print(val)  #val是传入的nid值
            return val   #返回值用于拼接成路径
    
    app.url_map.converters['regex1'] = RegexConverter
    @app.route('/index/<regex1("d+"):nid>',endpoint="sb")
    def index(nid):
        print("nid",nid,type(nid))
        print(url_for('sb', nid='888'))  #/index/888
        return 'Index'
    
    if __name__ == '__main__':
        app.run()

    模板

    模板传递参数、变量的循环、传递html语言代码并且识别

    test1.py

    
    
    USERS = {
    1:{'name':'张三','age':18,'gender':'男','text':"道路千万条"},
    2:{'name':'李四','age':28,'gender':'男','text':"安全第一条"},
    3:{'name':'王五','age':18,'gender':'女','text':"行车不规范"},
    }
    def func1(st,st1):
        return Markup(f"<h1>jsaon-gdx{st}{st1}</h1>")
    
    @app.route('/list',methods=['GET'])
    def list():
        info=USERS
        return render_template('list.html',info1=info,html="<h1>jsaon-gdx</h1>",html1=func1)

    list.html (注意:后台传递参数值是info1,前台接收参数也要写info1)

    <!DOCTYPE html>
    <html lang="en">
    <head>
        <meta charset="UTF-8">
        <title>Title</title>
    
    </head>
    <body>
    {% for k,v in info1.items() %}  #后台传递的info1参数
            <tr>
                <td>{{k}}</td>
                <td>{{v.name}}</td>
                <td>{{v['name']}}</td>
                <td>{{v.get('name')}}</td>
                <td><a href="{{url_for('sb',nid=k)}}">查看详细</a></td>
            </tr>
    {% endfor %}
    {{html|safe}}  #传递的html语句,使用|safe能取消转义,从字符串变成能正常显示的html语法
    {{html1("-DSB","-SB")}}  #使用Markup,能传递html语句,并且可以传参
    
    </body>
    </html>

    注意:Mark等价于django的mark_safe

    在html中也能通过url_for反向解析路径,并且能够传参(******)

     test.py

    @app.route('/detail/<int:nid>',methods=['GET'],endpoint="sb")
    def detail(nid):
    
        return "ok"

    list.html   (在detail视图函数中设置好别名,)

    <td><a href="{{url_for('sb',nid=k)}}">查看详细</a></td>  #路由跳转,并且把k值传递给nid

    请求响应

     from flask import Flask
        from flask import request
        from flask import render_template
        from flask import redirect
        from flask import make_response
    
        app = Flask(__name__)
    
    
        @app.route('/login.html', methods=['GET', "POST"])
        def login():
    
            # 请求相关信息
            # request.method  提交的方法
            # request.args  get请求提及的数据
            # request.form   post请求提交的数据
            # request.values  post和get提交的数据总和
            # request.cookies  客户端所带的cookie
            # request.headers  请求头
            # request.path     不带域名,请求路径
            # request.full_path  不带域名,带参数的请求路径
            # request.script_root  
            # request.url           带域名带参数的请求路径
            # request.base_url      带域名请求路径
            # request.url_root      域名
            # request.host_url      域名
            # request.host          127.0.0.1:500
            # request.files
            # obj = request.files['the_file_name']
            # obj.save('/var/www/uploads/' + secure_filename(f.filename))
    
            响应相关信息(4剑客)
            # return "字符串"
            # return render_template('html模板路径',**{})
            # return redirect('/index.html')
            #return jsonify({'k1':'v1'})
    
            # response = make_response(render_template('index.html'))
            # response是flask.wrappers.Response类型
            # response.delete_cookie('key')
            # response.set_cookie('key', 'value')
            # response.headers['X-Something'] = 'A value'
            # return response
            return "内容"
    
        if __name__ == '__main__':
            app.run()

    session

    cookie:存放在客户端的键值对
    session:存放在客户端的键值对
    token:存放在客户端,通过算法来校验

    在使用session之前必须设置一下密钥

    app = Flask(__name__)
    app.secret_key="askjdaksd"   #随便写

    除请求对象之外,还有一个 session 对象。它允许你在不同请求间存储特定用户的信息。它是在 Cookies 的基础上实现的,并且对 Cookies 进行密钥签名,要使用会话你需要设置一个密钥。 (app.session_interface对象)

    到源码app.session_interface这里面看(******)
    存session:
    1 调用save_session,将我们的session加密的val,读取配置文件['SESSION_COOKIE_NAME']得到key
    2 将1中的key,val存储到cookies
    
    取session:
    1 获取request里面的cookies,获取里面key,这个key就是['SESSION_COOKIE_NAME'],值就是加密的值
    2 对该值进行解密

    app.session_interface中save_session的参数(设置cookie的参数)

    key, 键
    value='', 值
    max_age=None, 超时时间 cookie需要延续的时间(以秒为单位)如果参数是 None`` ,这个cookie会延续到浏览器关闭为止
    expires=None, 超时时间(IE requires expires, so set it if hasn't been already.)
    path='/', Cookie生效的路径,/ 表示根路径,特殊的:根路径的cookie可以被任何url的页面访问,浏览器只会把cookie回传给带有该路径的页面,这样可以避免将cookie传给站点中的其他的应用。
    domain=None, Cookie生效的域名 你可用这个参数来构造一个跨站cookie。如, domain=".example.com"所构造的cookie对下面这些站点都是可读的:www.example.com 、 www2.example.com 和an.other.sub.domain.example.com 。如果该参数设置为 None ,cookie只能由设置它的站点读取
    secure=False, 浏览器将通过HTTPS来回传cookie
    httponly=False 只能http协议传输,无法被JavaScript获取(不是绝对,底层抓包可以获取到也可以被覆盖)

    session源码执行流程

    -save_seesion
        -响应的时候,把session中的值加密序列化放大到了cookie中,返回到浏览器中
    -open_session
        -请求来了,从cookie中取出值,反解,生成session对象,以后再视图函数中直接用sessoin就可以了。

    代码示例:

    from flask import Flask,session
    
    app = Flask(__name__)
    app.secret_key="askjdaksd"
    app.config['SESSION_COOKIE_NAME']="dsb"
    
    @app.route("/")
    def index():
        session['jason']="gdx"
        return "ok"
    
    @app.route("/index1")
    def index1():
        print(session['jason'])
        return "ok1"
    
    if __name__ == '__main__':
        app.run()

  • 相关阅读:
    pom变成红橙色
    拉链表
    Newsgroups数据集研究
    python 安装第三方包
    概率图(三)CRF条件随机场
    概率图(二)马尔科夫随机场MRF
    LDA主题模型
    TF-IDF算法
    mysql 自定义排序顺序
    [转]解决a different object with the same identifier value was already associated with the session错误
  • 原文地址:https://www.cnblogs.com/wangcuican/p/11844342.html
Copyright © 2020-2023  润新知