The <If> directive in Apache allows for conditional execution of configuration directives based on server variables. The correct syntax requires careful attention to expression formatting:
<If "%{VARIABLE_NAME} =~ /pattern/"> # Configuration here </If>
Here are several practical implementations that work in .htaccess files:
1. Checking Request Method
<If "%{REQUEST_METHOD} in ['GET','HEAD','OPTIONS']"> Header set X-Method-Valid "true" </If>
2. Port-Based Configuration
The original question had an incorrect port check example. Here's the proper way:
<If "%{SERVER_PORT} == '80'"> RewriteEngine On RewriteCond %{HTTPS} off RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301] </If>
The error in the original question occurred because:
- SERVER_PORT was checked against HTTP methods (invalid comparison)
- Missing quotes around the comparison value
- Possible missing expression delimiters
For more complex scenarios:
<If "(%{HTTP_HOST} =~ /example\.com/) && (%{HTTPS} != 'on')"> RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301] </If>
- Always wrap expressions in double quotes
- Use proper comparison operators: ==, !=, <, >, =~ (regex match)
- For string lists, use square brackets: ['value1','value2']
- Combine conditions with && (AND) or || (OR)
- Verify AllowOverride includes FileInfo (required for <If> directives)
- Check Apache error logs for specific syntax errors
- Test with simpler conditions first
- Ensure you're using Apache 2.4+ (earlier versions don't support this syntax)
The <If>
directive in Apache's .htaccess allows for conditional execution of configuration directives based on various server variables. Unlike IfDefine
or IfModule
, it evaluates expressions at request time.
Your example contains a logical error - comparing SERVER_PORT
(which is numeric) with HTTP methods. Here's the correct way to check request methods:
<If "%{REQUEST_METHOD} in ['GET','HEAD','OPTIONS']"> # Configuration for safe methods Header set X-Safe-Method "true" </If>
For port checking (which appears to be what you intended):
<If "%{SERVER_PORT} == 80"> RewriteRule ^(.*)$ https://example.com/$1 [R=301,L] </If>
The 500 error you encountered typically occurs when:
- Using incorrect expression syntax (missing quotes, wrong operators)
- Comparing incompatible variable types
- Having unclosed
<If>
blocks
Combine multiple conditions:
<If "%{REQUEST_URI} =~ /\.php$/ && %{QUERY_STRING} =~ /debug=1/"> php_flag display_errors on </If>
Check request headers:
<If "%{HTTP_USER_AGENT} =~ /Mobile/"> RewriteRule ^(.*)$ /mobile/$1 [L] </If>
While powerful, overusing <If>
can impact performance. For static conditions, consider:
IfModule
for module availability checksIfDefine
for build-time conditions- Environment variables for complex logic
Always test .htaccess changes gradually. Use:
apachectl configtest
Or check error logs for specific syntax errors when encountering 500 errors.