63 lines
2.1 KiB
ApacheConf
63 lines
2.1 KiB
ApacheConf
# Zettai Systems — Apache / cPanel
|
|
#
|
|
# Clean URLs: /about serves about.html; /about.html 301 → /about
|
|
# /services must NOT become /services/ (folder clash with services.html — breaks relative CSS)
|
|
|
|
ErrorDocument 404 /404.html
|
|
|
|
Options -Indexes
|
|
|
|
# Critical: without this, Apache turns /services into /services/ (real folder),
|
|
# then relative css/style.css resolves to /services/css/style.css and the page is unstyled.
|
|
<IfModule mod_dir.c>
|
|
DirectorySlash Off
|
|
</IfModule>
|
|
|
|
<IfModule mod_rewrite.c>
|
|
RewriteEngine On
|
|
RewriteBase /
|
|
|
|
<IfModule mod_negotiation.c>
|
|
Options -MultiViews
|
|
</IfModule>
|
|
|
|
# Old Odoo service URL → ERP (clean)
|
|
RewriteRule ^services/odoo\.html$ /services/erp [R=301,L]
|
|
RewriteRule ^services/odoo/?$ /services/erp [R=301,L]
|
|
|
|
# /index.html → /
|
|
RewriteCond %{THE_REQUEST} \s/+index\.html[\s?] [NC]
|
|
RewriteRule ^index\.html$ / [R=301,L]
|
|
|
|
# /path/page.html → /path/page (browser request only)
|
|
RewriteCond %{THE_REQUEST} \s/+(.+?)\.html[\s?] [NC]
|
|
RewriteRule ^ /%1 [R=301,L]
|
|
|
|
# /services/ → /services (fixes broken relative CSS under trailing slash)
|
|
RewriteRule ^services/$ /services [R=301,L]
|
|
|
|
# Nested extensionless pages: /services/foo/ → /services/foo
|
|
RewriteCond %{REQUEST_FILENAME} !-d
|
|
RewriteCond %{DOCUMENT_ROOT}/$1.html -f
|
|
RewriteRule ^(.+)/$ /$1 [R=301,L]
|
|
|
|
# /services → services.html (page, not the services/ directory)
|
|
RewriteRule ^services$ services.html [L]
|
|
|
|
# Extensionless URLs → .html
|
|
RewriteCond %{REQUEST_FILENAME} !-d
|
|
RewriteCond %{REQUEST_FILENAME} !-f
|
|
RewriteCond %{REQUEST_FILENAME}.html -f
|
|
RewriteRule ^(.+?)/?$ $1.html [L]
|
|
</IfModule>
|
|
|
|
# Safe security headers (do not block static assets)
|
|
<IfModule mod_headers.c>
|
|
Header always set X-Content-Type-Options "nosniff"
|
|
Header always set Referrer-Policy "strict-origin-when-cross-origin"
|
|
Header always set X-Frame-Options "SAMEORIGIN"
|
|
Header always set Permissions-Policy "camera=(), microphone=(), geolocation=()"
|
|
Header always set Content-Security-Policy "frame-ancestors 'self'; base-uri 'self'; object-src 'none'; form-action 'self'"
|
|
Header always set Strict-Transport-Security "max-age=31536000; includeSubDomains"
|
|
</IfModule>
|