处理表单数据

表单数据的处理涉及很多内容,从获取数据到保存数据大致有以下步骤:

1、  解析请求,获取表单数据

2、  对数据进行必要的转换,比如讲勾选框的值转换成python的布尔值

3、  验证数据是否符合要求,同时验证CSRF令牌。

4、  如果验证未通过则需要生成错误消息,并在模板中显示错误消息。

5、  如果验证通过,就把数据保存到数据库或做进一步处理

使用Flask-WTF和WTForms可以极大地简化这些步骤

提交表单

在HTML中,当<form>标签声明的表单中类型为submit的提交字段被单击时,就会创建一个表单的HTTP请求,请求中包含表单各个字段的数据。表单的提交行为主要有三个属性控制,如下表:

form标签的action属性用来指定表单被提交的目标URL,默认为当前URL,就是渲染该模板的路由所在的URL。

当使用get方法提交表单时,表单的数据会以查询字符串的形式附加在请求的URL里,如:

127.0.0.1:5000:/basic?username=xiaxiaoxu&password=12345

GET方式仅适用于长度不超过3000个字符,且不包含敏感信息的表单。因为这种方式会直接将用户提交的表单数据暴露在URL中,容易被攻击者截获,实例中的情况是危险的。因此处处于安全的考虑,我们一般使用post方法提交表单。使用post方式时,按照默认的编码类型,表单数据会存储在请求主体中,比如:

POST /basic HTTP/1.0

Content-Type:application/x-www-form-urlencoded

Content-Length:30

username=xiaxiaoxu&12345

Flask为路由设置默认的监听方法是GET,为了支持接收表单提交发送的POST请求,我们需要在app.route()装饰器里使用methods关键字为路由指定HTTP方法,比如:

@app.route('/',methods=['GET','POST'])
def basic():
form=LoginForm()
return render_template('basic.html',form=form)

验证表单数据

客户端验证和服务器端验证

表单的验证通常分为以下几种形式

客户端验证

客户端验证是指在客户端(比如web浏览器)对用户的输入值进行验证。比如,使用HTML5内置的验证属性即可实现基本的客户端验证(type、required、min、max、accept等)。

例如,给username字段添加required标志:

<input type=”text” name=”username” required>

如果用户没有输入内容而按下提交按钮,会弹出浏览器内置的错误提示

和其他附件HTML属性相同,我们可以在定义表单时通过render_kw传入这些属性,或是在渲染表单时传入,像requiredd这类布尔值属性,值可以为空或是任意ASCII字符,如:

{{ form.username(required=’’) }}

除了使用HTML5提供的属性实现基本的客户端验证,我们通常会使用javaScript实现完善的验证机制,比如使用javaScript表单验证库-jQuery

客户端方式可以实时动态提示用户输入是否正确,只有用户输入正确后才会将表单数据发送到服务器,客户端验证可以增强用户体验,降低服务器负载。

服务器端验证

服务器端验证是指用户把输入的数据提交到服务器端,在服务器端对数据进行验证。如果验证出错就会在响应中加入错误信息。用户修改后再提交表单,知道通过验证。在flask中使用WTForms实现的就是服务器端验证

WTForms验证机制

WTForms验证表单字段的方式是在实例化表单类时传入表单数据,然后对表单实例调用validate()方法。这会逐个对字段调用字段实例化时定义的验证器,返回表示验证结果的布尔值。如果验证失败,就把错误消息存储到表单实例的errors属性对应的字典中,验证的过程如下所示:

>>> from app import app
>>> from flask import request
>>> app.test_request_context('/basic').push()#激活请求上下文
>>> from flask import current_app
>>> app.app_context().push()#激活程序上下文
>>> current_app.name
'app'
>>>#定义LoginForm类
>>> from wtforms import Form, StringField,PasswordField,BooleanField
>>> from wtforms.validators import DataRequired,length
>>> class LoginForm(Form):
... username = StringField('Username', validators=[DataRequired()])
... password = PasswordField('Password',validators=[DataRequired(),length(8,128)])
...
>>> form = LoginForm(username='',password='')
>>> form.data #表单数据字典
{'username': '', 'password': ''}
>>> form.validate()
False
>>> form.errors
{'username': [u'This field is required.'], 'password': [u'Field must be between 8 and 128 characters long.']}
>>> form2 = LoginForm(username='xiaxiaoxu', password='')
>>> form2.data #表单数据字典
{'username': 'xiaxiaoxu', 'password': ''}
>>> form2.validate()
False
>>> form2.errors #错误消息字典
{'password': [u'Field must be between 8 and 128 characters long.']}
>>> form3 = LoginForm(username='xiaxiaoxu', password='')
>>> form3.data
{'username': 'xiaxiaoxu', 'password': ''}
>>> form3.validate()
True
>>> form3.errors
{}

因为表单使用POST方法提交,如果单纯使用WTForms,在实例化表单时需要首先把request.form传入表单类(LoginForm(username='',password='123')),而使用Flask-WTF时,表单类继承的FlaskForm基类默认会从request.form获取表单数据,所以不需要手动传入。

使用POST方法提交的表单,其数据会被Flask解析成为一个字典,可以通过请求对象的form属性获取(request.form);使用GET方法提交的表单的数据同样会被解析为字典,不过要通过请求对象的args属性获取(request.args)。

flask 处理表单数据的更多相关文章

  1. 【flask】处理表单数据

     表单数据的处理涉及很多内容,除去表单提交不说,从获取数据到保存数据大致会经历以下步骤: 解析请求,获取表单数据. 对数据进行必要的转换,比如将勾选框的植转换为Python的布尔值. 验证数据是否符合 ...

  2. Flask--(一对多)模型渲染表单数据

    模型建立一一对多模型: 多表添加外键,建立两张表之间的关系 一表关联多表的属性,可以方便快速访问多表的数据 模板一层循环渲染一表数据,二层循环渲染多表的数据 代码展示: from flask impo ...

  3. Flask:web表单

    客户端发送的所有通过POST发出的请求信息都可以通过request.form获取.但是如果我们要生成表单的HTML代码和验证提交的表单数据那么就需要采用另外的方法.Flask-WTF扩展可以把处理we ...

  4. flask web 表单验证 WTForms

    简介 WTForms 是一个flask集成框架,或者说是库,用于处理浏览器表单提交的数据,它在flask-WTF的基础上扩展并添加了一些随手可得的精巧帮助函数,这些函数将会是在flask里使用表单更加 ...

  5. Servlet的5种方式实现表单提交(注册小功能),后台获取表单数据

    用servlet实现一个注册的小功能 ,后台获取数据. 注册页面: 注册页面代码 : <!DOCTYPE html> <html> <head> <meta ...

  6. easyui不提交window中的form表单数据

    <form id="ff" method="post">, <div id="win" class="easyu ...

  7. Struct2提交表单数据到Acion

    Struct2提交表单数据到Action,Action取表单的数据,传递变量.对象 HTML.jsp <form action="reg.do" method="p ...

  8. json化表单数据

    /** * josn化表单数据 * @name baidu.form.json * @function * @grammar baidu.form.json(form[, replacer]) * @ ...

  9. 使用jQuery实现跨域提交表单数据

    我们在WEB开发中有时会遇到这种情况,比如要从A网站收集用户信息,提交给B网站处理,这个时候就会涉及到跨域提交数据的问题.本文将给您介绍如何使用jQuery来实现异步跨域提交表单数据.   在jQue ...

随机推荐

  1. oracle的undo表空间

    undo表空间是Oracle特有的概念.undo表空间中会自动分配undo段,这些undo段用来保存事务中的DML语句的undo信息,也就是来保存数据在被修改之前的值.在rollback,实例恢复(回 ...

  2. spring mvc 资源映射配置

    在springmvc配置文件中添加 <mvc:resources location="/css/" mapping="/css/**"/> < ...

  3. 1-4-bootloader架构学习

    1-4-bootloader架构学习 1.一般情况下嵌入式 Linux 系统中的软件主要分为以下几部分: 1) 引导加载程序:其中包括内部 ROM 中的固化启动代码和 BootLoader 两部分. ...

  4. 【SQL】where 后不可以接聚合函数,都哪些是聚合函数?

    where 后不可以接聚合函数,比如函数:SUM(count),AVG(count),MIN(count),MAX(count)

  5. MongoDB limit 选取 skip跳过 sort排序 方法

    MongoDB  limit 选取 skip跳过 sort排序 在mysql里有order by  MongoDB用sort代替order by > db.user.find() { " ...

  6. ITouch在xcode下提示‘No such file or directory, at ‘/SourceCache/DVTi...'

    版权声明:本文为博主原创文章,转载或又一次发表请先与我联系. https://blog.csdn.net/jonahzheng/article/details/37692733       用一个台老 ...

  7. metasploit的安装

    //直接安装 apt-get update apt-get install metasploit-framework //连接和安装postgresql apt-get install postgre ...

  8. 【C++问题整理】

    一.static   1.作用:    静态变量/函数:在整个文件内可见,不会被其他文件所用:静态变量:会被自动初始化为0: 类中的静态变量:类的成员,类对象公用 类中的静态函数:只能访问静态变量 2 ...

  9. [django]django配合前端vue前后端联调,django服务端解决跨域(django-cors-headers)

    django内部csrf post提交数据解决 https://www.cnblogs.com/iiiiiher/articles/9164940.html 前端写了个页面,里面$.post发现403 ...

  10. gerrit上的commit msg中关联jira单号(含gerrit的安装)

    这个问题折腾了很久,前期后后大概一个月吧,终于搞定了,查了很多资料,有的不完整,有的完全就不能用,有的没说完整,所以一定要记录下来,我的心血啊. 由于公司在用的gerrit的是正式环境中的,大家都在使 ...