Flask URL默认转换器、自定义转换器、to_python、to_url

网友投稿 209 2022-09-20

Flask URL默认转换器、自定义转换器、to_python、to_url

Flask框架自带的转换器类型

int转换器​​​​ :接收整数float转换器​​​​: 接收浮点数string转换器​​​​: 接收string类型(默认则是string转换器)path转换器​​​​:和默认的相似,但也接收斜线

设置int类型的路径参数

# 转换器 @app.route('/goods_info/')def goods_info(goods_id): return "goods_id is %d" % goods_id

测试访问 ​​设置float转换器@app.route('/goods_info/') def goods_info(goods_id): return "goods_id is %s" % goods_id

测试访问​​123 整数的时候,则报错Not Found。

测试访问​​hello 字符串的时候,则报错Not Found。

设置string类型的路径参数

# 设置转换器 @app.route('/goods_info/') def goods_info(goods_id): return "goods_id is %s" % goods_id

测试访问 ​​设置转换器 默认是string@app.route('/goods_info/') def goods_info(goods_id): return "goods_id is %s" % goods_id

设置path转换器的路径参数

# 设置path转换器@app.route('/goods_info/') def goods_info(goods_id): return "goods_id is %s" % goods_id

测试访问:​​path转换器 可以接收斜杠 ​​/​​ 将后面所有的字符串都作为参数传递。

上面的这几种Flask自带的转换器虽然可以设置很多参数了,但是还是无法匹配一些特殊需求的路径参数。

例如:在发送短信的URL中,路径参数设置为手机号码,上面的自带类型就无法精确匹配手机号码了。

这时候就需要自定义路由转换器出场了。

自定义路由转换器

1.自定义路由转换器的基础类:

from werkzeug.routing import BaseConverter

2.创建自定义转换器,以及将转换器加入Flask应用中:

# 创建自定义转换器# 1. 定义自己的转换器class RegexConverter(BaseConverter): """""" def __init__(self, url_map, regex): """ :param url_map: 固定传递的参数,用于调用父类的初始化方法 :param regex: 从url使用()传递过来的正则参数 """ # 调用父类的初始化方法 super(RegexConverter, self).__init__(url_map) # 将正则表达式的参数保存到对象的属性中,flask会去使用这个属性来进行路由的正则匹配 self.regex = regex# 2. 将自定义的转换器添加到flask的应用中app.url_map.converters["re"] = RegexConverter

3.在视图函数中设置自定义路由转换器​​re​​:

# 127.0.0.1:5000/send/18912345678# 使用re自定义转换器,其中()则是需要传递的参数@app.route("/send/") def send_sms(mobile_num): return "send sms to %s" % mobile_num

4.测试访问符合正则匹配的电话号码的url

访问 ​​​​Found。从效果来看,就可以知道通过这个自定义的转换器,我们可以实现这种特殊的参数获取。

创建专属手机号码的转换器

上面的转换器可以传递正则匹配的规则,属于一种万能转换器,下面将其创建一个专属手机号码的转换器。

# 创建Moblie的专属转换器class MobileConverter(BaseConverter): def __init__(self,url_map): # super(MobileConverter,self).__init__(url_map) # 调用父类方法一 super().__init__(url_map) # 调用父类方法二 self.regex = r'1[34578]\d{9}'# 注册MobileConverter转换器app.url_map.converters["mobile"] = MobileConverter# 设置视图函数@app.route("/send/")def send_sms(mobile_num): return "send sms to %s" % mobile_num

其实这个例子主要是想说明Flask可以创建多个自定义转换器。

另外,在Django中有中间类这个类方法来处理url请求至视图函数之间的业务处理,例如:权限验证,session数据记录等等。

在Flask中可以使用专属转换器的​​to_python​​​和​​to_url​​两个函数来实现类似中间类这样的功能。

下面来看看。

查看BaseConverter类中的源码

class BaseConverter(object): """Base class for all converters.""" regex = "[^/]+" weight = 100 def __init__(self, map): self.map = map def to_python(self, value): return value def to_url(self, value): if isinstance(value, (bytes, bytearray)): return _fast_url_quote(value) return _fast_url_quote(text_type(value).encode(self.map.charset))

首先从源码来分析一下这个继承类中​​to_python​​​和​​to_url​​函数。

to_python 将url传递的参数,直接将其传递至视图函数之中to_url 则是当另一个视图函数使用​​url_for()​​ 这个方法跳至该转换器的时候,会将url的参数传递到url路径的参数中。

单单这么解释有些抽象,下面来看看示例。

to_python 函数

# 创建Moblie的专属转换器class MobileConverter(BaseConverter): def __init__(self,url_map): # super(MobileConverter,self).__init__(url_map) super().__init__(url_map) self.regex = r'1[34578]\d{9}' def to_python(self, value): """""" print("to_python方法被调用") # value是在路径进行正则表达式匹配的时候提取的参数 return "abc" # 该value会传递到视图函数中app.url_map.converters["mobile"] = MobileConverter@app.route("/send/")def send_sms(mobile_num): return "send sms to %s" % mobile_num

此时测试访问 ​​send sms to 18912345678 的信息,但是由于​​to_python​​ 设置返回是 “abc”,所以浏览器将会打印 send sms to abc,下面来浏览器执行验证看看,如下:

从浏览器就可以判断出​​to_python​​方法就是url传递到视图函数中间的业务处理方法,其实就相当于Django的中间类。

如果有权限验证类的需求,可以在​​to_python​​中实现。

to_url 函数

# 创建Moblie的专属转换器class MobileConverter(BaseConverter): def __init__(self,url_map): # super(MobileConverter,self).__init__(url_map) super().__init__(url_map) self.regex = r'1[34578]\d{9}' def to_python(self, value): """""" print("to_python方法被调用") # value是在路径进行正则表达式匹配的时候提取的参数 return value # 该value会传递到视图函数中 def to_url(self, value): """使用url_for的方法的时候被调用""" print("to_url方法被调用") return "15811111111" # 该value会修改url路径中的参数为 15811111111app.url_map.converters["mobile"] = MobileConverter@app.route("/send/")def send_sms(mobile_num): return "send sms to %s" % mobile_num@app.route("/hello_send")def hello_send(): return redirect(url_for('send_sms', mobile_num=18612345678))

这个示例是首先访问 hello_send 视图函数,然后使用 url_for函数跳转至 send_sms 视图函数。

在这种过程中,hello_send 视图函数跳转的时候设置的路径参数为 mobile_num=18612345678。

那么正常在浏览器转发后的url访问应该是:​​​​http://127.0.0.1:5000/send/15811111111​​

下面来确认看看,访问​​http://127.0.0.1:5000/hello_send​​

可以从图中的传递说明,应该基本上都可以看出参数的传递过程。

版权声明:本文内容由网络用户投稿,版权归原作者所有,本站不拥有其著作权,亦不承担相应法律责任。如果您发现本站中有涉嫌抄袭或描述失实的内容,请联系我们jiasou666@gmail.com 处理,核实后本网站将在24小时内删除侵权内容。

上一篇:猿大侠:B站,又出了一个大料!
下一篇:线程池的7种创建方式,强烈推荐你用它...
相关文章

 发表评论

暂时没有评论,来抢沙发吧~