Files
HokmPlay/deploy/SUBDOMAIN_SPLIT.md
T
soroush.asadi 5d38312ef0
CI/CD / CI - API (dotnet build + engine sim) (push) Successful in 4m40s
CI/CD / CI - Web (tsc + next build) (push) Successful in 1m7s
CI/CD / Deploy - local stack (db + server + web) (push) Failing after 41s
Marketing site (bargevasat.ir) + admin-editable store links + subdomain split
- New standalone Next.js marketing site under site/ (static export, SEO):
  landing, download/install guide (Bazaar/Myket/iOS-PWA/web), FAQ (JSON-LD),
  privacy, terms, support, /admin link editor. fa RTL, sitemap/robots/manifest.
- Backend: SiteLinksService (JSON-file persisted) + GET /api/site/links (public)
  + POST /api/admin/site/links (X-Admin-Token). ADMIN_TOKEN + Site__DataDir via env.
- compose: hokm-site service (:1520) + hokm_data volume for links JSON.
- CI deploy job builds + deploys the site container.
- deploy/SUBDOMAIN_SPLIT.md: nginx blocks, cert reissue, DNS, ENV split.
- Exclude site/ from root tsc + web docker context.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
2026-06-08 07:19:43 +03:30

4.2 KiB
Raw Blame History

Subdomain split: marketing site + game + API

After this change there are three public hosts (all → edge nginx 185.239.1.100):

Host Serves Upstream (on 171.22.25.73)
bargevasat.ir, www.bargevasat.ir Marketing site (hokm-site) :1520
app.bargevasat.ir The game (hokm-web) :1500
api.bargevasat.ir API + SignalR (hokm-server) :1505 (CDN bypass)

1. DNS

Add/confirm Arecords (all → 185.239.1.100):

bargevasat.ir       A  185.239.1.100   (CDN ok)
www.bargevasat.ir   A  185.239.1.100   (CDN ok)
app.bargevasat.ir   A  185.239.1.100   (CDN ok)
api.bargevasat.ir   A  185.239.1.100   (CDN BYPASS / DNS-only)

2. TLS cert — reissue to include app

The current cert covers bargevasat.ir, www, api — add app:

sudo certbot certonly --webroot -w /var/www/certbot \
  -d bargevasat.ir -d www.bargevasat.ir -d app.bargevasat.ir -d api.bargevasat.ir \
  --agree-tos --no-eff-email --email you@example.com
# then copy/symlink fullchain.pem + privkey.pem into /etc/ssl/bargevasat/

(Or DNS01 if behind the CDN — see SSL notes.)

3. nginx (edit /root/mirror-server/nginx/nginx.conf)

Replace the single Barge Vasat web block with these three:

# Redirect http → https for all three
server {
    listen 80;
    server_name bargevasat.ir www.bargevasat.ir app.bargevasat.ir api.bargevasat.ir;
    location /.well-known/acme-challenge/ { root /var/www/certbot; }
    location / { return 301 https://$host$request_uri; }
}

# Marketing site → hokm-site :1520
server {
    listen 443 ssl;
    http2 on;
    server_name bargevasat.ir www.bargevasat.ir;
    ssl_certificate     /etc/ssl/bargevasat/fullchain.pem;
    ssl_certificate_key /etc/ssl/bargevasat/privateKey.pem;
    location / {
        proxy_pass http://171.22.25.73:1520;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
    }
}

# Game (Next static SPA) → hokm-web :1500
server {
    listen 443 ssl;
    http2 on;
    server_name app.bargevasat.ir;
    client_max_body_size 25m;
    ssl_certificate     /etc/ssl/bargevasat/fullchain.pem;
    ssl_certificate_key /etc/ssl/bargevasat/privateKey.pem;
    location / {
        proxy_pass http://171.22.25.73:1500;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
    }
}

# API + SignalR → hokm-server :1505 (WebSocket; keep CDN bypassed for this host)
server {
    listen 443 ssl;
    http2 on;
    server_name api.bargevasat.ir;
    client_max_body_size 50m;
    ssl_certificate     /etc/ssl/bargevasat/fullchain.pem;
    ssl_certificate_key /etc/ssl/bargevasat/privateKey.pem;
    location / {
        proxy_pass http://171.22.25.73:1505;
        proxy_http_version 1.1;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection $connection_upgrade;
        proxy_read_timeout 3600s;
    }
}

Reload: docker compose exec nginx nginx -t && docker compose exec nginx nginx -s reload

4. ENV_FILE secret (Gitea) — add/confirm

SITE_PORT=1520
NEXT_PUBLIC_APP_URL=https://app.bargevasat.ir
NEXT_PUBLIC_SITE_URL=https://bargevasat.ir
NEXT_PUBLIC_SERVER_URL=https://api.bargevasat.ir
CORS_ORIGINS=https://bargevasat.ir,https://www.bargevasat.ir,https://app.bargevasat.ir
ADMIN_TOKEN=<openssl rand -hex 24>

5. Deploy

docker compose build site web server && docker compose up -d (Add the site service to the CI deploy job's build/up + healthwait, same pattern as web.)

6. Verify

curl -I https://bargevasat.ir         # marketing (200)
curl -I https://app.bargevasat.ir     # game (200)
curl -I https://api.bargevasat.ir     # API (405 to HEAD is fine)

Admin: open https://bargevasat.ir/admin, enter ADMIN_TOKEN, set Bazaar/Myket links → Save.