语法规则
当您希望通过编程模式来自行编写边缘规则时,你需要对又拍云边缘规则的语法规则进行详细了解,方可自行编写规则。本文将围绕函数、变量、字符串常量、break 进行详细介绍。
函数
函数调用以 $
开头,后跟一组大写字母,字母之间可以包含下划线 _
,函数需要的参数放在()
中,以 ,
分隔。如果没有特别说明,边缘规则 中的函数参数个数不能少于要求的参数个数,否则视为语法错误,然后终止规则执行过程,多余的参数会被求值,但不影响调用。函数调用是有上下文的,譬如 $WHEN
这个函数,参数是 bool
类 型,参数中有不成立的条件 false
时,会终止本次规则执行过程。支持的函数有:
条件选择和判断
函数 | 含义 |
---|---|
$WHEN(E1, E2, ...) |
所有条件都成立时才会执行规则,并返回空字符串 |
$NOT(E) |
E 不成立时返回 true , 否则返回 false |
$ALL(E1, E2, ...) |
所有条件都成立时返回 true ,否则返回 false ,参数个数不限 |
$ANY(E1, E2, ...) |
其中一个条件成立时返回 true ,否则返回 false ,参数个数不限 |
$OR(E1, E2, ...) |
值为第一个为真的表达式 |
$SELECT(E1, E2, E3) |
E1 为真时值为 E2 ,否则为 E3 |
$PCALL(E) |
保护模式下解析 E ,失败时返回空字符串 |
字符匹配和捕获
函数 | 含义 |
---|---|
$MATCH(E1, E2) |
PCRE 匹配,E2 为要匹配的 pattern,返回 true 或者 false |
$CAPTURE(E1, E2, E3) |
按 E2 pattern 对 E1 进行捕获,E3 表示是否忽略大小写,捕获后生成 $n.m 形式的变量,n 为当前 CAPTURE 出现的次序,m 表示匹配分组;E2 为空时,表示对 E1 进行捕获,此时 E1 对应 $n.0 |
请求/响应修改
函数 | 含义 |
---|---|
$ADD_REQ_HEADER(E1, E2) |
添加请求头 E1 为 E2 |
$DEL_REQ_HEADER(E) |
删除请求头 E |
$ADD_RSP_HEADER(E1, E2) |
添加响应头 E1 为 E2 |
$DEL_RSP_HEADER(E) |
删除响应头 E |
$DEL_ARG(E) |
删除请求参数项 E |
$SET_METHOD(E) |
修改当前 HTTP 请求方法为 E ,E 可选值有:GET , HEAD , PUT , POST , DELETE , OPTIONS , PATCH ; 注 1 |
$SET_BODY(E) |
修改当前 HTTP 请求体的内容为 E ,仅在 PUT 或 POST 请求下有效 |
$SET_STATUS(E) |
修改当前 HTTP 响应状态码为 E ,使用时,整条规则最前面添加”!!”,例 !!xxxxxx$SET_STATUS(403) |
$REDIRECT(E1, E2) |
重定向地址到 E1 ,状态码为 E2(301, 302) |
$EXIT(E1, E2) |
以状态码 E1 退出,响应体为 E2 |
注: 删除响应头函数不能删除 CDN 自带的一些字段,比如 via、age、server、connection、x-cache、x-request-id、x-source、content-length、transfer-encoding等字段是有保护的。
数值计算
函数 | 含义 |
---|---|
$ADD(E1, E2) |
数字相加,返回 E1 + E2 结果数值 |
$MOD(E1, E2) |
数字取余,返回 E1 % E2 结果数值,其中 E2 不能为 0 |
$MSUB(E1, E2) |
数字相减,返回 E1 - E2 结果数值 |
$MULTIPLY(E1, E2) |
数字相乘,返回 E1 * E2 结果数值 |
$DIVIDE(E1, E2) |
数字相除,返回 E1 / E2 结果数值,其中 E2 不能为 0 |
$BYTE(E) |
返回字符 E 的 ASCII 编码值 |
$FLOOR(E) |
返回小于或等于数字 E 的最大整数 |
$CEIL(E) |
返回大于或等于数字 E 的最小整数 |
$GT(E1, E2) |
数字比较,是否大于,返回 true 或者 false |
$GE(E1, E2) |
数字比较,是否大于等于,返回 true 或者 false |
字符串操作
函数 | 含义 |
---|---|
$SUB(E1, from, to) |
字符串截取,从 from 到 to |
$GSUB(E1,E2,E3,N) |
E1 为要处理的字符串,E2 为要替换的字符串,E3 为替换成的字符串(可以为空,表示删除E1 ),N 为从字符串开始的替换E1 的个数,空或小于零表示所有,函数返回处理后的字符串 |
$EQ(E1, E2) |
字符串是否相等,返回 true 或者 false |
$UPPER(E) |
将 E 转换为大写 |
$LOWER(E) |
将 E 转换为小写 |
$LEN(E) |
返回字符串 E 的长度 |
通用功能类函数
函数 | 含义 |
---|---|
$ENCODE_BASE64(E) |
将字符串 E 按 base64 编码压缩 |
$DECODE_BASE64(E) |
将字符串 E 按 base64 编码解压 |
$ESCAPE(E) |
将字符串 E 按 URL 编码处理,具体实现和 Chrome JS 实现的 encodeURIComponent() 一致 |
$UNESCAPE(E) |
将字符串 E 按 URL 解码处理,具体实现和 Chrome JS 实现的 decodeURIComponent() 一致 |
$MD5(E) |
计算 E 的 md5 值 |
$MD5_BIN(E) |
计算 E 的 md5 值,并以二进制数据输出 |
$RANDI(E1, E2) |
返回大于 E1 并小于 E2 的随机数值 |
$UNIXT(y, m, d, h, min, sec) |
指定年,月,日,小时,分钟,秒,返回相应的 UNIX TIME |
$INT(E1, E2, E3) |
进制转换,将 E2 进制的数字(字符串形式) E1 转换成 E3 进制并返回,E2 , E3 可选,E2 默认为 10 |
$STRF_TIME(E1,E2 ) |
时间格式转换,表示把时间进行格式化成年月日时分,E1 代表 UNIX 时间戳,可以使用变量 $_TIME 来获取当前时间;E2 为间隔符,为可选项,不填时格式为 201802230955 ;间隔符为 - 时,格式为2018-02-23-09-55 |
限速相关
函数 | 含义 |
---|---|
$LIMIT_RATE_AFTER(E1, E2) |
限速策略设置,发送 E1 大小单位为 E2 字节数据后,进行限速,E2 可选值有:k (KB),m (MB) |
$LIMIT_RATE(E1, E2) |
限速策略设置,按 E1 大小每秒进行限速,单位为 E2 ,E2 可选值有:k (KB),m (MB) |
注 1:若当前请求带有请求体的情况下,$SET_METHOD(E)
不允许设置为除 PUT
和 POST
以外的方法。
其中 E[n]
代表合法的表达式,也就是说函数可以相互嵌套,例如规则可以为:
/$SUB($DECODE_BASE64($_HEADER_foo), $_GET_from, $_GET_to)/
;布尔函数包括 WHEN
都是短路的,譬如
, ALL, ANY$WHEN($ALL(), $EXIT(403))
不会返回 403
,因为 $ALL()
的值为 false
使用 ''
能对变量进行转义,使其不被解释,例如以下规则:
/foo/'$_HOST'
会被转换为:
/foo/$_HOST
对于含有请求参数的规则,原先的请求参数会附加到后面,如果不希望这样,可以放置一个 ‘?’ 在规则的最后面,例如这样:
/foo?bar=$1?
特别地,如果重写后的 URL 没有参数,那么此时需要在最后加两个 ?
,例如这样:
/foo??
变量
变量以 $_
开头,这些变量都是对此次请求上下文中一些参数的映射,譬如 $_HOST
对应此次请求头中的 Host
字段,$_GET_foo
对应此次请求 URL 参数 foo 的值,等等。若将变量内插到重写后的 URL 中,譬如 URL 改写 /$_GET_foo/bar
,如果请求参数中没有 foo
则视为此次改写 失败;
若将变量放在函数中,则由该函数确定返回的值,例如 $NOT($_GET_foo)
,如果参数中包含 foo
,则返回 false
,否则返回true
。目前支持的变量有:
变量 | 含义 |
---|---|
$_IP |
客户端 IP |
$_HOST |
请求头中的 Host 字段 |
$_HOST_n |
$_HOST_n 指 Host 中的第 n 个子域,例如对于 foo.bar.baz.com:$_HOST_1 = foo,$_HOST_2 = bar,$_HOST_3 = baz |
$_GET_name |
使用 Query String 中的变量(无需 urldecode) |
$_POST_name |
使用 POST 表单中的变量(只支持 www form ) |
$_HEADER_name |
使用 Header 中的值,注意 name 全为小写 |
$_RSPHEADER_name |
使用响应头的 Header 中的值,使用时,整条规则最前面添加”!!”,例 !!xxxxxx$EQ($_RSPHEADER_Content-Type,audio/mp4a-latm) |
$_COOKIE_name |
使用 Cookie 中的字段值 |
$_STATUS |
使用响应状态码的值,使用时,整条规则最前面添加”!!”,例 !!xxxxxx$EQ($_STATUS, 404) |
$_RANDOM |
随机字符串,字符集为 [a-zA-Z0-9] ,默认 8 位 |
$_RANDOM_n |
n 位随机字符串,其中 1 <= n <= 32 |
$_URI |
请求的 URI,不包含参数 |
$_QUERY |
Query String,不带前缀 ‘?’ |
$_METHOD |
GET/PUT/POST/DELETE/OPTIONS/PATCH |
$_SCHEME |
http/https,注意此处全为小写 |
$_TIME |
获取当前服务器时间,格式为 UNIX TIME |
$_BODY |
获取当前请求的 BODY(请求体)内容,大小限制为 16KB |
$_GEOIP_COUNTRY_CODE |
国家代码,可参照维基百科: https://en.wikipedia.org/wiki/ISO_3166-2 |
字符串常量
字符串常量有两种形式,第一种就是普通的字符串例如/foo/bar
,但是如果字符串中包含了一些特殊字符,例如空白字符将被省略,例如 $(),'
这些字符有特殊的用途,不能被直接使用,要使用这些特殊的字符,要加 \
前缀对其转义,例如 /foo/bar\,
;第二种是加单引号的字符串 ''
,单引号中的字符只有 \
是特殊转义字符前缀,其他的都视为普通字符,例如这样一条改写规则 /foo/'$\\,\''
,改写过后对应 /foo/$\,'
。
break
除了能勾选 break 选项
指定是否 break
,也可以直接在边缘规则最后加上 $$
表示 break
。