/ Nginx Configuration
2026-05-30 16:11:40 AWST
⚠ Safe handoff files only. Passwords and secrets are redacted.

Nginx Sites

/etc/nginx/sites-enabled/admin
server {
    listen 8080;
    server_name 192.168.100.197 103.138.201.66;

    root /var/www/admin/public;
    index index.php;

    location / {
        try_files $uri $uri/ /index.php?$query_string;
    }

    location ~ \.php$ {
        fastcgi_pass unix:/var/run/php/php8.3-fpm.sock;
        fastcgi_index index.php;
        fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name;
        include fastcgi_params;
        fastcgi_read_timeout 300;
    }

    location ~ /\.ht {
        deny all;
    }

    client_max_body_size 128M;

    access_log /var/log/nginx/admin_access.log;
    error_log  /var/log/nginx/admin_error.log;
}
/etc/nginx/sites-enabled/goseek
server {
    listen 8090;
    server_name _ goseek.jfmcommunications.com.au;

    root /var/www/goseek/public;
    index index.php;

    location / {
        try_files $uri $uri/ /index.php?$query_string;
    }

    location ~ \.php$ {
        fastcgi_pass unix:/var/run/php/php8.3-fpm.sock;
        fastcgi_index index.php;
        fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name;
        include fastcgi_params;
        fastcgi_read_timeout 300;
    }

    location ~ /\.ht { deny all; }

    client_max_body_size 64M;
    access_log /var/log/nginx/goseek_access.log;
    error_log  /var/log/nginx/goseek_error.log;
}
/etc/nginx/sites-enabled/handoff
server {
    listen 9002;
    server_name _ vqngx6j8dc9q1lvt7g2a7a646q2t.jfmcommunications.com.au;

    location /vqngx6j8dc9q1lvt7g2a7a646q2t/ {
        alias /var/www/handoff/public/vqngx6j8dc9q1lvt7g2a7a646q2t/;
        autoindex on;
        autoindex_exact_size off;
        autoindex_localtime on;
        add_header Cache-Control "no-store, no-cache, must-revalidate";
        expires -1;
        try_files $uri $uri/ =404;
    }

    location = / { return 301 http://$host:9002/vqngx6j8dc9q1lvt7g2a7a646q2t/; }
    location /   { return 301 http://$host:9002/vqngx6j8dc9q1lvt7g2a7a646q2t/; }

    access_log /var/log/nginx/handoff_access.log;
    error_log  /var/log/nginx/handoff_error.log;
}
/etc/nginx/sites-enabled/handoff-public-ssl
server {
    listen 80;
    listen [::]:80;
    server_name vqngx6j8dc9q1lvt7g2a7a646q2t.jfmcommunications.com.au;

    root /var/www/handoff/public;

    location ^~ /.well-known/acme-challenge/ {
        root /var/www/handoff/public;
        default_type "text/plain";
        try_files $uri =404;
    }

    location / {
        return 301 https://$host$request_uri;
    }
}

server {
    listen 443 ssl http2;
    listen [::]:443 ssl http2;
    server_name vqngx6j8dc9q1lvt7g2a7a646q2t.jfmcommunications.com.au;

    root /var/www/handoff/public;
    index index.html index.htm;

    ssl_certificate     /etc/letsencrypt/live/vqngx6j8dc9q1lvt7g2a7a646q2t.jfmcommunications.com.au/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/vqngx6j8dc9q1lvt7g2a7a646q2t.jfmcommunications.com.au/privkey.pem;

    access_log /var/log/nginx/handoff-public-ssl.access.log;
    error_log  /var/log/nginx/handoff-public-ssl.error.log;

    add_header Cache-Control "no-store, no-cache, must-revalidate, max-age=0" always;
    add_header Pragma "no-cache" always;
    add_header Expires "0" always;
    add_header X-Content-Type-Options "nosniff" always;
    add_header Referrer-Policy "no-referrer" always;
    add_header X-Frame-Options "DENY" always;
    add_header X-Robots-Tag "noindex, nofollow, noarchive" always;

    location ~ /\.(?!well-known) {
        return 404;
    }

    location ~* \.(pem|key|pfx|p12|crt|csr|env|ini|conf\.bak|bak|old|orig|swp)$ {
        return 404;
    }

    location = / {
        return 302 /vqngx6j8dc9q1lvt7g2a7a646q2t/;
    }

    location = /qngx6j8dc9q1lvt7g2a7a646q2t {
        return 301 /vqngx6j8dc9q1lvt7g2a7a646q2t/;
    }

    location = /qngx6j8dc9q1lvt7g2a7a646q2t/ {
        return 301 /vqngx6j8dc9q1lvt7g2a7a646q2t/;
    }

    location ^~ /qngx6j8dc9q1lvt7g2a7a646q2t/ {
        rewrite ^/qngx6j8dc9q1lvt7g2a7a646q2t/(.*)$ /vqngx6j8dc9q1lvt7g2a7a646q2t/$1 permanent;
    }

    # Non-slug aliases must always read from the current canonical slug tree.
    # Do not read /var/www/handoff/public/server first, because that can be stale.
    location /server/ {
        try_files /vqngx6j8dc9q1lvt7g2a7a646q2t$uri =404;
    }

    location /source/ {
        try_files /vqngx6j8dc9q1lvt7g2a7a646q2t$uri /vqngx6j8dc9q1lvt7g2a7a646q2t$uri/ =404;
    }

    location /admin/ {
        try_files /vqngx6j8dc9q1lvt7g2a7a646q2t$uri /vqngx6j8dc9q1lvt7g2a7a646q2t$uri/ =404;
    }

    location /mainsite/ {
        try_files /vqngx6j8dc9q1lvt7g2a7a646q2t$uri /vqngx6j8dc9q1lvt7g2a7a646q2t$uri/ =404;
    }

    location /shared/ {
        try_files /vqngx6j8dc9q1lvt7g2a7a646q2t$uri /vqngx6j8dc9q1lvt7g2a7a646q2t$uri/ =404;
    }

    location /transcription/ {
        try_files /vqngx6j8dc9q1lvt7g2a7a646q2t$uri /vqngx6j8dc9q1lvt7g2a7a646q2t$uri/ =404;
    }

    location = /latest-run.txt {
        try_files /vqngx6j8dc9q1lvt7g2a7a646q2t/latest-run.txt =404;
    }

    location = /latest-run.html {
        try_files /vqngx6j8dc9q1lvt7g2a7a646q2t/latest-run.html =404;
    }

    location ^~ /vqngx6j8dc9q1lvt7g2a7a646q2t/ {
        try_files $uri $uri/ =404;
    }

    location / {
        try_files /vqngx6j8dc9q1lvt7g2a7a646q2t$uri /vqngx6j8dc9q1lvt7g2a7a646q2t$uri/ =404;
    }
}
/etc/nginx/sites-enabled/legaltranscribe
# Legal Transcription Platform - Nginx Configuration
# Generated: Thu May 28 10:44:57 AWST 2026

# Redirect HTTP to HTTPS
server {
    listen 80;
    listen [::]:80;
    server_name _;
    return 301 https://$host$request_uri;
}

server {
    listen 443 ssl http2;
    listen [::]:443 ssl http2;
    server_name _;

    root /opt/legaltranscribe/app/public;
    index index.php;

    # TLS Configuration
    ssl_certificate     /etc/nginx/ssl/selfsigned.crt;
    ssl_certificate_key /etc/nginx/ssl/selfsigned.key;
    ssl_protocols       TLSv1.2 TLSv1.3;
    ssl_ciphers         ECDHE-ECDSA-AES128-GCM-SHA256:ECDHE-RSA-AES128-GCM-SHA256:ECDHE-ECDSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:DHE-RSA-AES128-GCM-SHA256;
    ssl_prefer_server_ciphers off;
    ssl_session_timeout 1d;
    ssl_session_cache   shared:SSL:10m;

    # Security headers
    add_header Strict-Transport-Security "max-age=63072000; includeSubDomains" always;
    add_header X-Frame-Options SAMEORIGIN always;
    add_header X-Content-Type-Options nosniff always;
    add_header Referrer-Policy "strict-origin-when-cross-origin" always;

    # Laravel
    location / {
        try_files $uri $uri/ /index.php?$query_string;
    }

    location ~ \.php$ {
        fastcgi_pass unix:/var/run/php/php8.3-fpm.sock;
        fastcgi_index index.php;
        fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name;
        include fastcgi_params;
        fastcgi_read_timeout 300;
    }

    # Block access to hidden files
    location ~ /\. {
        deny all;
    }

    # Block direct access to data/storage
    location ~ ^/(data|storage|backups) {
        deny all;
    }

    client_max_body_size 512M;

    access_log /var/log/nginx/legaltranscribe_access.log;
    error_log  /var/log/nginx/legaltranscribe_error.log;
}
/etc/nginx/sites-enabled/mainsite
server {
    listen 80;
    server_name 103.138.201.66 192.168.100.197;

    root /var/www/mainsite/public;
    index index.php;

    location / {
        try_files $uri $uri/ /index.php?$query_string;
    }

    location ~ \.php$ {
        fastcgi_pass unix:/var/run/php/php8.3-fpm.sock;
        fastcgi_index index.php;
        fastcgi_param SCRIPT_FILENAME $realpath_root$fastcgi_script_name;
        include fastcgi_params;
        fastcgi_read_timeout 300;
    }

    location ~ /\.ht {
        deny all;
    }

    client_max_body_size 128M;

    access_log /var/log/nginx/mainsite_access.log;
    error_log  /var/log/nginx/mainsite_error.log;
}
Auto-generated by publish_handoff.sh | 20260530_161140