werkzeug/routing.py-Rule源码分析
Rule类主要用来定义和表示一个URL的模式。主要定义了一些关键字参数,用来改变url的行为。例如:这个url可以接收的请求方法,url的子域名,默认路径,端点名称,是否强制有斜杠在末尾等等
在最开始使用route()传递的option参数,最后都是传给了Rule这个类来处理的
class Rule(RuleFactory):
def __init__(self, string, defaults=None, subdomain=None, methods=None,
build_only=False, endpoint=None, strict_slashes=None,
redirect_to=None, alias=False, host=None):
if not string.startswith('/'):
raise ValueError('urls must start with a leading slash')
self.rule = string
self.is_leaf = not string.endswith('/') self.map = None
self.strict_slashes = strict_slashes
self.subdomain = subdomain
self.host = host
self.defaults = defaults
self.build_only = build_only
self.alias = alias
if methods is None:
self.methods = None
else:
if isinstance(methods, str):
raise TypeError('param `methods` should be `Iterable[str]`, not `str`')
self.methods = set([x.upper() for x in methods])
if 'HEAD' not in self.methods and 'GET' in self.methods:
self.methods.add('HEAD')
self.endpoint = endpoint
self.redirect_to = redirect_to if defaults:
self.arguments = set(map(str, defaults))
else:
self.arguments = set()
self._trace = self._converters = self._regex = self._argument_weights = None
源代码
参数解析:
- string:一个有含有占位符的url路径(<converter(arguments):name>), converter是可选的(converter定义在Map里面),默认是字符串
- defaults:可选项。在同一个endpoint下的一个字典格式的默认规则,如果你访问某个url的时候,这个url存在default配置,则会显示defaluts对用的url路径 例如:
url_map = Map([
Rule('/all/', defaults={'page': 1}, endpoint='all_entries'),
Rule('/all/page/<int:page>', endpoint='all_entries')
])
# 当用户访问``http://example.com/all/page/1`` h将会重定向到``http://example.com/all/``.
- subdomain:用来定义这个rule的子域名规则的一个字符串。默认是disable的,用法如下
url_map = Map([
Rule('/', subdomain='<username>', endpoint='user/homepage'),
Rule('/stats', subdomain='<username>', endpoint='user/stats')
])
- methods:定义允许访问的方法。默认只允许get方法。在0.6.1版本中,会自动添加HEAD如果存在GET请求的话
- bulid_only:True, 只创建url,而不会被匹配。一般用于静态文件的路径创建,不需要WSGI application处理的情况下
- endpoint:这个url的端点名称,可以是任何类型。最好的选择是使用字符串表示,
- strict_slashes:是否严格要求URL后面的斜杠。为这个URL重写Map里面的strict_slashes配置
- redirect_to:重定向到其他地址。可以是一个字符串(其他url路径),也可以是一个可调用的对西对象。例如:
def foo_with_slug(adapter, id):
# ask the database for the slug for the old id. this of
# course has nothing to do with werkzeug.
return 'foo/' + Foo.get_slug_for_id(id) url_map = Map([
Rule('/foo/<slug>', endpoint='foo'),
Rule('/some/old/url/<slug>', redirect_to='foo/<slug>'), # 重定向到上面定义的路径
Rule('/other/old/url/<int:id>', redirect_to=foo_with_slug) # 重定向到foo_with_slug函数
])
- alias:在同一个endpoint里面为rule serves定义一个别名
- host:为整个host提供匹配规则。如果设置了host,则subdomain会是disabled状态
函数体解析:
def __init__(self, string, defaults=None, subdomain=None, methods=None,
build_only=False, endpoint=None, strict_slashes=None,
redirect_to=None, alias=False, host=None):
# 判断url路径是否是斜线开头
if not string.startswith('/'):
# 抛出异常:urls必须以斜线开头
raise ValueError('urls must start with a leading slash')
self.rule = string
self.is_leaf = not string.endswith('/') self.map = None
self.strict_slashes = strict_slashes
self.subdomain = subdomain
self.host = host
self.defaults = defaults
self.build_only = build_only
self.alias = alias
# 对methods参数的判断
if methods is None:
self.methods = None
else:
if isinstance(methods, str):
raise TypeError('param `methods` should be `Iterable[str]`, not `str`')
self.methods = set([x.upper() for x in methods])
# 如果没有HEAD和有GET的时候,把HEAD添加到methods里面
if 'HEAD' not in self.methods and 'GET' in self.methods:
self.methods.add('HEAD')
self.endpoint = endpoint
self.redirect_to = redirect_to if defaults:
# 通过map对象以及str函数,取出defaulte中的每一个键,并设置成字符串格式。最终保存为set格式:{'abc'}
self.arguments = set(map(str, defaults))
else:
self.arguments = set()
self._trace = self._converters = self._regex = self._argument_weights = None
在Map对象的add方法中调用了Rule对象的get_rules方法
def get_rules(self, map):
yield self
在Map对象的app方法中调用了Rule类的bind方法
这个方法主要用来绑定路由规则到map,并基于路由规则信息创建正则表达式
def bind(self, map, rebind=False):
# 判断这个rule的map属性是否已经被绑定过了map值
if self.map is not None and not rebind:
raise RuntimeError('url rule %r already bound to map %r' %
(self, self.map))
# 把Map的对象赋值给self.map
self.map = map
# 判断属性,如果Rule对象中没有,则使用Map类中的
if self.strict_slashes is None:
self.strict_slashes = map.strict_slashes
if self.subdomain is None:
self.subdomain = map.default_subdomain
# 调用Rule类的compile方法
self.compile()
bind方法最后调用了Rule类的compile方法
这个方法主要用来编译和存储正则表达式
werkzeug/routing.py-Rule源码分析的更多相关文章
- JUnit源码分析 - 扩展 - 自定义Rule
JUnit Rule简述 Rule是JUnit 4.7之后新加入的特性,有点类似于拦截器,可以在测试类或测试方法执行前后添加额外的处理,本质上是对@BeforeClass, @AfterClass, ...
- flask/app.py-add_url_rule源码分析
之前分析route方法的时候,可以看到中间会调用add_url_rule方法,add_url_rule方法和route方法一样属于Flask这个类的. add_url_rule方法主要用来连接url规 ...
- FastText总结,fastText 源码分析
文本分类单层网络就够了.非线性的问题用多层的. fasttext有一个有监督的模式,但是模型等同于cbow,只是target变成了label而不是word. fastText有两个可说的地方:1 在w ...
- Python 日志打印之logging.getLogger源码分析
日志打印之logging.getLogger源码分析 By:授客 QQ:1033553122 #实践环境 WIN 10 Python 3.6.5 #函数说明 logging.getLogger(nam ...
- illuminate/routing 源码分析之注册路由
我们知道,在 Laravel 世界里,外界传进来一个 Request 时,会被 Kernel 处理并返回给外界一个 Response.Kernel 在处理 Request 时,会调用 illumina ...
- OpenHarmony移植案例: build lite源码分析之hb命令__entry__.py
摘要:本文介绍了build lite 轻量级编译构建系统hb命令的源码,主要分析了_\entry__.py文件. 本文分享自华为云社区<移植案例与原理 - build lite源码分析 之 hb ...
- flask源码分析
本flask源码分析不间断更新 而且我分析的源码全是我个人觉得是很beautiful的 1 flask-login 1.1 flask.ext.login.login_required(func),下 ...
- Flask系列之源码分析(一)
目录: 涉及知识点 Flask框架原理 简单示例 路由系统原理源码分析 请求流程简单源码分析 响应流程简单源码分析 session简单源码分析 涉及知识点 1.装饰器 闭包思想 def wapper( ...
- Flask源码分析二:路由内部实现原理
前言 Flask是目前为止我最喜欢的一个Python Web框架了,为了更好的掌握其内部实现机制,这两天准备学习下Flask的源码,将由浅入深跟大家分享下,其中Flask版本为1.1.1. 上次了解了 ...
- Flask系列10-- Flask请求上下文源码分析
总览 一.基础准备. 1. local类 对于一个类,实例化得到它的对象后,如果开启多个线程对它的属性进行操作,会发现数据时不安全的 import time from threading import ...
随机推荐
- springboot+jwt完成登录认证
本demo用于测试jwt,通过登录验证通过后,使用jwt生成token,然后在请求header中携带token完成访问用户列表信息. 准备工作: 1. 实体类SysUser.java package ...
- [原]Arcgis arcmap修改图元配色
感谢南师大的“深爱”提供的帮助 1.选择识别工具,点击海洋,确定海洋色块的color index为255 2.右键tif选择属性 3.选择分页栏中的符号化(Symbology) 4.找到对应的Labe ...
- flutte的第一个hello world程序
用命令行创建项目: flutter create flutterdemo VSCode或者AS连接手机后 输入 flutter run 编译后就可以将默认的代码显示在手机上了 开始写hello wor ...
- stl中map的四种插入方法总结
stl中map的四种插入方法总结方法一:pair例:map<int, string> mp;mp.insert(pair<int,string>(1,"aaaaa&q ...
- .NET Core入门程序
易百教程 https://www.yiibai.com/dotnet_core/dotnet_core_getting_started.html
- linux部署php网页
liunx环境下运行php和传统的Java web程序不一样.我直接放在tomcat下竟然不行. 安装了php的一些环境,还是访问不了,原因是不支持https访问.没办法,还是得用tomcat,同时我 ...
- ios开发将截图保存到相册
- (void)loadImageFinished:(UIImage *)image { UIImageWriteToSavedPhotosAlbum(image, self, @selector(i ...
- Day2作业:购物商城
ReadMe: 注意事项: 1.本程序需要提前安装prettytable模块,在商品展示时使用了prettytable 2.数据库使用json模块,有中文数据,在mac系统上编写,运行没有出现问题,在 ...
- SAP RFC和BAPI
RFC和BAPI都是SAP提供的接口技术.RFC全称Remote Function Call,就是允许远程调用的函数模块. BAPI则是基于RFC的新技术,全称Business Application ...
- Delphi 中使用计算出的字段
在很多情况下,我们需要的数据与数据库中其它字段的数据相关,例如订单的金额为数量与单价的乘积.在应用程序中,若要在显示订单具体条目的同时显示金额,通常要创建一个字段,在显示该字段之前先进行乘法运算,将金 ...