您的位置:首页 > 其它

[py]一步一步实现tornado form验证

2017-08-29 23:10 162 查看

第一关



第二关



第四关



第五关



第六关



以下是各步逐渐成熟的代码.关数和上面图无关.

相关git代码

第零关: 一个index表单

#!/usr/bin/env python
# -*- coding:utf-8 -*-

import tornado.ioloop
import tornado.web
from hashlib import sha1
import os, time
import re

# 创建form类
class MainForm(object):
# 初始化
def __init__(self):
self.host = "(.*)"
self.ip = "^(25[0-5]|2[0-4]\d|[0-1]?\d?\d)(\.(25[0-5]|2[0-4]\d|[0-1]?\d?\d)){3}$"
self.port = '(\d+)'
self.phone = '^1[3|4|5|8][0-9]\d{8}$'

# 验证
def check_valid(self, request):
# 循环当前类中的成员,注意此种方法

flag = True
value_dict = {}

for key, regular in self.__dict__.items():
'''
通过request.get_argument()来获取用户前端输入的值
在循环时,不需要关心前端输入值的个数,这里以自定义方法为主
'''
post_value = request.get_argument(key)
# 前端提交的数据与自定义的正则表达式进行匹配验证
ret = re.match(regular, post_value)
print(key,"---------",ret, "---------",post_value)

# 如果结果 结果为None时候,即只要有一项不匹配,就返回false,flag = False
if not ret:
flag = False
# {"ip":192.168.1.1,"port":8080,....}
value_dict[key] = post_value
# print(value_dict)
return flag,value_dict

class MainHandler(tornado.web.RequestHandler):
def get(self):
self.render('index.html')

def post(self, *args, **kwargs):
obj = MainForm()
is_valid, value_dict= obj.check_valid(self)
# self.write('ok')
# 如果全部验证成功,则打印
if is_valid:
print(value_dict)
self.write("ok")

settings = {
'template_path': 'templates',
'static_path': 'statics',
'static_url_prefix': '/static/',
'cookie_secret': 'aiua
4000
sdhflashjdfoiuashdfiuh',
'login_url': '/login'
}

application = tornado.web.Application([
(r"/index", MainHandler),
], **settings)

if __name__ == "__main__":
print("http://127.0.0.1:8888/index")
application.listen(8888)
tornado.ioloop.IOLoop.instance().start()


index.html

<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title></title>
<link href="{{static_url("commons.css")}}" rel="stylesheet" />
</head>
<body>
<h1>hello</h1>
<form action="/index" method="post">

<p>hostname: <input type="text" name="host" /> </p>
<p>ip: <input type="text" name="ip" /> </p>
<p>port: <input type="text" name="port" /> </p>
<p>phone: <input type="text" name="phone" /> </p>
<input type="submit" />
</form>
</body>
</html>


第一关: 2个表单index和home需要验证

form11.html

#!/usr/bin/env python
# -*- coding:utf-8 -*-

import tornado.ioloop
import tornado.web
from hashlib import sha1
import os, time
import re

# 创建indexform类
class IndexForm(object):
# 初始化
def __init__(self):
self.host = "(.*)"
self.ip = "^(25[0-5]|2[0-4]\d|[0-1]?\d?\d)(\.(25[0-5]|2[0-4]\d|[0-1]?\d?\d)){3}$"
self.port = '(\d+)'
self.phone = '^1[3|4|5|8][0-9]\d{8}$'

# 验证
def check_valid(self, request):
# 循环当前类中的成员,注意此种方法

flag = True
value_dict = {}

for key, regular in self.__dict__.items():
'''
通过request.get_argument()来获取用户前端输入的值
在循环时,不需要关心前端输入值的个数,这里以自定义方法为主
'''
post_value = request.get_argument(key)
# 前端提交的数据与自定义的正则表达式进行匹配验证
ret = re.match(regular, post_value)
print(key,"---------",ret, "---------",post_value)

# 如果结果 结果为None时候,即只要有一项不匹配,就返回false,flag = False
if not ret:
flag = False
# {"ip":192.168.1.1,"port":8080,....}
value_dict[key] = post_value
# print(value_dict)
return flag,value_dict

# 创建homeform类
class HomeForm(object):
# 初始化
def __init__(self):
self.host = "(.*)"
self.ip = "^(25[0-5]|2[0-4]\d|[0-1]?\d?\d)(\.(25[0-5]|2[0-4]\d|[0-1]?\d?\d)){3}$"

# 验证
def check_valid(self, request):
# 循环当前类中的成员,注意此种方法

flag = True
value_dict = {}

for key, regular in self.__dict__.items():
'''
通过request.get_argument()来获取用户前端输入的值
在循环时,不需要关心前端输入值的个数,这里以自定义方法为主
'''
post_value = request.get_argument(key)
# 前端提交的数据与自定义的正则表达式进行匹配验证
ret = re.match(regular, post_value)
print(key,"---------",ret, "---------",post_value)

# 如果结果 结果为None时候,即只要有一项不匹配,就返回false,flag = False
if not ret:
flag = False
# {"ip":192.168.1.1,"port":8080,....}
value_dict[key] = post_value
# print(value_dict)
return flag,value_dict

class IndexHandler(tornado.web.RequestHandler):
def get(self):
self.render('index.html')

def post(self, *args, **kwargs):
obj = IndexForm()
is_valid, value_dict= obj.check_valid(self)
# self.write('ok')
# 如果全部验证成功,则打印
if is_valid:
print(value_dict)
self.write("ok")

class HomeHandler(tornado.web.RequestHandler):
def get(self):
self.render('home.html')

def post(self, *args, **kwargs):
obj = HomeForm()
is_valid, value_dict= obj.check_valid(self)
# self.write('ok')
# 如果全部验证成功,则打印
if is_valid:
print(value_dict)
self.write("ok")

settings = {
'template_path': 'templates',
'static_path': 'statics',
'static_url_prefix': '/static/',
'cookie_secret': 'aiuasdhflashjdfoiuashdfiuh',
'login_url': '/login'
}

application = tornado.web.Application([
(r"/index", IndexHandler),
(r"/home", HomeHandler),
], **settings)

if __name__ == "__main__":
print("http://127.0.0.1:8888/index")
application.listen(8888)
tornado.ioloop.IOLoop.instance().start()


index.html

<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title></title>
<link href="{{static_url("commons.css")}}" rel="stylesheet" />
</head>
<body>
<h1>hello</h1>
<form action="/index" method="post">

<p>hostname: <input type="text" name="host" /> </p>
<p>ip: <input type="text" name="ip" /> </p>
<p>port: <input type="text" name="port" /> </p>
<p>phone: <input type="text" name="phone" /> </p>
<input type="submit" />
</form>
</body>
</html>


home.html

<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title></title>
<link href="{{static_url("commons.css")}}" rel="stylesheet" />
</head>
<body>
<h1>hello</h1>
<form action="/home" method="post">

<p>hostname: <input type="text" name="host" /> </p>
<p>ip: <input type="text" name="ip" /> </p>
<input type="submit" />
</form>
</body>
</html>


第二关:2个表单index和home需要验证-继承

完整code

form12.py

#!/usr/bin/env python
# -*- coding:utf-8 -*-

import re

import tornado.web

# 验证类
class BaseForm(object):
# 验证
def check_valid(self, request):
# 循环当前类中的成员,注意此种方法

flag = True
value_dict = {}

for key, regular in self.__dict__.items():
'''
通过request.get_argument()来获取用户前端输入的值
在循环时,不需要关心前端输入值的个数,这里以自定义方法为主
'''
post_value = request.get_argument(key)
# 前端提交的数据与自定义的正则表达式进行匹配验证
ret = re.match(regular, post_value)
print(key, "---------", ret, "---------", post_value)

# 如果结果 结果为None时候,即只要有一项不匹配,就返回false,flag = False
if not ret:
flag = False
# {"ip":192.168.1.1,"port":8080,....}
value_dict[key] = post_value
# print(value_dict)
return flag, value_dict

# 创建indexform类
class IndexForm(BaseForm):
# 初始化
def __init__(self):
self.host = "(.*)"
self.ip = "^(25[0-5]|2[0-4]\d|[0-1]?\d?\d)(\.(25[0-5]|2[0-4]\d|[0-1]?\d?\d)){3}$"
self.port = '(\d+)'
self.phone = '^1[3|4|5|8][0-9]\d{8}$'

# 创建homeform类
class HomeForm(BaseForm):
# 初始化
def __init__(self):
self.host = "(.*)"
self.ip = "^(25[0-5]|2[0-4]\d|[0-1]?\d?\d)(\.(25[0-5]|2[0-4]\d|[0-1]?\d?\d)){3}$"

class IndexHandler(tornado.web.RequestHandler):
def get(self):
self.render('index.html')

def post(self, *args, **kwargs):
obj = IndexForm()
is_valid, value_dict = obj.check_valid(self)
# self.write('ok')
# 如果全部验证成功,则打印
if is_valid:
print(value_dict)
self.write("ok")

class HomeHandler(tornado.web.RequestHandler):
def get(self):
self.render('home.html')

def post(self, *args, **kwargs):
obj = HomeForm()
is_valid, value_dict = obj.check_valid(self)
# self.write('ok')
# 如果全部验证成功,则打印
if is_valid:
print(value_dict)
self.write("ok")

settings = {
'template_path': 'templates',
'static_path': 'statics',
'static_url_prefix': '/static/',
'cookie_secret': 'aiuasdhflashjdfoiuashdfiuh',
'login_url': '/login'
}

application = tornado.web.Application([
(r"/index", IndexHandler),
(r"/home", HomeHandler),
], **settings)

if __name__ == "__main__":
print("http://127.0.0.1:8888/index")
application.listen(8888)
tornado.ioloop.IOLoop.instance().start()

## 不能区分是哪里错了


home.html

<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title></title>
<link href="{{static_url("commons.css")}}" rel="stylesheet" />
</head>
<body>
<h1>hello</h1>
<form action="/home" method="post">

<p>hostname: <input type="text" name="host" /> </p>
<p>ip: <input type="text" name="ip" /> </p>
<input type="submit" />
</form>
</body>
</html>


index.html

<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title></title>
<link href="{{static_url("commons.css")}}" rel="stylesheet" />
</head>
<body>
<h1>hello</h1>
<form action="/index" method="post">

<p>hostname: <input type="text" name="host" /> </p>
<p>ip: <input type="text" name="ip" /> </p>
<p>port: <input type="text" name="port" /> </p>
<p>phone: <input type="text" name="phone" /> </p>
<input type="submit" />
</form>
</body>
</html>


第三关:封装字段

理解这个,需要一点前戏, 猛戳这里

以ipfield为例

效果



如果没自定义信息,如果输入格式错误,则报系统内置错误

如果自定义了错误信息,则优先报自定义的错误

逻辑关系



代码逻辑



完整code

form13.py

#!/usr/bin/env python
# -*- coding:utf-8 -*-

import re

import tornado.web

class IPField:
REGULAR = "^(25[0-5]|2[0-4]\d|[0-1]?\d?\d)(\.(25[0-5]|2[0-4]\d|[0-1]?\d?\d)){3}$"

# error_dict 自定义报错信息
def __init__(self, error_dict=None, required=True):
self.error_dict = {}

# 如果自定义了错误信息,更新错误
if error_dict:
self.error_dict.update(error_dict)

# 保存required
self.required = required

# 错误信息
self.error = None
# 是否匹配
self.is_valid = None
# 匹配成功后值是多少
self.value = None

# name 字段名(便于提示错误)
# input_value 用于输入值,用于验证
def validate(self, name, input_value):
'''

:param name: 字段名(便于提示错误)
:param input_value:
:return: input_value 用于输入值,用于验证
'''

if not self.required:
# 值允许为空
self.is_valid = True
self.value = input_value
else:
# 值不允许为空

if not input_value.strip():
# 用户输入为空
if self.error_dict.get("required", None):
# 生成错误信息

self.error = self.error_dict["required"]
else:
# 提示ip不能为空
self.error = "%s is required" % name
else:
# 用户输入了ip,接下来判断ip格式
ret = re.match(IPField.REGULAR, input_value)  # 静态字段IPField.REGULAR
if ret:
# 匹配成功
self.is_valid = True
self.value = ret.group()
# self.value = ret.input_value
else:
# 匹配失败 构造错误信息
if self.error_dict.get("valid", None):
self.error = self.error_dict["valid"]
else:
self.error = "%s is invalid" % name

# 验证类
class BaseForm(object):
# 验证
def check_valid(self, handle):
# 循环当前类中的成员,注意此种方法
flag = True
value_dict = {}

# 错误信息
error_msg_dict = {}
success_value_dict = {}
for key, regular in self.__dict__.items():
# key: ip
# regular: IPField对象
# input_value 用户输入的值
input_value = handle.get_argument(key)

regular.validate(key, input_value)
# 如果验证成功
if regular.is_valid:
# pass
success_value_dict[key] = regular.value
else:
error_msg_dict[key] = regular.error
# 如果验证失败
flag = False
value_dict[key] = input_value
return flag, success_value_dict, error_msg_dict

# 创建homeform类
class HomeForm(BaseForm):
# 初始化
def __init__(self):
# self.host = "(.*)"
# self.ip = "^(25[0-5]|2[0-4]\d|[0-1]?\d?\d)(\.(25[0-5]|2[0-4]\d|[0-1]?\d?\d)){3}$"
self.ip = IPField(required=True,
error_dict={"required": "别闹,不能为空", "valid": "格式错了,兄弟..."})  # required=True 必须要写
# self.ip = IPField()

class HomeHandler(tornado.web.RequestHandler):
def get(self):
self.render('home1.html')

def post(self, *args, **kwargs):
obj = HomeForm()

is_valid, success_dict, error_dict = obj.check_valid(self)
# self.write('ok')
# 如果全部验证成功,则打印
if is_valid:
print("sucess", success_dict)
else:
print("error", error_dict)

settings = {
'template_path': 'templates',
'static_path': 'statics',
'static_url_prefix': '/static/',
'cookie_secret': 'aiuasdhflashjdfoiuashdfiuh',
'login_url': '/login'
}

application = tornado.web.Application([
(r"/home", HomeHandler),
], **settings)

if __name__ == "__main__":
print("http://127.0.0.1:8888/index")
application.listen(8888)
tornado.ioloop.IOLoop.instance().start()


home1.html

<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title></title>
<link href="{{static_url("commons.css")}}" rel="stylesheet" />
</head>
<body>
<h1>hello</h1>
<form action="/home" method="post">
<p>ip: <input type="text" name="ip" /> </p>
<input type="submit" />
</form>
</body>
</html>
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: