Skip to content

Instantly share code, notes, and snippets.

@rohankhudedev
Last active July 4, 2023 01:26
Show Gist options
  • Star 3 You must be signed in to star a gist
  • Fork 3 You must be signed in to fork a gist
  • Save rohankhudedev/ef94d6cf4322faf18535754a105ef897 to your computer and use it in GitHub Desktop.
Save rohankhudedev/ef94d6cf4322faf18535754a105ef897 to your computer and use it in GitHub Desktop.
Necessary Apache .htaccess Configuration: Performance and Security settings
## ~-~-~- How to use ~-~-~-
# You can directly download as use as it is.
# Everything is listed is only perfomance and security related lines
# Validate .htaccess from http://www.htaccesscheck.com/
# Disable Directory Browsing: Security
Options All -Indexes
# If a dir is a symbol link, follow the link
Options +FollowSymLinks
# Disable multiviews
# Ref - https://stackoverflow.com/questions/25423141/what-exactly-does-the-multiviews-options-in-htaccess/25423722
<IfModule mod_negotiation.c>
Options -MultiViews
</IfModule>
# https://stackoverflow.com/questions/4026021/remove-php-extension-with-htaccess
#RewriteEngine on
#RewriteCond %{REQUEST_FILENAME}.php -f
#RewriteRule !.*\.php$ %{REQUEST_FILENAME}.php [QSA,L]
# Set Timezone of the Server (GMT)
# SetEnv TZ Asia/Kolkata
## Add a "en-US" language header and "UTF-8" without meta tags!
# Use UTF-8 encoding for anything served text/plain or text/html
AddDefaultCharset utf-8
# Force UTF-8 for a number of file formats
AddCharset utf-8 .atom .css .js .json .rss .vtt .xml
DefaultLanguage en-US
# Enable basic rewriting
RewriteEngine on
# Disable HTTP Trace
RewriteCond %{REQUEST_METHOD} ^TRACE
RewriteRule ^ - [F]
# This is must to implement https
RewriteCond %{HTTPS} off
# Forcing HTTPS on All Traffic
RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
# --------- Force redirect http to https://www
RewriteCond %{HTTPS} off
# First rewrite to HTTPS:
# Don't put www. here. If it is already there it will be included, if not
# the subsequent rule will catch it.
RewriteRule .* https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
# Now, rewrite any request to the wrong domain to use www.
# [NC] is a case-insensitive match
RewriteCond %{HTTP_HOST} !^www\. [NC]
RewriteRule .* https://www.%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
# ---------
#----------------------------------------------------------------------------OR------------------------------------------------
# --------- Force redirect http with www or without www to https://
# Remove www from url directories
RewriteCond %{HTTP_HOST} ^www\.(.*)$ [NC]
RewriteRule ^(.*)$ https://%1%{REQUEST_URI} [R=301,QSA,NC,L]
RewriteCond %{HTTPS} off
RewriteRule ^(.*)$ https://%{HTTP_HOST}%{REQUEST_URI} [L,R=301]
# ---------
<IfModule mod_mime.c>
AddCharset utf-8 .atom \
.bbaw \
.css \
.geojson \
.ics \
.js \
.json \
.jsonld \
.manifest \
.markdown \
.md \
.mjs \
.rdf \
.rss \
.topojson \
.vtt \
.webapp \
.webmanifest \
.xloc \
.xml
# Audio
AddType audio/mp4 m4a f4a f4b
AddType audio/mpeg mp3
AddType audio/ogg oga ogg opus
AddType audio/wav wav
AddType audio/webm webma
# Data interchange
AddType application/json json map
AddType application/ld+json jsonld
# JavaScript
# Normalize to standard type.
# http://tools.ietf.org/html/rfc4329#section-7.2
AddType application/javascript js jsonp
# Video
AddType video/mp4 f4v f4p m4v mp4
AddType video/ogg ogv
AddType video/webm webm
AddType video/x-flv flv
# Web fonts
AddType application/vnd.ms-fontobject .eot
AddType application/x-font-opentype .otf
AddType application/x-font-ttf ttc ttf
AddType application/font-woff .woff
AddType application/font-woff2 .woff2
AddType application/x-font-woff woff
AddType font/opentype otf
# Make SVGZ fonts work on the iPad.
# https://twitter.com/FontSquirrel/status/14855840545
AddType image/svg+xml svg svgz
AddEncoding gzip svgz
# Other
AddType application/octet-stream safariextz
AddType application/x-chrome-extension crx
AddType application/x-opera-extension oex
AddType application/x-web-app-manifest+json webapp
AddType application/x-xpinstall xpi
AddType application/xml atom rdf rss xml
AddType image/webp webp
AddType image/x-icon ico
AddType image/vnd.microsoft.icon ico
AddType text/cache-manifest appcache manifest
AddType text/css css
AddType image/svg+xml svg
AddType text/vtt vtt
AddType text/x-component htc
AddType text/x-vcard vcf
AddType application/vnd.openxmlformats .docx .pptx .xlsx .xltx . xltm .dotx .potx .ppsx
AddType application/manifest+json .webmanifest
AddType application/x-shockwave-flash swf
</IfModule>
#------------------------------
# Allow Cross-Domain Fonts
# CDN-served webfonts might not work in Firefox or IE due to CORS. This snippet solves the problem.
<IfModule mod_headers.c>
<FilesMatch "\.(eot|otf|ttc|ttf|woff|woff2)$">
Header set Access-Control-Allow-Origin "*"
</FilesMatch>
</IfModule>
# Enable Compression
<IfModule mod_deflate.c>
# Force compression for mangled headers.
# https://developer.yahoo.com/blogs/ydn/pushing-beyond-gzipping-25601.html
<IfModule mod_setenvif.c>
<IfModule mod_headers.c>
SetEnvIfNoCase ^(Accept-EncodXng|X-cept-Encoding|X{15}|~{15}|-{15})$ ^((gzip|deflate)\s*,?\s*)+|[X~-]{4,13}$ HAVE_Accept-Encoding
RequestHeader append Accept-Encoding "gzip,deflate" env=HAVE_Accept-Encoding
</IfModule>
</IfModule>
AddOutputFilterByType DEFLATE application/javascript
AddOutputFilterByType DEFLATE application/rss+xml
AddOutputFilterByType DEFLATE application/vnd.ms-fontobject
AddOutputFilterByType DEFLATE application/x-font
AddOutputFilterByType DEFLATE application/x-font-opentype
AddOutputFilterByType DEFLATE application/x-font-otf
AddOutputFilterByType DEFLATE application/x-font-truetype
AddOutputFilterByType DEFLATE application/x-font-ttf
AddOutputFilterByType DEFLATE application/x-javascript
AddOutputFilterByType DEFLATE application/xhtml+xml
AddOutputFilterByType DEFLATE application/xml
AddOutputFilterByType DEFLATE font/opentype
AddOutputFilterByType DEFLATE font/otf
AddOutputFilterByType DEFLATE font/ttf
AddOutputFilterByType DEFLATE image/svg+xml
AddOutputFilterByType DEFLATE image/x-icon
AddOutputFilterByType DEFLATE text/css
AddOutputFilterByType DEFLATE text/html
AddOutputFilterByType DEFLATE text/javascript
AddOutputFilterByType DEFLATE text/plain
AddOutputFilterByType DEFLATE application/atom+xml
AddOutputFilterByType DEFLATE application/json
AddOutputFilterByType DEFLATE application/x-web-app-manifest+json
AddOutputFilterByType DEFLATE text/x-component
AddOutputFilterByType DEFLATE text/xml
AddOutputFilterByType DEFLATE application/ld+json
AddOutputFilterByType DEFLATE application/x-httpd-fastphp
AddOutputFilterByType DEFLATE application/x-httpd-php
AddOutputFilterByType DEFLATE text/vtt
</IfModule>
<IfModule mod_gzip.c>
mod_gzip_on Yes
mod_gzip_dechunk Yes
mod_gzip_item_include file .(html?|txt|css|js|php|pl)$
mod_gzip_item_include handler ^cgi-script$
mod_gzip_item_include mime ^text/.*
mod_gzip_item_include mime ^application/x-javascript.*
mod_gzip_item_exclude mime ^image/.*
mod_gzip_item_exclude rspheader ^Content-Encoding:.*gzip.*
</IfModule>
#-----------
# Leverage Browser Caching
<IfModule mod_expires.c>
ExpiresActive On
# Perhaps better to whitelist expires rules? Perhaps.
ExpiresDefault "access plus 1 week"
# HTML components (HTCs)
ExpiresByType text/x-component "access plus 1 month"
# Data interchange
ExpiresByType application/atom+xml "access plus 1 hour"
ExpiresByType application/rdf+xml "access plus 1 hour"
ExpiresByType application/rss+xml "access plus 1 hour"
ExpiresByType application/json "access plus 0 seconds"
ExpiresByType application/ld+json "access plus 0 seconds"
ExpiresByType application/schema+json "access plus 0 seconds"
ExpiresByType application/vnd.geo+json "access plus 0 seconds"
ExpiresByType application/xml "access plus 0 seconds"
ExpiresByType text/calendar "access plus 0 seconds"
ExpiresByType text/xml "access plus 0 seconds"
ExpiresByType application/pdf "access 1 month"
ExpiresByType application/x-shockwave-flash "access 1 month"
# Favicon (cannot be renamed) and cursor images
ExpiresByType image/vnd.microsoft.icon "access plus 1 month"
ExpiresByType image/x-icon "access plus 1 month"
# Media: images, video, audio
ExpiresByType image/gif "access plus 1 month"
ExpiresByType image/png "access plus 1 month"
ExpiresByType image/jpg "access plus 1 month"
ExpiresByType image/jpeg "access plus 1 month"
ExpiresByType image/bmp "access plus 1 month"
ExpiresByType image/webp "access plus 1 month"
ExpiresByType audio/ogg "access plus 1 month"
ExpiresByType video/ogg "access plus 1 month"
ExpiresByType video/mp4 "access plus 1 month"
ExpiresByType video/webm "access plus 1 month"
# Webfonts
#collection
ExpiresByType font/collection "access plus 1 month"
# Embedded OpenType (EOT)
ExpiresByType application/vnd.ms-fontobject "access plus 1 month"
ExpiresByType font/eot "access plus 1 month"
# TrueType
ExpiresByType application/x-font-ttf "access plus 1 month"
ExpiresByType font/ttf "access plus 1 month"
# Web Open Font Format (WOFF) 1.0
ExpiresByType application/font-woff "access plus 1 month"
ExpiresByType application/x-font-woff "access plus 1 month"
ExpiresByType font/woff "access plus 1 month"
# OpenType
ExpiresByType font/opentype "access plus 1 month"
ExpiresByType image/svg+xml "access plus 1 month"
# Web Open Font Format (WOFF) 2.0
ExpiresByType application/font-woff2 "access plus 1 month"
ExpiresByType font/woff2 "access plus 1 month"
# Other
ExpiresByType text/x-cross-domain-policy "access plus 1 week"
# HTML
ExpiresByType text/html "access plus 1 minute"
ExpiresByType text/plain "access plus 1 month"
# CSS
ExpiresByType text/css "access plus 1 year"
# Javascript
ExpiresByType text/javascript "access plus 1 month"
ExpiresByType text/x-javascript "access plus 1 month"
ExpiresByType application/javascript "access plus 1 month"
ExpiresByType application/x-javascript "access plus 1 month"
# Manifest files
ExpiresByType application/manifest+json "access plus 1 week"
ExpiresByType application/x-web-app-manifest+json "access plus 0 seconds"
ExpiresByType text/cache-manifest "access plus 0 seconds"
# Markdown
ExpiresByType text/markdown "access plus 0 seconds"
</IfModule>
# Better site speed with better caching
<IfModule mod_headers.c>
<filesmatch "\.(ico|flv|jpg|jpeg|png|gif|css|js|swf|ttf|otf|woff|woff2|eot|svg|webp|mp4)$">
Header set Cache-Control "max-age=31536000, public"
</filesmatch>
<filesmatch "\.(html|htm)$">
Header set Cache-Control "max-age=7200, private, must-revalidate"
</filesmatch>
<filesmatch "\.(pdf)$">
Header set Cache-Control "max-age=86400, public"
</filesmatch>
# 2 DAYS
<FilesMatch "\.(xml|txt)$">
Header set Cache-Control "max-age=172800, public, must-revalidate"
</FilesMatch>
</IfModule>
#-----------
# Keep alive connection to server
<ifModule mod_headers.c>
Header set Connection keep-alive
</ifModule>
# ~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~-~
# # SECURITY - If you found that this file is not working then just remove security section
# Set HttpOnly Cookie. Change php_module according to your version. For php5 use `php5_module`
<IfModule php7_module>
php_flag session.cookie_httponly on
</IfModule>
# Tells apache not to display the server version on error pages, or other pages it generates.
ServerSignature Off
# Extra Security Headers
<IfModule mod_headers.c>
# Protect against (Cross Site Scripting)XSS attacks
# Prevent user to inject html/scripts from website forms.
Header set X-XSS-Protection "1; mode=block"
# Protect against page-framing and click-jacking
# or Header set X-Frame-Options SAMEORIGIN env=!allow_framing
Header set X-Frame-Options SAMEORIGIN
# Protect against content-sniffing or prevent mime based attacks
Header set X-Content-Type-Options nosniff
# Hide Server-side technology information
Header always unset X-Powered-By
Header unset X-Powered-By
# You can implement this header to instruct the browser how to handle the requests over a cross-domain.
# By implementing this header, you restrict loading your site’s assets from other domain to avoid resource abuse.
Header set X-Permitted-Cross-Domain-Policies none
#The default setting where referrer is sent to the same protocol as HTTP to HTTP, HTTPS to HTTPS.
Header set Referrer-Policy no-referrer-when-downgrade
# HTTP Strict Transport Security (HSTS). Required : only if https
Header set Strict-Transport-Security "max-age=31536000; includeSubDomains; preload"
#Content Security Policy. Default-src - Load everything from a defined source. Caution - Sometime doesnt work
# Header set Content-Security-Policy "default-src * data:; script-src https: 'unsafe-inline' 'unsafe-eval'; style-src https: 'unsafe-inline'"
#Header set Content-Security-Policy "default-src https:; script-src https: 'unsafe-inline'; style-src https: 'unsafe-inline'"
#Header always set Content-Security-Policy "upgrade-insecure-requests"
# With Permissions Policy, you can control browser features such as
# geolocation, fullscreen, speaker, USB, autoplay, speaker, microphone, payment, battery status, etc.
# to enable or disable within a web application
Header always set Permissions-Policy "fullscreen 'none'; microphone 'none'"
# This will prevent the use of mis-issued certificates for websites
Header set Expect-CT "enforce, max-age=31536000"
#Feature Policy
Header set Feature-Policy "accelerometer 'none'; autoplay 'self'; camera 'none'; encrypted-media 'self'; fullscreen 'self'; geolocation 'none'; gyroscope 'none'; magnetometer 'none'; microphone 'none'; midi 'none'; payment 'self'; picture-in-picture 'self'; sync-xhr 'self'; usb 'none';"
# https://owasp.org/www-project-secure-headers/#div-headers
Header append Vary "Accept-Encoding, User-Agent, Referer"
Header set Cross-Origin-Embedder-Policy "require-corp"
Header set Cross-Origin-Opener-Policy "same-origin-allow-popups"
Header set Cross-Origin-Resource-Policy "same-origin"
Header set Content-Security-Policy "upgrade-insecure-requests"
</IfModule>
# Block access to configuration, informational, documentation files
<FilesMatch "package.json|package-lock.json|phpunit.xml|composer.json|installed.json|composer.lock|artisan|readme.md|wp-config.php|xmlrpc.php">
order deny,allow
deny from all
</FilesMatch>
# Block access to hidden files & directories. Resulting in a 403 Forbidden error.
# ".htaccess|.editorconfig|.gitattributes|.gitignore|.env|.log|.ini"
<IfModule mod_rewrite.c>
RewriteCond %{SCRIPT_FILENAME} -d [OR]
RewriteCond %{SCRIPT_FILENAME} -f
RewriteRule "(^|/)\." - [F]
</IfModule>
# Disable Unnecessary HTTP Requests
RewriteCond %{REQUEST_METHOD} !^(GET|POST|HEAD)
RewriteRule .* - [R=405,L]
## Disallow Script Execution
#Options -ExecCGI
#AddHandler cgi-script .php .pl .py .jsp .asp .htm .shtml .sh .cgi
## If your server don't support ETags deactivate with "None" (and remove header)
#<IfModule mod_headers.c>
# Header unset ETag
#</IfModule>
@rohankhudedev
Copy link
Author

rohankhudedev commented Feb 4, 2021

Apache Configurations

  • Enable OpCache
  • Enable rewrite mode in server
  • Necessary httpd.conf settings(/etc/httpd/conf/httpd.conf)
<Directory "/var/www/html">
    Options Indexes FollowSymLinks
    AllowOverride All
    Require all granted
</Directory>

Header unset Server
Header always set Server "Kinder Joy"

ServerSignature Off #This alone has to set also in .htaccess
ServerTokens Prod

Security configuration in php.ini

expose_php = Off   # Disable PHP Version form headers
session.cookie_httponly = 1
session.cookie_secure = 1
session.use_strict_mode = 1
session.use_only_cookies = 1
allow_url_fopen = Off
open_basedir="/var/www/html/"
error_log=`/var/www/html/php_scripts_error.log`

disable_functions = exec,passthru,shell_exec,system,proc_open,popen,curl_exec,curl_multi_exec,parse_ini_file,show_source

disable_functions = ini_set,php_uname,getmyuid,getmypid,passthru,leak,listen,diskfreespace,tmpfile,link,ignore_user_abord,shell_exec,dl,set_time_limit,exec,system,highlight_file,source,show_source,fpaththru,virtual,posix_ctermid,posix_getcwd,posix_getegid,posix_geteuid,posix_getgid,posix_getgrgid,posix_getgrnam,posix_getgroups,posix_getlogin,posix_getpgid,posix_getpgrp,posix_getpid,posix,_getppid,posix_getpwnam,posix_getpwuid,posix_getrlimit,posix_getsid,posix_getuid,posix_isatty,posix_kill,posix_mkfifo,posix_setegid,posix_seteuid,posix_setgid,posix_setpgid,posix_setsid,posix_setuid,posix_times,posix_ttyname,posix_uname,proc_open,proc_close,proc_get_status,proc_nice,proc_terminate,phpinfo,popen,curl_exec,curl_multi_exec,parse_ini_file,allow_url_fopen,allow_url_include,pcntl_exec,chgrp,chmod,chown,lchgrp,lchown,putenv

# The configuration directive cgi.force_redirect prevents anyone from calling PHP directly with a URL
cgi.force_redirect = 1

@rohankhudedev
Copy link
Author

rohankhudedev commented Jan 12, 2022

Host Header Modification - Security Implementation did for Kinderjoy, 2021

Explanation - If we modifies HOST header for the website then user will get redirect the modified HOST. This shouldn't happen.
Expected output - Either HOST should get ignore and ignore redirection or user must get server generic message like Misdirected Request. The client needs a new connection for this request as the requested host name does not match the Server Name Indication (SNI) in use for this connection..

  • Blame - This has nothing to do with application. This has to solve in server
  • Browser extension used to replicate error
  • Solution
  • Reference
  • Worked Snippet - Edit /etc/httpd/conf/httpd.conf
<VirtualHost *:443>
       #Mention plain domain only
	ServerName domain.com
	ServerAlias www.domain.com
	UseCanonicalName On # Forces apache to use ServerName mentioned above instead of HostName from client request.
	DocumentRoot "/var/www/html/public"
</VirtualHost>
  • Alternative way to fix this
https://www.youtube.com/watch?v=KGTTlzZiihw
https://w3codegenerator.com/code-snippets/laravel/how-to-prevent-host-header-attack-in-laravel

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment