【课程笔记】Python web概述及Flask介绍

【课程笔记】Python web概述及Flask介绍

一、准备工作
1.安装virtualenv

打开命令行,执行:pip list 查看当前python环境里面是否安装virtualenv,如果没有,请执行:

pip install -i virtualenv  
pip install -i https://pypi.mirrors.ustc.edu.cn/simple/ virtualenv

安装完成后,再次执行pip list查看

2.创建虚拟环境

通过上面的步骤安装成功virtualenv之后,我们就可以创建虚拟环境了:virtualenv 虚拟环境名

注意:这个命令创建虚拟环境,会在当前所在目录进行创建,如C:\Users\Smalu(电脑管理者路径),所以如果你有指定路径存放虚拟环境,请先进入该路径

cd 文件地址

再执行

virtualenv your_env_name
3.进入虚拟环境

先要进入cd到虚拟环境的位置(目录)的Scripts中,然后在激活(activate.bat)虚拟环境,则进入新建的虚拟环境中了。

cd 虚拟环境名
cd Scripts
activate
4.在上述虚拟环境中,安装Flask环境
pip install –U flask
5.安装完成以后,再次使用pip list命令查看所有安装包
6.Flask的7个外部依赖包
名称功能
Click(7.1.2)命令行工具
itsdangerous(1.1.0)提供加密和签名功能
Jinjia2(2.11.3)模板渲染引擎
MarkupSafe(1.1.1)HTML字符转义(escape)工具
setuptools(51.3.3)可以帮助我们更简单的创建和分发Python包,尤其是拥有依赖关系的
Werkzeug(1.0.1)WSGI工具集,处理请求与响应,内置WSGI开发服务器、调试器和重载器
wheel(0.36.2)新的 Python 的 disribution,用于替代 Python 传统的 egg 文件
二、编程
1.编写第一个Flask程序
from flask import Flask
app = Flask(__name__)

@app.route('/')
def hello_world():
     return '你好!'

if __name__ == '__main__':
	app.debug = True
    app.run()

ps:
有两种途径来启用调试模式。一种是直接在应用对象上设置。
app.debug = True
app.run()
另一种是作为run方法的一个参数传入。
app.run(debug=True)

2.Flask 路由
from flask import Flask, views, redirect, url_for
app = Flask(__name__)


# 路由
@app.route('/hello1')
def hello1():
    return '第一种路由写法'


@app.route('/hello2')
def hello2():
    return '第二种路由写法'


app.add_url_rule('/hello2', 'h2', hello2, methods=['GET'])


if __name__ == '__main__':
    app.debug = True
    app.run()

运行:

[127.0.0.1:5000/hello1](http://127.0.0.1:5000/hello1)

tips:

1.黄色波浪线:代码靠得太近,一般空两行。

2.运行没效果:注意是不是运行到别的文件。

3.Flask 变量规则
from flask import Flask, views, redirect, url_for

app = Flask(__name__)


@app.route('/hello/<name>')    # 变量name默认值是str
def hello_name(name):
   return 'Hello %s!' % name


@app.route('/blog/<int:postID>')
def show_blog(postID):
   return 'Blog Number is %d' % postID


@app.route('/rev/<float:revNo>')
def revision(revNo):
   return 'Revision Number %.2f' % revNo


@app.route('/showany/<path:special_str>') # special_str允许存在/这种有歧义的字符
def showAnyInfo(special_str):
   return "I can show any info ,such as '%s'" % special_str
   
if __name__ == '__main__':
   app.debug = True
   app.run()

运行:

http://localhost:5000/hello/chen
http://localhost:5000/blog/5
http://localhost:5000/rev/0.68
http://localhost:5000/showany/shenm/%E8%80%8C%E9%9D%9Ee
4.为视图绑定多个URL
from flask import Flask, views, redirect, url_for

app = Flask(__name__)


@app.route('/')
@app.route('/index')
def index():
      return "Welcome to Flask"


if __name__ == '__main__':
    app.debug = True
    app.run()

运行:

http://localhost:5000
http://localhost:5000/index
5.构造 URL
from flask import Flask, views, redirect, url_for, render_template
app = Flask(__name__)



# 3.2构造url
@app.route('/post/<int:post_id>')
def show_post(post_id):
    print(post_id)
    return f'文章的id:{post_id}'


# 绑定url
@app.route('/url/')
def redirect_to_url():
    # 跳转到show_post视图函数
    return url_for('show_post', post_id=10)


if __name__ == '__main__':
    app.debug = True
    app.run()
6.HTTP方法
序号方法与描述
1GET, 以未加密的形式将数据发送到服务器。最常见的方法。
2HEAD, 和GET方法相同,但没有响应体。
3POST, 用于将HTML表单数据发送到服务器。POST方法接收的数据不由服务器缓存。
4PUT, 用上传的内容替换目标资源的所有当前表示。
5DELETE, 删除由URL给出的目标资源的所有当前表示。

(1)login.html

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
    <title>Title</title>
</head>
<body>

    <form action="/login" method = "post">
        <p>Enter Name:</p>
        <input type="text" name="name"/>
        <p>Enter Password:</p>
        <input type="password" name="passwd"/>
        <p><input type="submit" value="登录"/></p>
    </form>

</body>
</html>

(2)app.py 【写法1】

from flask import Flask, views, redirect, url_for, request, render_template

app = Flask(__name__)


@app.route('/login', methods=['GET', 'POST'])
def login():
    if request.method == 'POST':  # 请求方式为POST
        # 拿到表单提交过来的用户数据:
        name = request.form['name']
        passwd = request.form['passwd']

        if name=='nacy' and passwd=='123':
            return '恭喜,登录成功!'
        else:
            return '不好意思,登录失败!'
    else:      # 默认请求方式为GET
        return render_template('login.html')

    

if __name__ == '__main__':
    app.debug = True
    app.run()


# app.add_url_rule(rule=访问的url,endpoint=路由别名,view_func=视图名称,methods=[允许访问的方法])

    # app.run(host='0.0.0.0', port=8000, debug=True)

(3)app.py【写法2】

from flask import Flask, views, redirect, url_for, request, render_template

app = Flask(__name__)


@app.route('/login', methods=['GET', 'POST'])
def login():
    if request.method == 'POST':  # 请求方式为POST
        # 拿到表单提交过来的用户数据:
        return do_the_login()
    else:      # 默认请求方式为GET
        return show_the_login_form()


def do_the_login():
    name = request.form['name']
    passwd = request.form['passwd']

    if name == 'nacy' and passwd == '123':
        return '恭喜,登录成功!'
    else:
        return '不好意思,登录失败!'


def show_the_login_form():
    return render_template('login.html')


if __name__ == '__main__':
    app.debug = True
    app.run()


# app.add_url_rule(rule=访问的url,endpoint=路由别名,view_func=视图名称,methods=[允许访问的方法])

    # app.run(host='0.0.0.0', port=8000, debug=True)
7.模板-渲染模板

(1)index.html

Title

Welcome to Flask

(2)user.html

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
    <title>Title</title>
</head>
<body>
    <h1>Hello, {{ name }}!</h1>
</body>
</html>

(3)hello.html

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
    <title>Title</title>
</head>
<body>
    <h2>我是模板</h2>
    {{ my_int }}
    <br>
    {{ my_str }}
    <br>
    {{ my_array }}
    <br>
    {{ my_dict }}
    <hr>
    <h2>模板的list数据获取</h2>
    <hr>
    {{ my_array[0] }}
    <br>
    {{ my_array.1 }}
    <hr>
    <h2>字典数据获取</h2>
    <hr>
    {{ my_dict['name'] }}
    <br>
    {{ my_dict.age }}
    <hr>
    <h2>算术运算</h2>
    <br>
    {{ my_array.0 + 10 }}
    <br>
    {{ my_array[0] + my_array.1 }}
</body>
</html>

(4)student

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
    <title>Title</title>
</head>
<body>
    <form action="http://localhost:5000/result" method="POST">
     <p>Name <input type = "text" name = "Name" /></p>
     <p>Physics <input type = "text" name = "Physics" /></p>
     <p>Chemistry <input type = "text" name = "Chemistry" /></p>
     <p>Maths <input type ="text" name = "Mathematics" /></p>
     <p><input type = "submit" value = "submit" /></p>
    </form>
</body>
</html>

(5)result

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
    <title>Title</title>
</head>
<body>
    <table border = 1>
    {% for key, value in result.items() %}
    <tr>
       <th> {{ key }} </th>
       <td> {{ value }}</td>
    </tr>
    {% endfor %}
    </table>
</body>
</html>

(6)app.py

from flask import Flask, views, redirect, url_for, request, render_template

app = Flask(__name__)


# @app.route('/')
# def index():
#     # 渲染模板
#     return render_template('index.html')


@app.route('/user/<username>')  # 将参数传递到html页面
def show_user_profile(username):
    # 显示该用户名的用户信息
    return render_template('user.html', name=username) # 渲染模板


@app.route('/hello')
def hello():
    # 往模板中传入的数据
    my_str = 'Hello Word'
    my_int = 10
    my_array = [3, 4, 2, 1, 7, 9]
    my_dict = {
        'name': '李华',
        'age': 18
    }
    return render_template('hello.html',
                           my_str=my_str,
                           my_int=my_int,
                           my_array=my_array,
                           my_dict=my_dict)


@app.route('/student')
def student_info():
    return render_template('student.html')


@app.route('/result', methods=['GET', 'POST'])
def student_result():

    # 客户端提交给服务器的request请求,都被放在服务器的request中,使用的时候,需要从request中获取数据
    if request.method == 'POST':

        # 第一种方式:将数据从request.form表单中取出
        # name = request.form['Name']
        # physics = request.form['Physics']
        # chemistry = request.form['Chemistry']
        # mathematics = request.form['Mathematics']
        # result = {'Name':name,'Physics':physics,'Chemistry':chemistry,'Mathematics':mathematics}

        # print(request.form)
        # return render_template('result.html', result=result)

        # 第二种方式:form表单本身就是一个字典,所以可以直接传递
        return render_template('result.html', result=request.form)


if __name__ == '__main__':
    app.debug = True
    app.run()

注意:methods=[‘GET’, ‘POST’] 两种方式

运行:

http://127.0.0.1:5000
http://127.0.0.1:5000/user/chen
http://127.0.0.1:5000/hello
http://127.0.0.1:5000/student
8.Flask 消息闪现

(1)index.html

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
    <title>Title</title>
</head>
<body>
    {% with messages = get_flashed_messages() %}
         {% if messages %}
               {% for message in messages %}
                    <p>{{ message }}</p>
               {% endfor %}
         {% endif %}
    {% endwith %}
<h3>欢迎来到登录界面!</h3>
<a href = "{{ url_for('login') }}">login</a>
</body>
</html>

(2)login.html

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
    <title>Title</title>
</head>
<body>
    <form method = "post" action = "http://localhost:5000/login">
        <table>
            <tr>
                <td>Username</td>
                <td><input type = 'username' name = 'username'></td>
            </tr>
            <tr>
                <td>Password</td>
                <td><input type = 'password' name = 'password'></td>
            </tr>
            <tr>
                <td><input type = "submit" value = "Submit"></td>
            </tr>
        </table>
    </form>
    {% if error %}
        <p><strong>错误</strong>: {{ error }}</p>
    {% endif %}
</body>
</html>

(3)app.py

from flask import Flask, redirect, url_for, request, session, render_template, abort, flash

app = Flask(__name__)

# 如果app.secret_key未设置,则Flask将不允许你设置或访问会话字典。
app.secret_key = 'fsvgfsvfvfvfdbgdada'  # 随机,长度不限,唯一即可


@app.route('/')
def index():
    return render_template('index.html')


@app.route('/login', methods=['GET', 'POST'])
def login():
    error = None
    if request.method == 'POST':
        if request.form['username'] != 'admin' or request.form['password'] != 'admin':
            error = '您输入的用户名或密码错误,请重新输入!'
        else:
            flash('登录成功!')
            return redirect(url_for('index'))
    return render_template('login.html', error=error)


if __name__ == '__main__':
    app.debug = True
    app.run()

运行:

http://127.0.0.1:5000
http://127.0.0.1:5000/login
9.Flask重定向(redirect)和错误

(1)login.html

Title

(2)app.py

from flask import Flask, redirect, url_for, request, session, render_template, abort

app = Flask(__name__)


@app.route('/')
def index():
    return render_template('login.html')


@app.route('/login',methods = ['POST', 'GET'])
def login():
    if request.method == 'POST' :
        if request.form['username'] == 'admin' :
            return redirect(url_for('success'))
        else:
            abort(401)
    else:
        return redirect(url_for('index'))

    
@app.route('/success')
def success():
    return 'logged in successfully'


if __name__ == '__main__':
    app.debug = True
    app.run()

    
'''
Flask类具有带有错误代码的abort()函数:  Flask.abort(code)
code参数采用以下值之一:
    400 - 用于错误请求
    401 - 用于未身份验证的
    403 - Forbidden
    404 - 未找到
    406 - 表示不接受
    415 - 用于不支持的媒体类型
    429 - 请求过多
'''

10.模板中显示使用过滤器的变量

(1)常用过滤器

名称说明
safe渲染值时禁用字符转义,很适合显示变量中存储的HTML代码
capitalize字符串第一个字母大写,其他都小写
lower把值转换成小写形式
upper把值转换成大写形式
title字符串内若有多个单词,所有单词的首字母大写
trim把值的首尾空格去掉
striptags渲染之前把值中所有的 HTML 标签都删掉

(2)test_filter.html

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
    <meta charset="UTF-8">
    <title>Jinja2 Filter</title>
</head>
<body>
    <p style="color: blue"> {{ 'Hello Jinja2 !' | reverse }} </p>
    <br/><p style="color: pink"> {{ data.keys() | upper }} </p>
    <br/><p style="color: aqua"> {{ data.values() | lower}}</p>
    {% for key in data.keys() %}
        <div>
            <p style="color: rebeccapurple"> {{ '%s : %s' | format(key, data[key]) }} </p>
        </div>
    {% endfor %}

    {{ SomePath['SomePath'] | safe | truncate(200, True)}}

    <br/><p style="color: blue"> {{ data.keys() | first | upper }} </p>
    {% filter upper %}
        python 碎片<br/>
        {{ data }}
    {% endfilter %}
</body>
</html>

(3)test_filter2.html

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
    <title>Title</title>
</head>
<body>
    {% set name='nacy.Shan' %}

    {# 输出大写 #}
    <h1>hello, {{ name|upper }}!</h1>

    {# 输出大写,超过3个字符打断,用'...'替代 #}
    <h1>hello, {{ name|upper|truncate(3,True) }} !</h1>

    {# 当变量未定义时,显示默认字符串,可以缩写为d #}
    {{ name | default('No name', true) }} <br />
    {{ new_name | d('No new_name ', true) }} <br />

    {# 单词首字母大写 #}
    {{ 'hello' | capitalize }} <br />

    {# 单词全小写 #}
    {{ 'XML' | lower }} <br />

    {# 去除字符串前后的空白字符 #}
    {{ '  hello  ' | trim }} <br />

    {# 字符串反转,返回"olleh" #}
    {{ 'hello' | reverse }} <br />

    {# 格式化输出,返回"Number is 2" #}
    {{ '%s is %d' | format("Number", 2) }} <br />

    {# 关闭HTML自动转义 #}
    {{ '<em>name</em>' | safe }} <br />

    {# 四舍五入取整,返回13.0 #}
    {{ 12.8888 | round }} <br />

    {# 向下截取到小数点后2位,返回12.88 #}
    {{ 12.8888 | round(2, 'floor') }} <br />

    {# 绝对值,返回12 #}
    {{ -12 | abs }} <br />

    {# 取第一个元素 #}
    {{ [1,2,3,4,5] | first }} <br />

    {# 取最后一个元素 #}
    {{ [1,2,3,4,5] | last }} <br />

    {# 返回列表长度,可以写为count #}
    {{ [1,2,3,4,5] | length }} <br />

    {# 列表求和 #}
    {{ [1,2,3,4,5] | sum }} <br />

    {# 列表排序,默认为升序 #}
    {{ [3,2,1,5,4] | sort }} <br />

    {# 合并为字符串,返回"1 | 2 | 3 | 4 | 5" #}
    {{ [1,2,3,4,5] | join(' | ') }} <br />

    {# 列表中所有元素都全大写。这里可以用upper,lower,但capitalize无效 #}
    {{ ['tom','bob','ada'] | upper }} <br />

    {# 字典操作 #}
{#    {% set users=[{'name':'Tom','gender':'M','age':20},#}
{#                  {'name':'John','gender':'M','age':18},#}
{#                  {'name':'Mary','gender':'F','age':24},#}
{#                  {'name':'Bob','gender':'M','age':31},#}
{#                  {'name':'Lisa','gender':'F','age':19}]#}
{#    %}#}

    {# 按指定字段排序,这里设reverse为true使其按降序排 #}
    <ul>
    {% for user in users | sort(attribute='age', reverse=true) %}
        <li>{{ user.name }}, {{ user.age }}</li>
    {% endfor %}
    </ul>

    {# 列表分组,每组是一个子列表,组名就是分组项的值 #}
    <ul>
    {% for group in users|groupby('gender') %}
    <li>{{ group.grouper }}
    <ul>
        {% for user in group.list %}
    <li>{{ user.name }}</li>
        {% endfor %}</ul>
    </li>
    {% endfor %}
    </ul>

    {# 取字典中的某一项组成列表,再将其连接起来 #}
    {{ users | map(attribute='name') | join(', ') }}
</body>
</html>

(4)other.py

class User(object):
    def __init__(self, name, age, gender='male'):
        self.name = name
        self.age = age
        self.gender = gender

    def __str__(self):
        return 'name: ' + self.name + ', age: ' + self.age + ', gender:' + self.gender

(5)app.py

from flask import Flask, views, redirect, url_for, request, render_template

from other import User

app = Flask(__name__)


@app.route('/test_filter')
def test_flask_filter():
    data = {
        'Python': '编程语言',
        'Flask': 'Web 框架',
        'Jinja2': '模板引擎',
        'HTML': '前端语言'
    }
    SomePath = {'SomePath': '<h1 style="color:red">SomePath</h1>'}
    return render_template('test_filter.html', data=data, SomePath=SomePath)


@app.route('/test_filter2')
def test_flask_filter2():
    user1 = User('nacy', 18, 'female')
    print(type(user1))
    print(user1.name)
    print(user1.age)
    print(user1.gender)
    user2 = User('bill', 28, 'male')
    user3 = User('jack', 20, 'male')
    user4 = User('lily', 25, 'female')
    users = [user1, user2, user3, user4]

    return render_template('test_filter2.html', users=users)


if __name__ == '__main__':
    app.debug = True
    app.run()


# app.add_url_rule(rule=访问的url,endpoint=路由别名,view_func=视图名称,methods=[允许访问的方法])

    # app.run(host='0.0.0.0', port=8000, debug=True)

运行:

http://127.0.0.1:5000/test_filter
http://127.0.0.1:5000/test_filter2
11.模板碎片化灵活处理

(1)base.html

<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN"
        "http://www.w3.org/TR/html4/loose.dtd">
<html>
<head>
    {% block head %}
        <title>
            {% block title %}{% endblock %} - My Application
        </title>
    {% endblock %}
</head>
<body>
    {% block body %}
    {% endblock %}
</body>
</html>

(2)index.html

{% extends 'base.html' %}

{% block title %}Index{% endblock %}
{% block head %}
    {{ super() }}
    <style>
        body{
            background-color: aqua;
        }
    </style>
{% endblock %}

{% block body %}
    <h1>Hello, World!</h1>
{% endblock %}

(3)app.py

from flask import Flask, views, redirect, url_for, request, render_template

app = Flask(__name__)


@app.route('/')
def index():
    return render_template('index.html')


if __name__ == '__main__':
    app.debug = True
    app.run()

运行:

http://127.0.0.1:5000/
12.Flask Cookies

(1)关于Cookies

​ Cookie以文本文件的形式存储在客户端的计算机上。其目的是记住和跟踪与客户使用相关的数据,以获得更好的访问者体验和网站统计信息。Request对象包含Cookie的属性。它是所有cookie变量及其对应值的字典对象,客户端已传输。除此之外,cookie还存储其网站的到期时间,路径和域名。
​ 在Flask中,对cookie的处理步骤为:

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-eoSRdHQp-1658367070106)(C:\Users\s7980\AppData\Roaming\Typora\typora-user-images\image-20220710235535026.png)]

(2)index.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>cookies——index</title>
</head>
<body>
    {% if set_ok  %}
        {# 之前没有cookie,初次访问此页面,我向浏览器写入了cookie #}
        恭喜,设置cookie成功!
    {% else %}
        {# 取cookies的值并显示出来吧 #}
        {% for key,value in cookies.items() %}
            {{ key }} : {{ value }} <br />
        {% else %}
            还没有可取的cookie
        {% endfor %}
    {% endif %}
</body>
</html>

(3)app.py

from flask import Flask, request, make_response, render_template

app = Flask(__name__)


# 4.1-2 flask  Cookie和Session
@app.route('/')
def hello_world():
    # return 'hello flask'
    return '你好,欢迎学习flask'


@app.route('/set_cookie')
def set_cookies():
    resp = make_response(render_template('index.html', set_ok=True))  # 设置响应体
    resp.set_cookie('暨大', '学生', max_age=3600)
    resp.set_cookie('靓仔', '张三', max_age=3600)
    resp.set_cookie('靓女', '慕容', max_age=3600)

    return resp


@app.route('/get_cookie')
def get_cookie():
    # 从 request中 获取cookies信息
    cookies = request.cookies
    return render_template('index.html', cookies=cookies)


@app.route('/del_cookie/<cookiename>')
def del_cookie(cookiename):
    # 设置响应体
    resp = make_response(f'删除cookie:"{cookiename}"成功')
    resp.delete_cookie(cookiename)
    cookie = request.cookies
    print(cookie)

    return resp


if __name__ == '__main__':
    # app.config['DEBUG'] = True
    app.debug = True
    app.run()

运行:

http://127.0.0.1:5000/set_cookie
http://127.0.0.1:5000/get_cookie
http://127.0.0.1:5000/del_cookie/%E5%BC%A0%E4%B8%89
13.Flask Sessions

(1)关于Sessions

​ 与Cookie不同,Session(会话)数据存储在服务器上。会话是客户端登录到服务器并注销服务器的时间间隔。需要在该会话中保存的数据会存储在服务器上的临时目录中。
​ 为每个客户端的会话分配会话ID。会话数据存储在cookie的顶部,服务器以加密方式对其进行签名。对于此加密,Flask应用程序需要一个定义的SECRET_KEY。
​ Session对象也是一个字典对象,包含会话变量和关联值的键值对。

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-Q1QpeLyS-1658367070109)(C:\Users\s7980\AppData\Roaming\Typora\typora-user-images\image-20220711000229333.png)]

(2)app.py

from flask import Flask, request, session, redirect, url_for

app = Flask(__name__)
app.secret_key = 'sabdjanjdsajkbdja27234737237'  # 设置随机的秘钥,长度随意

# 4.3 Session


@app.route('/')
def index():
    if 'name' in session:
        name = session['name']
        return '登录用户名是:' + name + '<br>' + \
               "<b><a href = '/logout'>点击这里注销</a></b>"

    # return '<h1 style="color : red">你好,欢迎学习flask</h1>'
    return "您暂未登录, <br>" \
           "<a href = '/login'></b>" + "点击这里登录</b></a>"


@app.route('/login', methods=['GET', 'POST'])
def login():
    if request.method == 'POST':
        session['name'] = request.form['username']
        return redirect(url_for('index'))

    '''
    return '<form action="/login" method="post">' \
                '<a>用户名:<input name="username" type="text"></a><br>' \
                '<a>密码:<input name="password" type="text"></a><br>' \
                '<a><input name="login" type="submit" value="登录"></a>' \
            '</form>'
    '''

    return '''<form action = "" method = "post">
                <p><input type="text" name="username"/></p>
                <p><input type="submit" value="登录"/></p>
            </form>'''


@app.route('/logout')
def logout():
    session.pop('name',None)
    return redirect(url_for('index'))


if __name__ == '__main__':
    # app.config['DEBUG'] = True
    app.debug = True
    app.run()
附录.登录注册功能尝试

1.深入理解 get 模式

(1)http_get_test.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Get</title>
</head>
<body>
    <a>username:{{name}}</a><br>
    <a>password:{{pwd}}</a>
</body>
</html>

(2)【第一种】app.py

from flask import Flask, request, url_for

app = Flask(__name__)


@app.route('/get')
def get():
    print(request)
    username = request.args.get('user')
    password = request.args.get('pwd')

    return f'url获取到的信息是:{username, password}'


if __name__ == '__main__':
    app.debug = True
    app.run()

(3)【第二种】app.py

from flask import Flask, request, render_template, redirect, url_for

app = Flask(__name__)


# 3.3 HTTP get方法和post方法

@app.route('/')
def index():
    return 'hello flask'


# 3.3.1 url 获取参数/url传参的方式
# 第1种
@app.route('/get_test/<args>')
def getargs(args):
    print(args)
    return f'获取到的args是:{args}'


# 第2种
@app.route('/get_test')
def get():
    print(request)
    username = request.args.get('user')
    password = request.args.get('pwd')

    # return f'url获取到的信息是:{username, password}'
    return render_template('http_get_test.html', name=username, pwd=password)



if __name__ == '__main__':
    app.debug = True
    app.run()

运行:

http://127.0.0.1:5000/
http://127.0.0.1:5000/get_test?user=admin&pwd=111
http://127.0.0.1:5000/register_test

2.深入理解post模式

(1) http_register_test.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>POST</title>
</head>
<body>
    <form action="/register_test" method="post">
      <a>用户名:<input name="username" type="text"></a><br>
      <a>密码:<input name="password" type="text"></a><br>
      <a><input name="add" type="submit" value="注册"></a>
    </form>
</body>
</html>

(2)http_register_success.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>注册成功</title>
</head>
<body>
    <form method="post">
        <a>注册成功!</a><br>
        <a>用户名:<input name="username" type="text"></a><br>
        <a>密码:<input name="password" type="text"></a><br>
        <a><input name="login" type="submit" value="登录"></a>
    </form>
</body>
</html>

(3)app.py

from flask import Flask, request, render_template, redirect, url_for

app = Flask(__name__)


# USER = [{'username': '张三', 'password': '123'}]
# USER = [{'username': '张三', 'password': '123'},
#         {'username': '李四', 'password': '1234'},
#         {'username': '王五', 'password': '12345'}]
USER = []


# 3.3.2 POST方法
# 3.3.2.1 模拟注册功能
@app.route('/register_test', methods=['GET', 'POST'])
def post():
    if request.method == 'POST':
        user = request.form.get('username')
        pwd = request.form['password']
        print(user, pwd)

        USER.append({'username': user, 'password': pwd})
        print(USER)
        # return f'用户:{user}, 密码:{pwd}'

        return render_template('http_register_success.html', username=user, password=pwd)
    else:
        return render_template('http_register_test.html')

    
if __name__ == '__main__':
    app.debug = True
    app.run()

运行:

http://127.0.0.1:5000/register_test

3.综合运用

(1)http_get_test.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Get</title>
</head>
<body>
    <a>username:{{name}}</a><br>
    <a>password:{{pwd}}</a>
</body>
</html>

(2)http_login_success_test.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>登录成功</title>
</head>
<body>
    <p>login success</p>
    <p>恭喜登录成功</p>
    <a>用户名:{{username}}</a><br>
    <a>密码:{{password}}</a>
</body>
</html>

(3)http_login_test.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>登录</title>
</head>
<body>
    <form action="/login" method="post">
          <a>用户名:<input name="username" type="text"></a><br>
          <a>密码:<input name="password" type="text"></a><br>
          <a><input name="login" type="submit" value="登录"></a>
    </form>
</body>
</html>

(4)http_register_success.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>注册成功</title>
</head>
<body>
    <p>register success</p>
    <p>注册成功</p>
    <a>用户名:{{username}}</a><br>
    <a>密码:{{password}}</a>
</body>
</html>

(5)http_register_test.html

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>注册</title>
</head>
<body>
    <form action="/register_test" method="post">
        <a>用户名:<input name="username" type="text"></a><br>
        <a>密码:<input name="password" type="text"></a><br>
        <a><input name="login" type="submit" value="注册"></a>
    </form>
</body>
</html>

(6)app.py

from flask import Flask, request, render_template, redirect, url_for

app = Flask(__name__)


# 3.3 HTTP get方法和post方法

@app.route('/')
def index():
    return 'hello flask'


# 3.3.1 url 获取参数/url传参的方式
# 第1种
@app.route('/get_test/<args>')
def getargs(args):
    print(args)
    return f'获取到的args是:{args}'


# 第2种
@app.route('/get_test')
def get():
    print(request)
    username = request.args.get('user')
    password = request.args.get('pwd')

    # return f'url获取到的信息是:{username, password}'
    return render_template('http_get_test.html', name=username, pwd=password)


# USER = [{'username': '张三', 'password': '123'}]
# USER = [{'username': '张三', 'password': '123'},
#         {'username': '李四', 'password': '1234'},
#         {'username': '王五', 'password': '12345'}]
USER = []


# 3.3.2 POST方法
# 3.3.2.1 模拟注册功能
@app.route('/register_test', methods=['GET', 'POST'])
def post():
    if request.method == 'POST':
        user = request.form.get('username')
        pwd = request.form['password']
        print(user, pwd)

        USER.append({'username': user, 'password': pwd})
        print(USER)
        # return f'用户:{user}, 密码:{pwd}'

        return render_template('http_register_success.html', username=user, password=pwd)
    else:
        return render_template('http_register_test.html')


# 3.3.2.2 模拟登录功能
@app.route('/login', methods=['GET', 'POST'])
def login():
    if request.method == 'POST':
        # 从form 表单中获取提交的登录数据, 两种方法都可以
        user = request.form.get('username')
        pwd = request.form['password']

        '''
        判断用户登录是否成功
        if user != '张三' or pwd != '123':
            return '用户名或密码错误,请重新输入!'
        else:
            return '登录成功'
        '''
        print(USER)
        if {'username': user, 'password': pwd} not in USER:
            return '用户名或密码错误,请重新输入!'
        else:
            return render_template('http_login_success_test.html', username=user, password=pwd)
        # 使用的是假数据,所以这里要先判断USER是否为空
    else:
        return render_template('http_login_test.html')


if __name__ == '__main__':
    app.debug = True
    app.run()

运行:

http://127.0.0.1:5000/
http://127.0.0.1:5000/get_test?user=admin&pwd=111
http://127.0.0.1:5000/register_test
http://127.0.0.1:5000/login
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 1
    评论
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值