一.Flask - CBV

from flask import Flask, render_template, url_for, views

app = Flask(__name__)

class Login(views.MethodView):
def get(self, *args, **kwargs):
print(url_for('my_login')) # 通过my_login进行反向解析
return render_template('login.html')
def post(self, *args, **kwargs):
return 'login success' app.add_url_rule('/login', view_func=Login.as_view('my_login')) if __name__ == '__main__':
app.run(debug=True)

注意: 视图类中定义了哪些方法, 就可以允许哪种方式的请求, 也可以通过指定参数methods=["GET","POST"], 指定参数时可以在视图类中指定, 也可以在add_url_rule方法中指定.

二.Flask - Session

我们使用过flask内置的session,知道它是把session存放在浏览器,即客户端。今天要学习的flask-session是flask的第三方组件,看一下它和flask内置的session有什么不同以及它的使用方法。

flask-session是flask框架的session组件,flask内置session使用签名cookie保存,而该组件则将支持session保存到多个地方,如:

- redis
- memcached
- filesystem
- mongodb
- sqlalchmey

1.安装flask-session

pip3 install flask-session

2.回顾flask自带的session的使用方法

from flask import Flask, session

app = Flask(__name__)

app.secret_key = '~!@#$%'  # 配置session反向解析的秘钥

@app.route('/index')
def index():
session['user'] = 'value'
return 'hello' if __name__ == '__main__':
app.run(debug=True)

启动该程序, 使用浏览器访问http://127.0.0.1:5000, 可看到如下session:

3.flask-session的使用(以保存到redis为例)

from flask import Flask, session
from flask_session import Session # 导入flask-session中的Session类
from redis import Redis app = Flask(__name__)
# 对实例进行配置
app.config['SESSION_TYPE'] = 'redis'
app.config['SESSION_REDIS'] = Redis(host='127.0.0.1', port=6379, db=6) Session(app) # 把原来app中的session进行替换 @app.route('/index')
def index():
session['user'] = 'value'
return 'hello' if __name__ == '__main__':
app.run(debug=True)

启动程序, 浏览器访问http://127.0.0.1:5000, 找到浏览器Cookie中的键值对:

使用cmd控制台打开redis客户端, 进行如下操作:

三.WTForms组件

WTForms是flask的组件, 类似于django的modelform组件.

1.安装

pip3 install wtforms

2.使用(以登录注册为例)

wtf.py文件:

from flask import Flask, render_template, request
from wtforms.fields import simple, core
from wtforms import Form, validators app = Flask(__name__, template_folder="./app01/templates") # Form组件: 注册类
class RegForm(Form):
username = simple.StringField(
label='用户名',
validators=[
validators.DataRequired(message='该字段不能为空'),
validators.Length(min=3, max=10, message='用户名必须3-10个字符')
],
id='user_id',
render_kw={'class': 'user_name'}
)
password = simple.PasswordField(
label='密码',
validators=[
validators.DataRequired(message='该字段不能为空'),
validators.Length(min=6, max=12, message='密码必须6-12个字符')
],
id='pwd',
render_kw={'class': 'pwd'}
)
repassword = simple.PasswordField(
label='确认密码',
validators=[
validators.EqualTo(fieldname='password', message='两次密码不一致'),
],
id='re_pwd',
render_kw={'class': 're_pwd'}
)
email = simple.StringField(
label='邮箱',
validators=[
validators.DataRequired(message='该字段不能为空'),
validators.Email(message='必须符合邮箱格式')
],
id='email',
render_kw={'class': 'email'}
)
gender = core.RadioField(
label='性别',
coerce=int, # 提交的数据类型,即1或2的数据类型(如下所示)
choices=(
(1, '女'), # 元组第一个元素是value, 第二个元素是显示的值
(2, '男')
),
default=1 # 默认值为1
)
hobby = core.SelectMultipleField(
label='爱好',
validators=[
validators.Length(min=1, max=3, message='爱好的数量为1-3个'),
],
coerce=str, # 注意,类型为str时,下面choices中每个元组第一个值必须带引号
choices=(
('1', '健身'),
('2', '游泳'),
('3', '旅游'),
('4', '摄影'),
),
default=('1', '3') # 默认选中两个
)
# button = simple.SubmitField # 渲染提交按钮 # Form组件: 登录类
class LoginForm(Form):
username = simple.StringField(
label='用户名',
validators=[ # 校验条件,可迭代条件,因为可能校验多个条件
validators.DataRequired(message='该字段不能为空'),
validators.Length(min=3, max=10, message='用户名必须3-10个字符')
],
description='this is a description', # 描述标记
id='user_id', # 标签id
widget=None, # 默认组件(比如input type='text')在StringField中已经被实例化了
render_kw={'class': 'my_login'} # 添加属性和值
)
password = simple.PasswordField(
label='密码',
validators=[
validators.DataRequired(message='该字段不能为空'),
validators.Length(min=6, max=12, message='密码必须6-12个字符')
],
description='this is a description',
id='pwd',
default=None,
render_kw={'class': 'pwd'}
) # 视图函数: 注册
@app.route('/reg', methods=['GET', 'POST'])
def reg():
if request.method == 'GET':
rf = RegForm() # 实例化Form组件
return render_template('register.html', wtf=rf)
else:
rf = RegForm(request.form)
if rf.validate(): # 校验成功
return rf.data.get('username')
else: # 校验失败
print(rf.data)
print(rf.errors)
return render_template('register.html', wtf=rf) # 视图函数: 登录
@app.route('/login', methods=['GET', 'POST'])
def login():
if request.method == 'GET':
lf = LoginForm() # 实例化Form组件
return render_template('login.html', wtf=lf)
else:
lf = LoginForm(request.form) # 将用户提交的数据传入组件中
if lf.validate(): # 校验用户提交的数据
return lf.data.get('username') # 正确的数据在lf.data中
else: # 校验失败,错误的数据在lf.errors中
return render_template('login.html', wtf=lf) if __name__ == '__main__':
app.run(debug=True)

register.html文件:

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>注册</title>
</head>
<body>
<form action="" method="post" novalidate>
{% for field in wtf %}
<p>
{{ field.label }}
{{ field }}
{{ field.errors.0 }}
</p>
{% endfor %}
<input type="submit" value="注册">
</form>
</body>
</html>

login.html文件:

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>登录</title>
</head>
<body>
<form action="" method="post" novalidate>
<p>
{{ wtf.username.label }}
{{ wtf.username }}{{ wtf.username.errors.0 }}
</p>
<p>
{{ wtf.password.label }}
{{ wtf.password }}{{ wtf.password.errors.0 }}
</p>
<input type="submit" value="登录">
</form>
</body>
</html>

flask(3.0)的更多相关文章

  1. Airflow安装异常:ERROR: flask-appbuilder 1.12.3 has requirement Flask<2,>=0.12, but you'll have flask 0.11.1 which is incompatible.

    1 详细异常: ERROR: flask-appbuilder 1.12.3 has requirement Flask<2,>=0.12, but you'll have flask 0 ...

  2. [Python] Flask从0到1开发轻量级网页

    概述 Flask采用MVT模型,即Model, Template, View Model:定义数据的存储格式,并且提供了数据库访问的API View:定义那些数据被显示,是业务逻辑处理模块 Templ ...

  3. [py]flask从0到1-模板/增删改查

    flask知识点 1.后端渲染html到前端 render_template 2.后端获取前端数据 request.args.get 3.前端获取后端数据 模板 4.警示消息 flash {{ get ...

  4. flask(2.0)

    目录 一. Flask基础(一) 1.Flask启动 2.路由 3.Response 4.Request 5.Jinja2 6.session 二.Flask基础(二) 1.路由配置 (1)metho ...

  5. flask(1.0)

    目录 一. 关于KeyError和IndexError 二. Python三大主流框架对比 三. flask基础 1.安装flask 2.用flask写出的第一个页面 3.Flask的Response ...

  6. Flask:操作SQLite3(0.1)

    Windows 10家庭中文版,Python 3.6.4,Flask 1.0.2 本文介绍了第一次在Flask框架中操作SQLite3数据库的测试,参考了官网的文档Using SQLite 3 wit ...

  7. Flask:cookie 和 session (0.1)

    Windows 10家庭中文版,Python 3.6.4,Flask 1.0.2 Cookie是什么?有什么用? 某些网站为了辨别用户身份.进行 session 跟踪而储存在用户本地终端上的数据(通常 ...

  8. Flask:静态文件&模板(0.1)

    Windows 10家庭中文版,Python 3.6.4,Flask 1.0.2 前面看了Flask的Quickstart文档,可是,一直没有练习里面的内容,这不,刚刚练习完毕,来写篇博文记录一下! ...

  9. Flask 发布 1.0 稳定版

    简评:现在都开始版本大跃进了吗?对,别看别人,说的就是你 pipenv(名单太长,待补齐...) Flask 其实早就已经十分稳定了,而在第一个 commit 大概 8 年之后,版本号才最终反映出了这 ...

随机推荐

  1. hdfs冷热数据分层存储

    hdfs如何让某些数据查询快,某些数据查询慢? hdfs冷热数据分层存储 本质: 不同路径制定不同的存储策略. hdfs存储策略 hdfs的存储策略 依赖于底层的存储介质. hdfs支持的存储介质: ...

  2. ubuntu NGINX uwsgi https 部署Django 遇到的问题

    搞了3天终于把Django成功部署到Ubuntu,记录一下: 引用来自泡泡茶壶: Ubuntu下的Nginx + Uwsgi + Django项目部署详细流程 前提说明: Django作为小程序的后端 ...

  3. 使用PHP读取PHP文件并输出到屏幕上

    看完这篇文章,你一定忘不掉htmlentities的用法 背景 今天有个需求,就是一个PHP开发的网址中,有一个页面可以提供给用户修改已经存在的PHP文件中的代码,并POST到服务器上保存. 每次将读 ...

  4. 【leetcode】1296. Divide Array in Sets of K Consecutive Numbers

    题目如下: Given an array of integers nums and a positive integer k, find whether it's possible to divide ...

  5. 图论小专题C

    3 负环及其应用 3.1 判定算法 判断负环只能用"边松弛"算法,也就是Bellman-Ford和SPFA算法.这两个算法都是\(O(NM)\)级别的.因为负环中一定存在一条负边, ...

  6. 路由配置系统(URLconf)

    URL配置(URLconf)就像Django所支撑网站的目录. 它的本质是URL与要为该URL调用的视图函数之间的映射表.你就是以这种方式告诉Django,对于URL(1)调用代码(1), 对于URL ...

  7. MyBatis动态Sql 的使用

    Mapper.xml提示: 1:mapper包中新建一个文件:mybatis-3-mapper.dtd 2:在web app libraries/mybatis.jar/org.apache.ibat ...

  8. Lombok Pojo默认初始值问题

    Lombok以注解形式来简化java代码,提高开发效率.比如我们常用的@Builder.@Data.@AllArgsConstructor.@NoArgsConstructor.@ToString等. ...

  9. 2018-2019-2 20165330《网络对抗技术》Exp8 Web基础

    目录 基础问题 相关知识 实验内容 实验步骤 实验总结与体会 实验内容 Web前端HTML 能正常安装.启停Apache.理解HTML,理解表单,理解GET与POST方法,编写一个含有表单的HTML ...

  10. Java学习回顾总结

    java-01初识Java见上一篇 Java-02 1.命名规范与规范: 标识符命名规则:首字母为字母|下划线|$ 其余部分数字|字母|下划线|$ 命名规范: 变量属性方法命名规范:第一个单词首字母小 ...