🍖五种转换器及自定义转换器
一.转换器
1.五种转换器(与Django中转换器相同)
转换器名称 | 描述 |
---|---|
string | 默认类型,接受不带斜杠的任何文本 |
int | 接受正整数 |
float | 接受正浮点值 |
path | 接收string 但也接受斜线 |
uuid | 接受UUID(通用唯一识别码)字符串 xxxx-xxxx-xxxxx-xxxxx |
2.使用
- 路由格式:
<类型:参数名>
# int整型
@app.route(rule='/user2/<int:id>')
def user2(id):
print('type(id), id:', type(id), id) # type(id), id: <class 'int'=""> 1
return f'<mark>Hello {id}!'
# string字符串
@app.route(rule='/user3/<string:id>')
def user3(id):
print('type(id), id:', type(id), id) # type(id), id: <class 'str'=""> zcdsb123
return f'<mark>Hello {id}!'
# string字符串
@app.route(rule='/user4/<float:id>')
def user4(id):
print('type(id), id:', type(id), id) # type(id), id: <class 'float'=""> 1.1
return f'<mark>Hello {id}!'
# path路径
@app.route(rule='/user5/<path:id>')
def user5(id):
print('type(id), id:', type(id), id) # type(id), id: <class 'str'=""> lxdsb/zcdsb
return f'<mark>Hello {id}!'
# uuid唯一识别码
@app.route(rule='/user6/<uuid:id>')
def user6(id):
print('type(id), id:', type(id), id) # type(id), id: <class 'uuid.uuid'=""> 95db2e6c-e7a7-11ea-9ca3-48ba4e4e6384
return f'<mark>Hello {id}!'
3.转换器默认配置
- flask系统自带转换器编写在werkzeug.routing.py文件中
#: the default converter mapping for the map.
DEFAULT_CONVERTERS: t.Mapping[str, t.Type[BaseConverter]] = {
"default": UnicodeConverter,
"string": UnicodeConverter,
"any": AnyConverter,
"path": PathConverter,
"int": IntegerConverter,
"float": FloatConverter,
"uuid": UUIDConverter,
}
# 每种转换器都映射到一个类, 类中书写了相应的匹配规则
二.自定义转换器
1.为什么自定义转换器
- 关于路由参数的限制,flask内置的类型不够具体,在开发中,我们经常接受参数,需要更加精确的限制
- 这时候,可以使用正则匹配路由参数
- 正则匹配路由参数,其实就是扩展flask内置的路由限定类型,需要完成4个步骤
2.自定义转换器步骤
- 导入转换器基类:在 Flask 中,所有的路由的匹配规则都是使用转换器对象进行记录
- 自定义转换器:自定义类继承于转换器基类
- 添加转换器到默认的转换器字典中
- 使用自定义转换器实现自定义匹配规则
3.自定义一个专门处理手机号的转换器
from flask import Flask, request
# 初始化
app = Flask(import_name=__name__)
# 编写路由视图
@app.route(rule='/')
def index():
return "<h1>hello world!</h1>"
# 1. 引入flask的路由转换器
from werkzeug.routing import BaseConverter
# 2. 创建自定义路由转换器,继承BaseConverter
class MobileConverter(BaseConverter):
def __init__(self, map, *args):
super().__init__(map)
self.regex = "1[3-9]\d{9}" # 匹配手机号
# 3. 把自定义转换器添加到flask默认的转换器字典中,也就是和原来的int,float等放在一块
app.url_map.converters['mobile'] = MobileConverter
# 4. 类似原来的路由参数限制一样,调用自定义转换器名称即可
@app.route(rule='/user/<mobile:mobile>')
def user(mobile):
return mobile
4.自定义一个匹配邮箱的转换器
# 1. 引入flask的路由转换器
from werkzeug.routing import BaseConverter
# 2. 创建自定义路由转换器,继承BaseConverter
class RegexConverter(BaseConverter):
def __init__(self, map, *args):
super().__init__(map)
# self.regex = "\w+@\w+\.\w+"
self.regex = args[0] # 拿到匹配时传过来的匹配规则args=(\w+@\w+\.\w+, )
# 3. 把自定义转换器添加到flask默认的转换器字典中,也就是和原来的int,float等放在一块
app.url_map.converters['re'] = RegexConverter
# 4. 类似原来的路由参数限制一样,调用自定义转换器名称,这里传入的匹配规则会赋值给args[0]
# @app.route(rule='/user/<re:email>')
@app.route(rule='/user/<re("\w+@\w+\.\w+"):email>')
def user2(email):
print(app.url_map) # 获取所有的路由列表
return email
# 声明和加载配置
class Config():
DEBUG = True
app.config.from_object(Config)
5.万能转换器
from flask import Flask, jsonify, views, url_for
from werkzeug.routing import BaseConverter
app = Flask(__name__)
app.debug = True
class RegexConverter(BaseConverter):
"""
自定义URL匹配正则表达式
"""
def __init__(self, map, regex):
super(RegexConverter, self).__init__(map)
# self.regex 固定的属性,专门用来存放正则表达式, flask会去使用这个属性来进行路由的正则匹配
self.regex = regex
def to_python(self, value):
"""
路由匹配时,匹配成功后传递给视图函数中参数的值
"""
return int(value)
def to_url(self, value):
"""
使用url_for反向生成URL时,传递的参数经过该方法处理,返回的值用于生成URL中的参数
"""
val = super(RegexConverter, self).to_url(value)
return val
# 将自定义的转换器添加到flask的应用中
app.url_map.converters['regex'] = RegexConverter
# regex(参数):参数传入正则表达式,这样就可以转换任何你传入的规则
@app.route('/index/<regex("\d+"):nid>', endpoint='index')
def index(nid):
print(nid)
return 'This is index!'
if __name__ == '__main__':
app.run()
</regex("\d+"):nid></re("\w+@\w+.\w+"):email></mobile:mobile></uuid:id></path:id></float:id></string:id></int:id>