On this page
Apache HTTP Server 中的表达式
历史上,Apache HTTP Server 的不同模块中用于表达条件的表达式有多种语法变体。目前正在进行一些努力,仅对所有配置指令使用一个名为* ap_expr 的变体。本文档介绍 ap_expr *表达式解析器。
- ap_expr *表达式旨在替换 HTTPD 中的大多数其他表达式变体。例如,不赞成使用的SSLRequire表达式可以替换为Require expr。
Backus-Naur 格式的语法
Backus-Naur Form(BNF)是无上下文语法的一种标记技术,通常用于描述计算中使用的语言的语法。在大多数情况下,表达式用于表示布尔值。对于这些,BNF 中的起点是expr
。但是,一些伪指令,例如LogMessage接受表达式,该表达式的结果为字符串值。对于这些,BNF 的起点是string
。
Note
expr ::= "true" | "false"
| "!" expr
| expr "&&" expr
| expr "||" expr
| "(" expr ")"
| comp
comp ::= stringcomp
| integercomp
| unaryop word
| word binaryop word
| word "in" "{" wordlist "}"
| word "in" listfunction
| word "=~" regex
| word "!~" regex
stringcomp ::= word "==" word
| word "!=" word
| word "<" word
| word "<=" word
| word ">" word
| word ">=" word
integercomp ::= word "-eq" word | word "eq" word
| word "-ne" word | word "ne" word
| word "-lt" word | word "lt" word
| word "-le" word | word "le" word
| word "-gt" word | word "gt" word
| word "-ge" word | word "ge" word
wordlist ::= word
| wordlist "," word
word ::= word "." word
| digit
| "'" string "'"
| """ string """
| variable
| rebackref
| function
string ::= stringpart
| string stringpart
stringpart ::= cstring
| variable
| rebackref
cstring ::= ...
digit ::= [0-9]+
variable ::= "%{" varname "}"
| "%{" funcname ":" funcargs "}"
rebackref ::= "$" [0-9]
function ::= funcname "(" word ")"
listfunction ::= listfuncname "(" word ")"
Variables
表达式解析器提供了许多形式为%{HTTP_HOST}
的变量。注意,变量的值可能取决于对其进行评估的请求处理的阶段。例如,在完成身份验证之前,先对<If >
指令中使用的表达式进行求值。因此,在这种情况下不会设置%{REMOTE_USER}
。
以下变量提供命名的 HTTP 请求 Headers 的值。其他 Headers 的值可以通过req
function获得。使用这些变量可能会导致将 Headers 名称添加到 HTTP 响应的 Vary Headers 中,除非在接受表达式的指令中另有说明。 req_novary
function可用于规避此行为。
Name |
---|
HTTP_ACCEPT |
HTTP_COOKIE |
HTTP_FORWARDED |
HTTP_HOST |
HTTP_PROXY_CONNECTION |
HTTP_REFERER |
HTTP_USER_AGENT |
其他与请求相关的变量
Name | Description |
---|---|
REQUEST_METHOD |
传入请求的 HTTP 方法(例如GET ) |
REQUEST_SCHEME |
请求 URI 的方案部分 |
REQUEST_URI |
请求 URI 的路径部分 |
DOCUMENT_URI |
与REQUEST_URI 相同 |
REQUEST_FILENAME |
如果已在引用REQUEST_FILENAME 时由服务器确定了与请求匹配的文件或脚本的完整本地文件系统路径。否则,例如在虚拟主机上下文中使用时,该值与REQUEST_URI |
SCRIPT_FILENAME |
与REQUEST_FILENAME 相同 |
LAST_MODIFIED |
如果文件在LAST_MODIFIED 时已由服务器确定,则以20101231235959 格式对文件的最后修改日期和时间进行参考。 |
SCRIPT_USER |
脚本所有者的用户名。 |
SCRIPT_GROUP |
脚本组的组名。 |
PATH_INFO |
尾随路径名信息,请参阅AcceptPathInfo |
QUERY_STRING |
当前请求的查询字符串 |
IS_SUBREQ |
如果当前请求是子请求,则为“ true ”,否则为“ false ” |
THE_REQUEST |
完整的请求行(例如“ GET /index.html HTTP/1.1 ”) |
REMOTE_ADDR |
远程主机的 IP 地址 |
REMOTE_PORT |
远程主机的端口(2.4.26 及更高版本) |
REMOTE_HOST |
远程主机的主机名 |
REMOTE_USER |
经过身份验证的用户的名称(如果有)(在<If> 期间不可用) |
REMOTE_IDENT |
mod_ident设置的用户名 |
SERVER_NAME |
当前虚拟主机的ServerName |
SERVER_PORT |
当前虚拟主机的服务器端口,请参阅ServerName |
SERVER_ADMIN |
当前虚拟主机的ServerAdmin |
SERVER_PROTOCOL |
请求使用的协议 |
DOCUMENT_ROOT |
当前虚拟主机的DocumentRoot |
AUTH_TYPE |
已配置的AuthType(例如“ basic ”) |
CONTENT_TYPE |
响应的 Content Type(在<If> 期间不可用) |
HANDLER |
handler创建响应的名称 |
HTTP2 |
“ on ”(如果请求使用 http/2),否则为“ off ” |
HTTPS |
如果请求使用 https,则为“ on ”,否则为“ off ” |
IPV6 |
如果连接使用 IPv6,则为“ on ”,否则为“ off ” |
REQUEST_STATUS |
请求的 HTTP 错误状态(在<If> 期间不可用) |
REQUEST_LOG_ID |
请求的错误日志 ID(请参见ErrorLogFormat) |
CONN_LOG_ID |
连接的错误日志 ID(请参阅ErrorLogFormat) |
CONN_REMOTE_ADDR |
连接的对等 IP 地址(请参见mod_remoteip模块) |
CONTEXT_PREFIX |
|
CONTEXT_DOCUMENT_ROOT |
Misc variables
Name | Description |
---|---|
TIME_YEAR |
当前年份(例如2010 ) |
TIME_MON |
当前月份(01 ,...,12 ) |
TIME_DAY |
该月的当前日期(01 ,...) |
TIME_HOUR |
当前时间的小时部分(00 ,...,23 ) |
TIME_MIN |
当前时间的分钟部分 |
TIME_SEC |
当前时间的第二部分 |
TIME_WDAY |
星期几(从0 到星期日开始) |
TIME |
日期和时间,格式为20101231235959 |
SERVER_SOFTWARE |
服务器版本字符串 |
API_VERSION |
API 版本的日期(模块幻数) |
某些模块会注册其他变量,请参见例如mod_ssl。
Binary operators
除某些内置比较运算符外,二进制运算符的格式为“ -[a-zA-Z][a-zA-Z0-9_]+
”,即减号和至少两个字符。名称不区分大小写。模块可以注册其他二进制运算符。
Comparison operators
Name | Alternative | Description |
---|---|---|
== |
= |
String equality |
!= |
String inequality | |
< |
字符串小于 | |
<= |
字符串小于或等于 | |
> |
字符串大于 | |
>= |
字符串大于或等于 | |
=~ |
字符串匹配正则表达式 | |
!~ |
字符串与正则表达式不匹配 | |
-eq |
eq |
Integer equality |
-ne |
ne |
Integer inequality |
-lt |
lt |
整数小于 |
-le |
le |
小于或等于整数 |
-gt |
gt |
整数大于 |
-ge |
ge |
大于或等于整数 |
其他二进制运算符
Name | Description |
---|---|
-ipmatch |
IP 地址与地址/网络掩码匹配 |
-strmatch |
左字符串匹配右字符串给定的模式(包含通配符*,?,[]) |
-strcmatch |
与-strmatch 相同,但不区分大小写 |
-fnmatch |
与-strmatch 相同,但斜杠与通配符不匹配 |
Unary operators
一元运算符采用一个参数,格式为“ -[a-zA-Z]
”,即减号和一个字符。名称*区分大小写。模块可以注册其他一元运算符。
Name | Description | Restricted |
---|---|---|
-d |
该参数被视为文件名。如果文件存在并且是目录,则为 True | yes |
-e |
该参数被视为文件名。如果文件(或目录或特殊文件)存在则为真 | yes |
-f |
该参数被视为文件名。如果文件存在且为常规文件,则为 True | yes |
-s |
该参数被视为文件名。如果文件存在且不为空,则为 True | yes |
-L |
该参数被视为文件名。如果文件存在且为符号链接,则为 true | yes |
-h |
该参数被视为文件名。如果文件存在且为符号链接(与-L 相同),则为 True。 |
yes |
-F |
如果 string 是有效文件,则为 true,可通过该路径的所有服务器当前配置的访问控制进行访问。这使用内部子请求进行检查,因此请谨慎使用-它可能会影响服务器的性能! | |
-U |
如果 string 是有效的 URL,则为 true,可通过该路径的所有服务器当前配置的访问控制来访问。这使用内部子请求进行检查,因此请谨慎使用-它可能会影响服务器的性能! | |
-A |
-U 的别名 |
|
-n |
如果字符串不为空,则为真 | |
-z |
如果字符串为空则为真 | |
-T |
如果字符串为空,“ 0 ”,“ off ”,“ false ”或“ no ”(不区分大小写),则为 False。否则为真。 |
|
-R |
与“ %{REMOTE_ADDR} -ipmatch ... ”相同,但效率更高 |
标记为“受限”的运算符在mod_include之类的某些模块中不可用。
Functions
普通的字符串值函数将一个字符串作为参数并返回一个字符串。函数名称不区分大小写。模块可以注册其他功能。
Name | Description | Special notes |
---|---|---|
req , http |
获取 HTTP 请求头;Headers 名称可以添加到 Vary Headers 中,请参见下文 | |
req_novary |
与req 相同,但 Headers 名称不会添加到 Vary Headers 中 |
|
resp |
获取 HTTP 响应 Headers(大多数响应 Headers 在<If> 期间尚未设置) |
|
reqenv |
查找请求环境变量(作为快捷方式,v 也可用于访问变量)。 |
ordering |
osenv |
查找 os 环境变量 | |
note |
查找请求说明 | ordering |
env |
返回第一个匹配项note ,reqenv ,osenv |
ordering |
tolower |
将字符串转换为小写 | |
toupper |
将字符串转换为大写 | |
escape |
以%hex 编码转义特殊字符 | |
unescape |
不转义%hex 编码的字符串,仅保留编码的斜杠;如果找到%00,则返回空字符串 | |
base64 |
使用 base64 编码对字符串进行编码 | |
unbase64 |
解码 base64 编码的字符串,如果找到 0x00,则返回截断的字符串 | |
md5 |
使用 MD5 哈希字符串,然后使用十六进制编码对哈希进行编码 | |
sha1 |
使用 SHA1 哈希字符串,然后使用十六进制编码对哈希进行编码 | |
file |
从文件读取内容(包括行尾,如果存在) | restricted |
filemod |
返回文件的最后修改时间(如果文件不存在或不是常规文件,则返回 0) | restricted |
filesize |
返回文件的大小(如果文件不存在或不是常规文件,则返回 0) | restricted |
在最后一栏中标记为“受限”的功能在mod_include之类的某些模块中不可用。
在最后一栏中标记为“ ordering”的功能需要对服务器的不同组件的 Sequences 进行一些考虑,尤其是在<If>指令中使用该功能时,该指令的评估相对较早。
Environment variable ordering
使用函数req
或http
时,Headers 名称将自动添加到 HTTP 响应的 Vary Headers 中,除非在接受表达式的指令中另有说明。 req_novary
函数可用于防止将名称添加到 Vary Headers 中。
除了字符串值函数外,还有一些列表值函数,它们将一个字符串作为参数并返回一个单词列表,即一个字符串列表。单词表可以与特殊的-in
运算符一起使用。函数名称不区分大小写。模块可以注册其他功能。
没有内置的列表值函数。 mod_ssl提供PeerExtList
。有关详细信息,请参见SSLRequire的描述(但SSLRequire之外也可以使用PeerExtList
)。
Example expressions
以下示例说明如何使用表达式评估请求:
# Compare the host name to example.com and redirect to www.example.com if it matches
<If "%{HTTP_HOST} == 'example.com'">
Redirect permanent "/" "http://www.example.com/"
</If>
# Force text/plain if requesting a file with the query string contains 'forcetext'
<If "%{QUERY_STRING} =~ /forcetext/">
ForceType text/plain
</If>
# Only allow access to this content during business hours
<Directory "/foo/bar/business">
Require expr %{TIME_HOUR} -gt 9 && %{TIME_HOUR} -lt 17
</Directory>
# Check a HTTP header for a list of values
<If "%{HTTP:X-example-header} in { 'foo', 'bar', 'baz' }">
Header set matched true
</If>
# Check an environment variable for a regular expression, negated.
<If "! reqenv('REDIRECT_FOO') =~ /bar/">
Header set matched true
</If>
# Check result of URI mapping by running in Directory context with -f
<Directory "/var/www">
AddEncoding x-gzip gz
<If "-f '%{REQUEST_FILENAME}.unzipme' && ! %{HTTP:Accept-Encoding} =~ /gzip/">
SetOutputFilter INFLATE
</If>
</Directory>
# Check against the client IP
<If "-R '192.168.1.0/24'">
Header set matched true
</If>
# Function example in boolean context
<If "md5('foo') == 'acbd18db4cc2f85cedef654fccc4a4d8'">
Header set checksum-matched true
</If>
# Function example in string context
Header set foo-checksum "expr=%{md5:foo}"
# This delays the evaluation of the condition clause compared to <If>
Header always set CustomHeader my-value "expr=%{REQUEST_URI} =~ m#^/special_path\.php$#"
# Conditional logging
CustomLog logs/access-errors.log common "expr=%{REQUEST_STATUS} >= 400"
CustomLog logs/access-errors-specific.log common "expr=%{REQUEST_STATUS} -in {'405','410'}"
Other
Name | Alternative | Description |
---|---|---|
-in |
in |
单词表中包含的字符串 |
/regexp/ |
m#regexp# |
正则表达式(第二种形式允许使用与/不同的分隔符) |
/regexp/i |
m#regexp#i |
不区分大小写的正则表达式 |
$0 ... $9 |
正则表达式反向引用 |
正则表达式反向引用
字符串$0
... $9
允许引用先前执行的,成功匹配正则表达式的捕获组。通常,它们只能与匹配的正则表达式在同一表达式中使用,但是某些模块允许特殊用途。
与 SSLRequire 比较
- ap_expr *语法主要是已弃用的SSLRequire指令的语法的超集。差异在SSLRequire的文档中进行了描述。
Version History
req_novary
function可用于 2.4.4 和更高版本。