# ==========================================================================
# Capacity Expansion Co — Apache configuration
# GoDaddy Gen4 VPS · Fully Managed Linux · cPanel · PHP enabled
# ==========================================================================

# --------------------------------------------------------------------------
# Directory browsing and default document
# --------------------------------------------------------------------------
Options -Indexes
DirectoryIndex index.html index.php

# ==========================================================================
# DEPLOYMENT CONFIG — the only two lines that change between environments.
#
#   Demo   (https://rubixdemos.com/capacityexpansion):
#       ErrorDocument 404 /capacityexpansion/404
#       RewriteBase /capacityexpansion/
#
#   Live   (https://capacityexpansion.com):
#       ErrorDocument 404 /404
#       RewriteBase /
#
#   When switching to Live, also run:  python3 src/relativize.py
#   after setting DEPLOY_PREFIX = "/" in that script (re-anchors 404.html).
# ==========================================================================
ErrorDocument 404 /capacityexpansion/404

<IfModule mod_rewrite.c>
RewriteEngine On
RewriteBase /capacityexpansion/

# ---- Force HTTPS and strip www (single consistent 301) -------------------
# Host-agnostic: preserves whatever path the site is installed under.
RewriteCond %{HTTPS} !=on [OR]
RewriteCond %{HTTP_HOST} ^www\. [NC]
RewriteCond %{HTTP_HOST} ^(?:www\.)?(.+)$ [NC]
RewriteRule ^ https://%1%{REQUEST_URI} [L,R=301]

# ---- index.html / index -> the directory root ----------------------------
# The capture keeps any subdirectory prefix intact.
RewriteCond %{THE_REQUEST} \s/+(.*?)index\.html[\s?] [NC]
RewriteRule ^ /%1 [R=301,L]
RewriteRule ^index/?$ ./ [R=301,L]

# ---- Redirect any .html request to its clean URL -------------------------
RewriteCond %{THE_REQUEST} \s/+(.+?)\.html[\s?] [NC]
RewriteRule ^ /%1 [R=301,L]

# ---- Serve the .html file for the clean URL ------------------------------
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_FILENAME}\.html -f
RewriteRule ^(.+?)/?$ $1.html [L]

# ---- Block direct web access to non-public directories -------------------
RewriteRule ^(lib|data|uploads|src)/ - [F,L]
RewriteRule ^cgi-bin/ - [F,L]
</IfModule>

# --------------------------------------------------------------------------
# Security headers
# --------------------------------------------------------------------------
<IfModule mod_headers.c>
Header always set Strict-Transport-Security "max-age=31536000; includeSubDomains"
Header always set X-Content-Type-Options "nosniff"
Header always set X-Frame-Options "SAMEORIGIN"
Header always set Referrer-Policy "strict-origin-when-cross-origin"
Header always set Permissions-Policy "camera=(), microphone=(), geolocation=()"
Header always set Content-Security-Policy "default-src 'self'; script-src 'self' 'unsafe-inline' https://www.googletagmanager.com https://www.google-analytics.com https://www.google.com https://www.gstatic.com; style-src 'self' 'unsafe-inline' https://fonts.googleapis.com; font-src 'self' https://fonts.gstatic.com; img-src 'self' data: https:; connect-src 'self' https://www.google-analytics.com https://www.googletagmanager.com https://www.google.com; frame-src https://www.google.com https://maps.google.com https://www.googletagmanager.com; object-src 'none'; base-uri 'self'; form-action 'self'"
Header always unset X-Powered-By
Header unset X-Powered-By
</IfModule>

# --------------------------------------------------------------------------
# GZIP / Brotli compression
# --------------------------------------------------------------------------
<IfModule mod_deflate.c>
AddOutputFilterByType DEFLATE text/html text/plain text/xml text/css text/javascript
AddOutputFilterByType DEFLATE application/javascript application/x-javascript application/json
AddOutputFilterByType DEFLATE application/xml application/rss+xml application/atom+xml
AddOutputFilterByType DEFLATE image/svg+xml
AddOutputFilterByType DEFLATE font/ttf font/otf font/woff font/woff2
AddOutputFilterByType DEFLATE application/font-woff application/font-woff2
AddOutputFilterByType DEFLATE application/vnd.ms-fontobject
</IfModule>

<IfModule mod_brotli.c>
AddOutputFilterByType BROTLI_COMPRESS text/html text/plain text/xml text/css text/javascript
AddOutputFilterByType BROTLI_COMPRESS application/javascript application/x-javascript application/json
AddOutputFilterByType BROTLI_COMPRESS application/xml application/rss+xml application/atom+xml
AddOutputFilterByType BROTLI_COMPRESS image/svg+xml
AddOutputFilterByType BROTLI_COMPRESS font/ttf font/otf font/woff font/woff2
</IfModule>

# --------------------------------------------------------------------------
# Browser caching
# --------------------------------------------------------------------------
<IfModule mod_expires.c>
ExpiresActive On
ExpiresDefault "access plus 1 month"
ExpiresByType text/html "access plus 1 hour"
ExpiresByType text/css "access plus 1 year"
ExpiresByType text/javascript "access plus 1 year"
ExpiresByType application/javascript "access plus 1 year"
ExpiresByType application/x-javascript "access plus 1 year"
ExpiresByType image/jpeg "access plus 1 year"
ExpiresByType image/png "access plus 1 year"
ExpiresByType image/gif "access plus 1 year"
ExpiresByType image/webp "access plus 1 year"
ExpiresByType image/svg+xml "access plus 1 year"
ExpiresByType image/x-icon "access plus 1 year"
ExpiresByType font/ttf "access plus 1 year"
ExpiresByType font/otf "access plus 1 year"
ExpiresByType font/woff "access plus 1 year"
ExpiresByType font/woff2 "access plus 1 year"
ExpiresByType application/font-woff "access plus 1 year"
ExpiresByType application/font-woff2 "access plus 1 year"
</IfModule>
<IfModule mod_headers.c>
<FilesMatch ".(ico|jpe?g|png|gif|webp|svg|css|js|woff|woff2|ttf|otf)$">
Header set Cache-Control "max-age=31536000, public"
</FilesMatch>
<FilesMatch ".(html|htm)$">
Header set Cache-Control "max-age=3600, public, must-revalidate"
</FilesMatch>
</IfModule>

# --------------------------------------------------------------------------
# MIME types
# --------------------------------------------------------------------------
<IfModule mod_mime.c>
AddType image/webp .webp
AddType application/manifest+json .webmanifest
AddType image/x-icon .ico
AddType font/woff2 .woff2
</IfModule>

# --------------------------------------------------------------------------
# Block access to sensitive files
# --------------------------------------------------------------------------
<FilesMatch "^\.">
  Require all denied
</FilesMatch>

<FilesMatch "(?i)^(config\.php|config\.sample\.php|formkit\.php|composer\.(json|lock)|package(-lock)?\.json|README(\.md)?|.*\.(log|ini|sh|bak|old|orig|sql|tpl|dist|py|swp|env|yml|yaml))$">
  Require all denied
</FilesMatch>

<FilesMatch "(?i)\.(log|bak|old|orig|sql|env|ini|sh|py)$">
  Require all denied
</FilesMatch>

# Never expose PHP source as plain text
<IfModule mod_negotiation.c>
  Options -MultiViews
</IfModule>

# --------------------------------------------------------------------------
# Hardening
# --------------------------------------------------------------------------
<IfModule mod_php.c>
  php_flag display_errors off
  php_flag log_errors on
  php_flag allow_url_include off
  php_flag allow_url_fopen on
  php_value upload_max_filesize 5M
  php_value post_max_size 8M
</IfModule>

ServerSignature Off

# Limit request methods to those the site actually uses
<IfModule mod_rewrite.c>
RewriteCond %{REQUEST_METHOD} ^(TRACE|TRACK|DELETE|PUT|PATCH|CONNECT)$
RewriteRule ^ - [F,L]
</IfModule>
