I have a website that uses the same core .htaccess
details as many other websites; however this website does not properly load the .htaccess
directives -- giving a basic HTTP header set of:
HTTP/1.1 200 OK
Date: Mon, 12 Nov 2018 09:34:28 GMT
Server: Apache
Keep-Alive: timeout=5, max=100
Connection: Keep-Alive
Transfer-Encoding: chunked
Content-Type: text/html; charset=UTF-8
The website itself loads fine, but additonal headers in .htaccess are not being agknowledged / loaded.
.htaccess
is being read, right?Yes -- The htaccess file contains HTTPS forced redirects and domain name redirects (from the .co.uk to .com address (both to the same website account))
These work.
The PHP headers on a test page are loading just fine:
<?php
header("Cache-Control: no-cache, must-revalidate");
header('Content-Type: text/html; charset=utf-8');
header("X-Clacks-Overhead: GNU Terry Pratchett");
header("Content-Language: en");
header("X-XSS-Protection: 1; mode=block");
header("X-Frame-Options: SAMEORIGIN");
header("X-Content-Type-Options: nosniff");
?>
But the same headers set in the .htaccess
are not being agknowledged.
.htaccess
syntax error!Not that I can see; usually with a .htaccess error the site loads an HTTP-500 error message, however here the site loads in the browser without issue.
When there IS a deliberate syntax error the error-500 HTTP response comes back as expected.
Absolutely; I couldn't agree more. The Apache error logs are empty!
httpd.conf
allows reading of .htaccess
.htaccess
has the correct permissins (0644)Here:
Options +FollowSymLinks
Options -Indexes
RewriteEngine On
ErrorDocument 404 /index.php?msg=404
ErrorDocument 403 /index.php?msg=403
#Set asset items to cache for 1 week.
<FilesMatch "\.(gif|jpe?g|png|ico|css|js|swf|mp3)$">
Header set Cache-Control "max-age=1972800, public, must-revalidate"
</FilesMatch>
RewriteCond %{HTTPS} !=on
RewriteRule ^ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
## This does not appear to work (for either)
#Header always set Strict-Transport-Security "max-age=31536000;" env=HTTPS
Header always set Strict-Transport-Security "max-age=31536000; includeSubdomains;" "expr=%{HTTPS} == 'on'"
Header set Expect-CT enforce,max-age=2592000
RewriteCond %{HTTP_HOST} ^(www\.)?thewebsite\.co\.uk$ [NC]
RewriteRule ^/?(.*)$ https://www.thewebsite.com%{REQUEST_URI} [R=301,L]
###
##### Seems to workdown to roughly this point.
###
#force requests to begin with a slash.
RewriteCond %{REQUEST_URI} !^$
RewriteCond %{REQUEST_URI} !^/
RewriteRule .* - [R=403,L]
RewriteCond %{HTTP_HOST} !^$
RewriteCond %{HTTP_HOST} !^www\. [NC]
RewriteRule ^ https://www.%{HTTP_HOST}%{REQUEST_URI} [R=301,L]
RewriteCond %{ENV:REDIRECT_STATUS} 200
RewriteRule .* - [L]
### This file does not exist on the directory at present.
<Files .account-user.ini>
order allow,deny
deny from all
</Files>
###
#### None of these appear on assessment tools such as Security Headers
#### Or redbot.
###
Header set Cache-Control no-cache,must-revalidate
Header set X-Clacks-Overhead "GNU Terry Pratchett"
Header set X-XSS-Protection 1;mode=block
Header set X-Content-Type-Options nosniff
Header always set X-Frame-Options SAMEORIGIN
Header set Expect-CT enforce,max-age=2592000
Header set Content-Language en
Header set Referrer-Policy origin-when-cross-origin
<LimitExcept GET POST HEAD>
deny from all
</LimitExcept>
.htaccess
do not appear to work..htaccess
..htaccess
is being read by Apache because other commands (such as mod_Rewrite
s) are being actionedFrom research by other parties (the hosting providers) it seems that somehow the .htaccess
works and loads all the correct headers for non PHP pages.
For even plain PHP pages; the headers are blank.
Clarification
Header("...");
.htaccess
. This is the problem.So it looks like my
.htaccess
can't set headers for PHP pages. How can I fix this?
Improper syntax being used It is quite common for a syntax error to be the reason for an . htaccess file not working. If you are familiar with how to read and configure . htaccess rules, double check your configuration.
Save the file and type the URL yoursite.com/foobar/ . If the reditect works and the URL gets redireted to the homepage of example.com then it's clear that your htaccess is working and being read by your Apache server. If it still doesn't work then the problem might be that your hosting provider has not enabled it.
htaccess file can be found at /opt/bitnami/APPNAME/. htaccess. Some applications do not have the /opt/bitnami/apache2/conf/vhosts/htaccess/APPNAME-htaccess.
It seems that PHP ignores headers defined in .htaccess when working as a FastCGI module.
There are a lot of suggestions how to fix this. In your case I would recommend to have a file that defines all your headers
<?php
// file headers.php
header('Cache-Control: no-cache,must-revalidate');
header('X-Clacks-Overhead: "GNU Terry Pratchett"');
header('X-XSS-Protection: 1;mode=block');
header('X-Content-Type-Options: nosniff');
header('X-Frame-Options: SAMEORIGIN');
header('Expect-CT: enforce,max-age=2592000');
header('Content-Language: en');
header('Referrer-Policy: origin-when-cross-origin');
?>
and save it to your DocumentRoot directory. Then add this entry to your .htaccess file to include it with every request:
php_value auto_prepend_file /var/www/html/headers.php
Testing it:
<?php
// file test.php
die("hello world");
?>
And the headers are being sent:
$ curl -I ubuntu-server.lan/test.php
HTTP/1.1 200 OK
Date: Sun, 25 Nov 2018 09:37:52 GMT
Server: Apache/2.4.18 (Ubuntu)
Cache-Control: no-cache,must-revalidate
X-Clacks-Overhead: "GNU Terry Pratchett"
X-XSS-Protection: 1;mode=block
X-Content-Type-Options: nosniff
X-Frame-Options: SAMEORIGIN
Expect-CT: enforce,max-age=2592000
Content-Language: en
Referrer-Policy: origin-when-cross-origin
Content-Type: text/html; charset=UTF-8
Always keep in mind that when you change headers in .htaccess to also change them in headers.php.
Hope this helps!
I think this problem results from the httpd/apache2 headers_module
not being loaded correctly (although you state otherwise in one of the above comments). You can check this by executing this command in the terminal:
apachectl -M | grep headers_module
If you get no output headers_module (shared)
(or similar), then you have to activate the httpd/apache2 headers module. On a CentOS system you have to load the respective source file in your configuration (default /etc/httpd/conf/httpd.conf
).
You have to add this line
LoadModule headers_module /usr/lib/apache2/modules/mod_headers.so
and then restart the http server wih sudo systemctl restart httpd.service
With EasyApache 4 the folder where httpd/apache2 modules are located might differ and be /usr/lib64/apache2/modules/
.
I hope this helps!
It is not so much FastCGI as it is mod_proxy_fcgi, the method of asking Apache to "execute" FastCGI by passing it to some other listener.
When you use any mod_proxy* module, .htaccess isn't processed at all, because you're acting as a proxy and short-circuiting any disk-related configuration sections.
php-fpm will be looking at the request URL and reading data from disk, but Apache isn't. It is just confusing to people because they can be running on the same host and the files are often in a directory httpd could serve directly.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With