• 首页
  • vue
  • TypeScript
  • JavaScript
  • scss
  • css3
  • html5
  • php
  • MySQL
  • redis
  • jQuery
  • Apache 中的表达式

    从历史上看,有几种表达式的语法变体用于表示 Apache HTTP Server 的不同模块中的条件。目前正在努力仅为所有 configuration 指令使用一个名为 ap_expr 的变体。本文档描述了 ap_expr 表达式解析器。

    ap_expr 表达式旨在替换 HTTPD 中的大多数其他表达式变体。对于 example,不推荐使用的SSLRequire表达式可以替换为要求 expr。

    语法 Backus-Naur 表格符号

    Backus-Naur 表格(BNF)是 context-free 语法的表示法技术,通常用于描述计算中使用的语言的语法。在大多数情况下,表达式用于表示 boolean 值。对于这些,BNF 的起点是expr。但是,像LogMessage这样的一些指令会接受求值为 string value 的表达式。对于那些人来说,BNF 的起点是string

    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 ")"
    

    变量

    表达式解析器提供了多个%{HTTP_HOST}形式的变量。请注意,变量的 value 可能取决于评估它的请求处理的阶段。对于 example,在完成身份验证之前会评估<If >指令中使用的表达式。因此,在这种情况下不会设置%{REMOTE_USER}

    以下变量提供了命名的 HTTP 请求 headers 的值。可以使用req功能获取其他 headers 的值。使用这些变量可能会导致 header name 被添加到 HTTP 响应的 Vary 标头中,除非接受表达式的指令另有说明。req_novary功能可用于规避此行为。

    名称
    HTTP_ACCEPT
    HTTP_COOKIE
    HTTP_FORWARDED
    HTTP_HOST
    HTTP_PROXY_CONNECTION
    HTTP_REFERER
    HTTP_USER_AGENT

    其他请求相关变量

    名称描述
    REQUEST_METHOD传入请求的 HTTP 方法(e.g.GET)
    REQUEST_SCHEME请求的 URI 的 scheme 部分
    REQUEST_URI请求的 URI 的路径部分
    DOCUMENT_URIREQUEST_URI相同
    REQUEST_FILENAME如果已经由 time REQUEST_FILENAME处的服务器确定了该请求的文件或脚本的完整本地文件系统路径,则引用该路径。否则,例如在虚拟 host context 中使用时,_val与REQUEST_URI相同
    SCRIPT_FILENAMEREQUEST_FILENAME相同
    LAST_MODIFIED如果已经由 time LAST_MODIFIED处的服务器确定,则以20101231235959格式对文件进行最后修改的 date 和 time 被引用。
    SCRIPT_USER脚本所有者的用户 name。
    SCRIPT_GROUP脚本 group 的 group name。
    PATH_INFO尾随路径 name 信息,请参阅中的 AcceptPathInfo
    QUERY_STRING查询当前请求的 string
    IS_SUBREQtrue”如果当前请求是子请求,否则为“false
    THE_REQUEST完整的请求 line(e.g.,“GET /index.html HTTP/1.1”)
    REMOTE_ADDRremote host 的 IP 地址
    REMOTE_PORTremote host 的 port(2.4.26 及更高版本)
    REMOTE_HOSTremote host 的 host name
    REMOTE_USER经过身份验证的用户的 name(如果有)(在<If>期间不可用)
    REMOTE_IDENT由mod_ident设置的用户 name
    SERVER_NAME当前 vhost 的服务器名称
    SERVER_PORT当前 vhost 的 server port,请参见服务器名称
    SERVER_ADMIN当前 vhost 的ServerAdmin
    SERVER_PROTOCOL请求使用的协议
    DOCUMENT_ROOT当前 vhost 的DocumentRoot
    AUTH_TYPE配置进行 AuthType(e.g.“basic”)
    CONTENT_TYPE响应的 content type(在<If>期间不可用)
    HANDLER处理器的创建响应的 name
    HTTP2如果请求使用 http/2,则为“on”,否则为“off
    HTTPS如果请求使用 https,则为“on”,否则为“off
    IPV6如果连接使用 IPv6 则为“on”,否则为“off
    REQUEST_STATUS请求的 HTTP 错误状态(在<If>期间不可用)
    REQUEST_LOG_ID请求的错误 log id(请参阅ErrorLogFormat)
    CONN_LOG_ID连接的错误 log id(请参阅ErrorLogFormat)
    CONN_REMOTE_ADDR连接的对等 IP 地址(参见modremoteip模块)
    CONTEXT_PREFIX
    CONTEXT_DOCUMENT_ROOT

    其他变量

    名称描述
    TIME_YEAR当年(e.g .2010)
    TIME_MON当前月份(01,...,12)
    TIME_DAY当月的当天(01,...)
    TIME_HOUR当前 time 的小时部分(00,...,23)
    TIME_MIN当前 time 的分钟部分
    TIME_SEC当前 time 的第二部分
    TIME_WDAY一周中的某一天(周日0开头)
    TIME格式为20101231235959的 date 和 time
    SERVER_SOFTWARE服务器 version string
    API_VERSIONAPI version 的 date(模块幻数)

    一些模块注册其他变量,请参见 mod_ssl。

    二进制操作员

    对于某些 built-in 比较 operators 的 exception,binary operators 的形式为“-[a-zA-Z][a-zA-Z0-9_]+”,i.e。一个减号和至少两个字符。 name 不区分大小写。模块可以注册其他二进制 operators。

    比较 operators

    名称替代描述
    ===String 等于
    !=String 不等式
    <String 小于
    <=String 小于或等于
    >String 大于
    >=String 大于或等于
    =~String 匹配正则表达式
    !~String 不匹配正则表达式
    -eqeqInteger 平等
    -neneInteger 不等式
    -ltltInteger 小于
    -leleInteger 小于或等于
    -gtgtInteger 大于
    -gegeInteger 大于或等于

    其他二进制 operators

    名称描述
    -ipmatchIP 地址匹配 address/netmask
    -strmatchleft string 匹配右 string 给出的 pattern(包含通配符*,?,[152])
    -strcmatch-strmatch相同,但不区分大小写
    -fnmatch-strmatch相同,但斜线与通配符不匹配

    一元操作员

    一元 operators 采用一个参数,形式为“-[a-zA-Z]”,i.e。一个减号和一个字符。 name 区分大小写。模块可以注册其他一元运算符。

    名称描述受限
    -d该参数被视为文件名。 True 如果文件存在且是目录
    -e该参数被视为文件名。 True 如果文件(或目录或特殊)存在
    -f该参数被视为文件名。 True 如果文件存在且是常规文件
    -s该参数被视为文件名。 True 如果文件存在且不为空
    -L该参数被视为文件名。 True 如果文件存在且是符号链接
    -h该参数被视为文件名。 True 如果文件存在且是符号链接(与-L相同)
    -FTrue 如果 string 是一个有效文件,可以通过该路径的所有服务器的 currently-configured 访问控制访问。这使用内部子请求来进行检查,因此请小心使用它- 它会影响服务器的 performance!
    -UTrue 如果 string 是一个有效的 URL,可以通过该路径的所有服务器的 currently-configured 访问控制访问。这使用内部子请求来进行检查,因此请小心使用它- 它会影响服务器的 performance!
    -A-U的别名
    -nTrue 如果 string 不为空
    -zTrue 如果 string 为空
    -TFalse 如果 string 为空,“0”,“off”,“false”或“no”(不区分大小写)。 True 否则。
    -R与“%{REMOTE_ADDR}-ipmatch ...”相同,但效率更高

    标记为“受限制”的 operators 在mod_include等某些模块中不可用。

    功能

    普通 string-valued 函数将一个 string 作为参数,return 一个 string。函数名称不区分大小写。模块可以注册其他功能。

    名称描述特别说明
    req, http获取 HTTP 请求标头;标题名称可以添加到 Vary 标题,见下文
    req_novaryreq相同,但标题名称不会添加到 Vary 标头中
    resp获取 HTTP 响应标头(在<If>期间,大多数响应 headers 尚未设置)
    reqenv查找请求环境变量(作为快捷方式,v也可用于访问变量)。ordering
    osenv查找操作系统环境变量
    note查询请求备注ordering
    env返回notereqenvosenv的第一个 matchordering
    tolower将 string 转换为小写
    toupper将 string 转换为大写
    escape以%十六进制编码转义特殊字符
    unescapeUnescape%十六进制编码 string,只留下编码斜线;如果找到%00,return empty string
    base64使用 base64 编码对 string 进行编码
    unbase64如果找到 0x00,则解码 base64 编码的 string,return 截断的 string
    md5使用 MD5 散列 string,然后使用十六进制编码对散列进行编码
    sha1使用 SHA1 散列 string,然后使用十六进制编码对散列进行编码
    file从文件中读取内容(包括 line 结尾,如果存在)限制
    filemod返回文件的最后修改 time(如果文件不存在或者不是常规文件,则返回 0)限制
    filesize返回文件的大小(如果文件不存在或者不是常规文件,则返回 0)限制

    最终列中标记为“受限制”的功能在mod_include等某些模块中不可用。

    在最后一列中标记为“ordering”的函数需要考虑服务器的不同组件的 ordering,尤其是在<1>指令中使用 function 时,相对较早地进行评估。

    环境变量 ordering

    当在<如果>条件中查找环境变量时,重要的是要考虑在此请求处理过早发生此解决方案的时间。作为指导原则,在虚拟 host context(目录,位置,htaccess)之外定义的任何指令都不太可能有机会执行。虚拟 host 范围中的SetEnvIf 之后是在此解决方案之前运行的一个指令

    当在<如果>之外使用reqenv时,分辨率通常会在稍后发生,但确切的时间取决于表达式在其中使用的指令。

    当使用函数reqhttp时,标题 name 将自动添加到 HTTP 响应的 Vary 标头中,除非接受表达式的指令另有说明。req_novary function 可用于防止将名称添加到 Vary 标头中。

    除了 string-valued 函数之外,还有 list-valued 函数,它们将一个 string 作为参数并_返回一个 wordlist,i.e。 strings 列表。 wordlist 可以与特殊的-in operator 一起使用。函数名称不区分大小写。模块可以注册其他功能。

    没有 built-in list-valued 函数。 mod_ssl提供PeerExtList。有关详细信息,请参阅SSLRequire的说明(但PeerExtList也可在SSLRequire之外使用)。

    Example 表达式

    以下示例显示了如何使用表达式来评估请求:

    # 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'}"
    

    其他

    名称替代描述
    -ininwordlist 中包含 string
    /regexp/m#regexp#正则表达式(第二种形式允许与/)不同的分隔符
    /regexp/im#regexp#i不区分大小写的正则表达式
    $0 ...$9正则表达式反向引用

    正则表达式反向引用

    strings $0...$9允许从先前执行的,成功匹配的正则表达式中引用捕获组。它们通常只能在与匹配的正则表达式相同的表达式中使用,但某些模块允许特殊用途。

    与 SSLRequire 的比较

    ap_expr 语法主要是不推荐使用的SSLRequire指令语法的超集。差异在SSLRequire的文档中描述。

    Version History

    req_novary功能适用于 2.4.4 及更高版本。

    上篇:处理器