BAE环境中,每一个应用对应一个配置文件app.conf,不少开发者在初次接触BAE的时候,对如何使用app.conf比较困惑,本文对app.conf作一个基本的介绍。 php
1. BAE环境中HTTP请求的处理流程
要理解app.conf的做用,首先要理解HTTP请求在BAE环境中是如何被处理的。 html
- WEB请求首先到达前端 WEB proxy,WEB proxy负责将请求转发给后端的某一个WEB server。(注意,后端可能会有多个WEB server来处理应用的请求)
- 请求到达后端 WEB server后,WEB server 根据 app.conf进行一些特定的处理,因此说app.conf主要是用来控制后端WEB server的处理逻辑的。app.conf的做用比较多,其中主要的功能是实现URL rewrite。
- URL rewrite 完成后,原始的URL被改写, WEB server能根据改写后的URL识别出请求类型,
- 对于静态请求,例如图片、模板、CSS文件、JS文件等,WEB server直接处理
- 对于动态请求,例如PHP脚本、Python脚本等,WEB server进一步将其转发给后端的 Runtime去处理。
- 后端Runtime根据请求,找到对应的处理脚本,例如index.php,执行脚本,并将处理结果返回给浏览器。
2. 用app.conf实现URL rewrite
- 如何使用app.conf ,请先参看BAE配置文件
- 关于 URL rewrite,能够参考URL rewrite
- app.conf 采用的是 YAML格式,参考YAML
- app.conf中,每条规则包括“规则类型”、“规则”和“执行”三个部分,“规则类型”中最重要的是“url”类型, 用来实现URL rewrite。 “规则”指定了URL匹配模式,“执行”指定了URL rewrite的结果; 若某个URL匹配了这个模式,则按照“执行” 对URL进行rewrite。
- 规则是按顺序匹配的,一旦匹配上,就不往下继续匹配了。
- “规则”和“执行”部分支持正则表达式,但使用的是LUA格式的正则表达式,详细的语法后面会介绍。
3. 你在设计app.conf 时要考虑的东西
- 如何设计你的应用的URL的表现形式
- 如何将URL请求路由到你的动态处理脚本
- 区分动态请求和静态请求。对于静态请求,最好让后端WEB server直接处理,这样能够提升性能。
4. 你在设计动态脚本时要考虑的东西
- URL被重写了,有些状况下,须要知道原始URL的信息,能够经过环境变量REQUEST_URI来获取
5. 示例
如图所示,假设你开发了一个应用,但愿把全部的静态文件,都放在应用的 /static 目录下,其它全部的URL,都统一转发给 index.php处理。 前端
示例图中有两条规则,第一条规则,用来处理静态文件;第二条规则,用来处理动态脚本;
规则是按顺序匹配的,一旦匹配上,就不往下继续匹配了 正则表达式
(.*)是正则表达式里面的分组方式,例如URL为 http://xxx.duapp.com/static/f1.jpg ,那么 (.*) 匹配的是 f1.jpg, $1 表示第一个 (.*) 匹配的内容,这里只有一个,那就是 f1.jpg; 后端
示例图中,有两个URL请求, 浏览器
第一个是 http://xxx.duapp.com/aaa/bbb, 经WEB proxy转发后到达WEB server,WEB server根据app.conf 规则进行匹配,匹配到第二条规则,从而将其改写为 http://xxx.duapp.com/index.php, WEB server判断这是一个动态请求,继续向后转发给PHP runtime处理;PHP runtime找到应用目录下的index.php进行处理,并将结果返回给前端。 app
第二个是 http://xxx.duapp.com/static/xxx.jpg, 经WEB proxy转发后到达WEB server,WEB server根据app.conf 规则进行匹配,匹配到第一条规则,从而将其改写为 http://xxx.duapp.com/static/xxx.jpg(改写后的URL与原始的URL是同样的), WEB server判断这是一个静态请求,则本身到应用目录下的static子目录中,找到 xxx.jpg,将其内容返回给前端。 性能
6. app.conf 所用的正则表达式语法简介
BAE rewrite 采用的是 Lua 正则的规则。惟一不一样在于将 Lua 正则的转义符号 % 替换成你们所熟悉的 \
可以使用BAE规则检查器来检查你的规则 url
- x (这里 x 是指其不是这些转义字符 ^$()\.[]*+-? 之一) — 其表明了这个字符自己.
- . 表明任何字符
- * 与普通正则一致,贪婪匹配,即{0,}
- + 与普通正则一致,贪婪匹配,即{1,}
- - 非贪婪匹配,即 *?
- ? 与普通正则一致,贪婪匹配,即{0,1}
- \n n 为1到9之间的数字,用于表示捕获的分组,相似与 \1
- ^ 当在正则表达式开头时,表示匹配字符串起始位置,不然视为普通字符^
- $ 当在正则表达式结尾时,表示匹配字符串结束位置,不然视为普通字符$
- \a 表明任何字母. 即[a-zA-Z]
- \c 表明任何的控制字符暂不支持
- \d 表明任何的数字字符. 即[0-9] 或 \d
- \l 表明全部的小写字母. 即[a-z]
- \p 表明全部的标点符号字符暂不支持
- \s 表明全部空格,tab 字符
- \u 表明全部的大写字母. 即[A-Z]
- \w 表明全部的字母数字. 即[a-zA-Z0-9] 或 \w
- \x 表明16进制数字,相似于 \x,后面须要紧跟两位16进制数字
- \z 表明字符值是 0 的字符. 注意:值为0 的字符是没法正常表达的在表达式中,若是你要使用他,请使用 \z暂不支持
- \x (x是任何非字母和数字的字符)表明字符 x. 这是一种标准的方式来表明应用转义字符. 任何标点符号字符(即便不是转义字符) 在其前面添加一个 \ 能够用来表示其本身 例如 \\ 表示 \ , \$ 表示 $
- [set] 表明一个字符集合. 若是要表达一个范围集合,在范围开始的字符和结尾的字符之间使用 – , 例如要表达 3,4,5,6 这个集合 能够用 [3456] ,也能够用 [3-6] .上面提到的 \x 也能够用到集合中. 例如, [\w_] 表达全部的字母和数字加一个下划线
- [^set] 表达全部不出如今集合内的