htaccess If ... Else总是选择Else

Bee*_*ice 16 apache .htaccess environment-variables apache2.4

我在httpd-vhosts.conf中设置了一个环境变量

SetEnv EARLY_VAR 1
Run Code Online (Sandbox Code Playgroud)

我尝试根据它在.htaccess中的值设置特殊规则

<If "%{ENV:EARLY_VAR} == '1'">
   SetEnv TEST_VAR  if_branch
</If>
<Else>
    SetEnv TEST_VAR  else_branch
</Else>
Run Code Online (Sandbox Code Playgroud)

我希望TEST_VAR环境变量相等if_branch.在PHP中

var_dump(getenv('EARLY_VAR')); // string '1'
var_dump(getenv('TEST_VAR')); // string 'else_branch'
Run Code Online (Sandbox Code Playgroud)

我也尝试EARLY_VAR.htaccessIf/Else上面设置,使用SetEnvSetEnvIf.始终执行Else分支.

为什么是这样?

Apache 2.4

anu*_*ava 7

不使用表达式即if/else指令,您可以这样做:

# set EARLY_VAR to 1
SetEnvIf Host ^ EARLY_VAR=1

# if EARLY_VAR is 1 then set TEST_VAR to if_branch
SetEnvIf EARLY_VAR ^1$ TEST_VAR=if_branch

# if EARLY_VAR is NOT 1 then set TEST_VAR to else_branch
SetEnvIf EARLY_VAR ^(?!1$) TEST_VAR=else_branch
Run Code Online (Sandbox Code Playgroud)

这适用于更老的Apache版本,即 <2.4


编辑:

在你的Apache配置或vhost配置中有这个变量初始化:

SetEnvIf Host ^ EARLY_VAR=5
Run Code Online (Sandbox Code Playgroud)

然后在你的.htaccess中你可以使用:

<If "env('EARLY_VAR') == '5'">
   SetEnv TEST_VAR if_branch
</If>
<Else>
   SetEnv TEST_VAR else_branch
</Else>
Run Code Online (Sandbox Code Playgroud)

在Apache/vhost配置中需要env变量声明的原因是因为.htaccess是在Apache/vhost配置和在同一.htaccess中设置的env变量之后加载的,因此无法在if/else表达式中进行评估.

另请注意,使用SetEnvIf而不是SetEnv使这些变量可用于if/else表达式非常重要.


hjp*_*r92 5

看一下SetEnv指令的文档,我注意到:

设置内部环境变量,然后可供Apache HTTP Server模块使用,并传递给CGI脚本和SSI页面.

这意味着环境可供其他模块使用.然而,<if>指令由核心提供.如果您在<if>子句期间尝试查看环境是否为空,则可以确认:

<If "-z %{ENV:EARLY_VAR}">
   SetEnv TEST_VAR  if_branch
</If>
Run Code Online (Sandbox Code Playgroud)

要么

<If "-z env('EARLY_VAR')">
   SetEnv TEST_VAR  if_branch
</If>
Run Code Online (Sandbox Code Playgroud)

两者都会给你:

string(1) "1" string(9) "if_branch" 
Run Code Online (Sandbox Code Playgroud)

在你的PHP中.


Apache的环境变量wiki/docs页面上还列出了以下警告:

SetEnv指令在请求处理期间运行较晚,这意味着指令例如SetEnvIf并且RewriteCond不会看到使用它设置的变量.