专栏首页python-爬虫Flask-wtforms类似django中的form组件

Flask-wtforms类似django中的form组件

一.安装

pip3 install wtforms

二.简单使用

1.创建flask对象

from flask import Flask, render_template, request, redirect
from wtforms import Form
from wtforms.fields import simple
from wtforms import validators
from wtforms import widgets

app = Flask(__name__, template_folder='templates')

app.debug = True

二.生成form组件

class LoginForm(Form):
    # 字段(内部包含正则表达式)
    name = simple.StringField(
        label='用户名',  #form表单的标签
        validators=[   #过滤的一些条件
            validators.DataRequired(message='用户名不能为空.'),
            validators.Length(min=6, max=18, message='用户名长度必须大于%(min)d且小于%(max)d')
        ],
        widget=widgets.TextInput(), # 页面上显示的插件
        render_kw={'class': 'form-control'}  #form表单页面中显示的类名

三.路由

@app.route('/login', methods=['GET', 'POST'])
def login():
    if request.method == 'GET':
        form = LoginForm() #生成form对象
        return render_template('login.html', form=form)  #form对象渲染
    else:
        form = LoginForm(formdata=request.form) 
        if form.validate():   #进行form校验
            print('用户提交数据通过格式验证,提交的值为:', form.data)
        else:
            print(form.errors)
        return render_template('login.html', form=form)

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

四.页面渲染

<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <title>Title</title>
</head>
<body>
<h1>登录</h1>
<form method="post">
    <p>{{form.name.label}} {{form.name}} {{form.name.errors[0] }}</p>

    <p>{{form.pwd.label}} {{form.pwd}} {{form.pwd.errors[0] }}</p>
    <input type="submit" value="提交">
</form>
</body>
</html>

三.相关属性

1.field字段

WTForms支持HTML字段:

字段类型

说明

StringField

文本字段, 相当于type类型为text的input标签

TextAreaField

多行文本字段

PasswordField

密码文本字段

HiddenField

隐藏文本字段

DateField

文本字段, 值为datetime.date格式

DateTimeField

文本字段, 值为datetime.datetime格式

IntegerField

文本字段, 值为整数

DecimalField

文本字段, 值为decimal.Decimal

FloatField

文本字段, 值为浮点数

BooleanField

复选框, 值为True 和 False

RadioField

一组单选框

SelectField

下拉列表

SelectMultipleField

下拉列表, 可选择多个值

FileField

文件上传字段

SubmitField

表单提交按钮

FormFiled

把表单作为字段嵌入另一个表单

FieldList

子组指定类型的字段

2.Validators验证器

WTForms可以支持很多表单的验证函数:

验证函数

说明

Email

验证是电子邮件地址

EqualTo

比较两个字段的值; 常用于要求输入两次密钥进行确认的情况

IPAddress

验证IPv4网络地址

Length

验证输入字符串的长度

NumberRange

验证输入的值在数字范围内

Optional

无输入值时跳过其它验证函数

DataRequired

确保字段中有数据

Regexp

使用正则表达式验证输入值

URL

验证url

AnyOf

确保输入值在可选值列表中

NoneOf

确保输入值不在可选列表中

3.字段参数

参数名

介绍

label

字段别名,在页面中可以通过字段.label展示

validators

验证规则列表

filters

过氯器列表,用于对提交数据进行过滤

description

描述信息,通常用于生成帮助信息

id

表示在form类定义时候字段的位置,通常你不需要定义它,默认会按照定义的先后顺序排序。

default

默认值

widget

html插件,通过该插件可以覆盖默认的插件,更多通过用户自定义

render_kw

自定义html属性

choices

复选类型的选项

4.局部钩子

#在form类中
def validate_字段名(self, field):
    	#self.data 获得全局字段的一个类似字典的格式
		#self.data['字段'],可以获得全局中任意字段
        #field.data 当前字段的值
        #无需返回值,如果有不满足的情况需要抛错
        #如两个密码,有两种情况
        # raise validators.ValidationError("密码不一致") # 继续后续验证
        #  raise validators.StopValidation("密码不一致")  # 不再继续后续验证

5.再不改变模型情况下修改值

#在form类中
    def __init__(self, *args, **kwargs):
        super(RegisterForm, self).__init__(*args, **kwargs)
        self.字段名.choices = ((1, '篮球'), (2, '足球'), (3, '羽毛球'))

四.写好的模板

from flask import Flask, render_template, request, redirect
from wtforms import Form
from wtforms.fields import core
from wtforms.fields import html5
from wtforms.fields import simple
from wtforms import validators
from wtforms import widgets

app = Flask(__name__, template_folder='templates')
app.debug = True



class RegisterForm(Form):
    name = simple.StringField(
        label='用户名',
        validators=[
            validators.DataRequired()
        ],
        widget=widgets.TextInput(),
        render_kw={'class': 'form-control'},
        default='cxw'
    )

    pwd = simple.PasswordField(
        label='密码',
        validators=[
            validators.DataRequired(message='密码不能为空.')
        ],
        widget=widgets.PasswordInput(),
        render_kw={'class': 'form-control'}
    )

    pwd_confirm = simple.PasswordField(
        label='重复密码',
        validators=[
            validators.DataRequired(message='重复密码不能为空.'),
            validators.EqualTo('pwd', message="两次密码输入不一致")
        ],
        widget=widgets.PasswordInput(),
        render_kw={'class': 'form-control'}
    )

    email = html5.EmailField(
        label='邮箱',
        validators=[
            validators.DataRequired(message='邮箱不能为空.'),
            validators.Email(message='邮箱格式错误')
        ],
        widget=widgets.TextInput(input_type='email'),
        render_kw={'class': 'form-control'}
    )

    gender = core.RadioField(
        label='性别',
        choices=(
            (1, '男'),
            (2, '女'),
        ),
        #这句话的意思是上面的choices元组的第一个值是int类型
        #如果上上面为(‘1’, '男'),(‘2’, '女'),则下面的coerce则不用写
        coerce=int # “1” “2”
     )
    #这里是单选框
    city = core.SelectField(
        label='城市',
        choices=(
            ('bj', '北京'),
            ('sh', '上海'),
        )
    )
	#这里是多选框
    hobby = core.SelectMultipleField(
        label='爱好',
        choices=(
            (1, '篮球'),
            (2, '足球'),
        ),
        coerce=int
    )
	#这里是多选的checkbox
    favor = core.SelectMultipleField(
        label='喜好',
        choices=(
            (1, '篮球'),
            (2, '足球'),
        ),
        widget=widgets.ListWidget(prefix_label=False),
        option_widget=widgets.CheckboxInput(),
        coerce=int,
        default=[1, 2]
    )
	#这里可以改值
    def __init__(self, *args, **kwargs):
        super(RegisterForm, self).__init__(*args, **kwargs)
        self.favor.choices = ((1, '篮球'), (2, '足球'), (3, '羽毛球'))

    def validate_pwd_confirm(self, field):
        """
        自定义pwd_confirm字段规则,例:与pwd字段是否一致
        :param field:
        :return:
        """
        # 最开始初始化时,self.data中已经有所有的值

            if field.data != self.data['pwd']:
            # raise validators.ValidationError("密码不一致") # 继续后续验证
            raise validators.StopValidation("密码不一致")  # 不再继续后续验证


@app.route('/register', methods=['GET', 'POST'])
def register():
    if request.method == 'GET':
        #这里可以传默认值
        form = RegisterForm(data={'gender': 2,'hobby':[1,]}) # initial
        return render_template('register.html', form=form)
    else:
        form = RegisterForm(formdata=request.form)
        if form.validate():
            print('用户提交数据通过格式验证,提交的值为:', form.data)
        else:
            print(form.errors)
        return render_template('register.html', form=form)



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

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

我来说两句

0 条评论
登录 后参与评论

相关文章

  • 周末手撸管理系统(一)

    小小咸鱼YwY
  • python爬虫(爬取视频)

    小小咸鱼YwY
  • python调用百度图片识别api

    链接:https://cloud.baidu.com/doc/Reference/s/9jwvz2egb

    小小咸鱼YwY
  • python版本管理(python环境隔

    这将是一篇比较短的文章。 我发文向来注重文章质量,营养不够的宁可不发,但是我相信很多人需要这篇文章。 之所以要去搞清楚这个问题,是我在把 vscode 的 ...

    py3study
  • 从网络协议的角度聊一聊最近Github被大规模攻击事件

    3月27日 Github 疑似遭受大规模攻击, desktop.github.com 、 pages.github.com 、 *.github.io 等多个站...

    ConardLi
  • 我碰到的那些面试题js及es6(1)

    es6是一个新的标准,它包含了许多新的语言特性和库,是JS最实质性的一次升级。比如箭头函数、字符串模板、generators(生成器)、async/await、...

    李才哥
  • SAP Cloud Platform Identity Authentication service

    subaccount和Identity Authentication tenant是一一对应关系:

    Jerry Wang
  • RedHat5.4中关于中文乱码的解决方法

    开始用的vmware6.5,没能把中文包装上,虽然能换成中文,但所有的中文都是十六进制的小方块,困扰了我好长时间了。

    阳光岛主
  • HTML块级元素和行内元素

    秋白
  • [javascript] elementui下login登录页界面和js验证逻辑

    陶士涵

扫码关注云+社区

领取腾讯云代金券