update the domains

This commit is contained in:
root
2026-05-16 16:51:59 -04:00
parent 4408f7cc8f
commit 7e4fb6d62a
9 changed files with 50 additions and 44 deletions
+6 -5
View File
@@ -4,12 +4,13 @@ API_PORT=4000
API_URL=http://localhost:4000 API_URL=http://localhost:4000
API_INTERNAL_URL=http://api:4000/api/v1 API_INTERNAL_URL=http://api:4000/api/v1
NEXT_PUBLIC_API_URL=http://localhost:4000/api/v1 NEXT_PUBLIC_API_URL=http://localhost:4000/api/v1
NEXT_PUBLIC_MARKETING_URL=http://localhost:3000 NEXT_PUBLIC_MARKETING_URL=http://localhost:3003
NEXT_PUBLIC_MARKETPLACE_URL=http://localhost:3000/explore NEXT_PUBLIC_MARKETPLACE_URL=http://localhost:3000/marketplace
NEXT_PUBLIC_DASHBOARD_URL=http://localhost:3001 NEXT_PUBLIC_DASHBOARD_URL=http://localhost:3001/dashboard
NEXT_PUBLIC_ADMIN_URL=http://localhost:3002 NEXT_PUBLIC_ADMIN_URL=http://localhost:3002/admin
NEXT_PUBLIC_PUBLIC_SITE_DOMAIN=localhost:3003 NEXT_PUBLIC_PUBLIC_SITE_DOMAIN=localhost:3003
DASHBOARD_URL=http://localhost:3001 DASHBOARD_URL=http://localhost:3001/dashboard
ADMIN_URL=http://localhost:3002/admin
JWT_SECRET=dev-secret JWT_SECRET=dev-secret
JWT_EXPIRY=8h JWT_EXPIRY=8h
RENTER_JWT_EXPIRY=7d RENTER_JWT_EXPIRY=7d
+6 -8
View File
@@ -1,9 +1,6 @@
# ── Traefik domains — used in docker-compose labels ────────────────────────── # ── Traefik domains — used in docker-compose labels ──────────────────────────
ACME_EMAIL=rentaldrivego@gmail.com ACME_EMAIL=rentaldrivego@gmail.com
MARKETPLACE_DOMAIN=rentaldrivego.ma
API_DOMAIN=api.rentaldrivego.ma API_DOMAIN=api.rentaldrivego.ma
DASHBOARD_DOMAIN=dashboard.rentaldrivego.ma
ADMIN_DOMAIN=admin.rentaldrivego.ma
PUBLIC_SITE_DOMAIN=rentaldrivego.ma PUBLIC_SITE_DOMAIN=rentaldrivego.ma
PGMANAGE_DOMAIN=pgmanage.rentaldrivego.ma PGMANAGE_DOMAIN=pgmanage.rentaldrivego.ma
@@ -21,15 +18,16 @@ NEXT_PUBLIC_API_URL=https://api.rentaldrivego.ma/api/v1
# ── Frontend public URLs ─────────────────────────────────────────────────────── # ── Frontend public URLs ───────────────────────────────────────────────────────
NEXT_PUBLIC_MARKETING_URL=https://rentaldrivego.ma NEXT_PUBLIC_MARKETING_URL=https://rentaldrivego.ma
NEXT_PUBLIC_MARKETPLACE_URL=https://rentaldrivego.ma/explore NEXT_PUBLIC_MARKETPLACE_URL=https://rentaldrivego.ma/marketplace
NEXT_PUBLIC_DASHBOARD_URL=https://dashboard.rentaldrivego.ma NEXT_PUBLIC_DASHBOARD_URL=https://rentaldrivego.ma/dashboard
NEXT_PUBLIC_ADMIN_URL=https://admin.rentaldrivego.ma NEXT_PUBLIC_ADMIN_URL=https://rentaldrivego.ma/admin
NEXT_PUBLIC_PUBLIC_SITE_DOMAIN=rentaldrivego.ma NEXT_PUBLIC_PUBLIC_SITE_DOMAIN=rentaldrivego.ma
DASHBOARD_URL=https://dashboard.rentaldrivego.ma DASHBOARD_URL=https://rentaldrivego.ma/dashboard
ADMIN_URL=https://rentaldrivego.ma/admin
# ── CORS ────────────────────────────────────────────────────────────────────── # ── CORS ──────────────────────────────────────────────────────────────────────
# Comma-separated list of allowed browser origins. REQUIRED in production. # Comma-separated list of allowed browser origins. REQUIRED in production.
CORS_ORIGINS=https://rentaldrivego.ma,https://dashboard.rentaldrivego.ma,https://admin.rentaldrivego.ma CORS_ORIGINS=https://rentaldrivego.ma
# ── Auth ────────────────────────────────────────────────────────────────────── # ── Auth ──────────────────────────────────────────────────────────────────────
JWT_SECRET=PMPS5k0D7rUeJOk0NkhI5bRtoGjkUqjK JWT_SECRET=PMPS5k0D7rUeJOk0NkhI5bRtoGjkUqjK
+6 -8
View File
@@ -1,9 +1,6 @@
# ── Traefik domains — used in docker-compose labels ────────────────────────── # ── Traefik domains — used in docker-compose labels ──────────────────────────
ACME_EMAIL=rentaldrivego@gmail.com ACME_EMAIL=rentaldrivego@gmail.com
MARKETPLACE_DOMAIN=app.rentaldrivego.ma
API_DOMAIN=api.rentaldrivego.ma API_DOMAIN=api.rentaldrivego.ma
DASHBOARD_DOMAIN=dashboard.rentaldrivego.ma
ADMIN_DOMAIN=admin.rentaldrivego.ma
PUBLIC_SITE_DOMAIN=rentaldrivego.ma PUBLIC_SITE_DOMAIN=rentaldrivego.ma
PGMANAGE_DOMAIN=pgmanage.rentaldrivego.ma PGMANAGE_DOMAIN=pgmanage.rentaldrivego.ma
@@ -21,15 +18,16 @@ NEXT_PUBLIC_API_URL=https://api.rentaldrivego.ma/api/v1
# ── Frontend public URLs ─────────────────────────────────────────────────────── # ── Frontend public URLs ───────────────────────────────────────────────────────
NEXT_PUBLIC_MARKETING_URL=https://rentaldrivego.ma NEXT_PUBLIC_MARKETING_URL=https://rentaldrivego.ma
NEXT_PUBLIC_MARKETPLACE_URL=https://app.rentaldrivego.ma/explore NEXT_PUBLIC_MARKETPLACE_URL=https://rentaldrivego.ma/marketplace
NEXT_PUBLIC_DASHBOARD_URL=https://dashboard.rentaldrivego.ma NEXT_PUBLIC_DASHBOARD_URL=https://rentaldrivego.ma/dashboard
NEXT_PUBLIC_ADMIN_URL=https://admin.rentaldrivego.ma NEXT_PUBLIC_ADMIN_URL=https://rentaldrivego.ma/admin
NEXT_PUBLIC_PUBLIC_SITE_DOMAIN=rentaldrivego.ma NEXT_PUBLIC_PUBLIC_SITE_DOMAIN=rentaldrivego.ma
DASHBOARD_URL=https://dashboard.rentaldrivego.ma DASHBOARD_URL=https://rentaldrivego.ma/dashboard
ADMIN_URL=https://rentaldrivego.ma/admin
# ── CORS ────────────────────────────────────────────────────────────────────── # ── CORS ──────────────────────────────────────────────────────────────────────
# Comma-separated list of allowed browser origins. REQUIRED in production. # Comma-separated list of allowed browser origins. REQUIRED in production.
CORS_ORIGINS=https://rentaldrivego.ma,https://app.rentaldrivego.ma,https://dashboard.rentaldrivego.ma,https://admin.rentaldrivego.ma CORS_ORIGINS=https://rentaldrivego.ma
# ── Auth ────────────────────────────────────────────────────────────────────── # ── Auth ──────────────────────────────────────────────────────────────────────
JWT_SECRET=PMPS5k0D7rUeJOk0NkhI5bRtoGjkUqjK JWT_SECRET=PMPS5k0D7rUeJOk0NkhI5bRtoGjkUqjK
+1
View File
@@ -3,6 +3,7 @@ const apiOrigin = (process.env.API_INTERNAL_URL ?? process.env.API_URL ?? 'http:
const apiUrl = new URL(apiOrigin) const apiUrl = new URL(apiOrigin)
const nextConfig = { const nextConfig = {
basePath: '/admin',
images: { images: {
remotePatterns: [ remotePatterns: [
{ {
+1
View File
@@ -24,6 +24,7 @@ const storagePatterns = [
.filter((p, i, arr) => arr.findIndex((q) => q.hostname === p.hostname && q.port === p.port) === i) .filter((p, i, arr) => arr.findIndex((q) => q.hostname === p.hostname && q.port === p.port) === i)
const nextConfig = { const nextConfig = {
basePath: '/dashboard',
images: { images: {
remotePatterns: [ remotePatterns: [
{ {
+7 -6
View File
@@ -1,17 +1,18 @@
import { resolveBrowserAppUrl } from '@/lib/appUrls' import { resolveBrowserAppUrl } from '@/lib/appUrls'
function toAppOrigin(url: string): string { function toAppBase(url: string): string {
try { try {
return new URL(url).origin const u = new URL(url)
return (u.origin + u.pathname).replace(/\/$/, '')
} catch { } catch {
return url.replace(/\/$/, '') return url.replace(/\/$/, '')
} }
} }
export const marketplaceUrl = toAppOrigin( export const marketplaceUrl = toAppBase(
resolveBrowserAppUrl(process.env.NEXT_PUBLIC_MARKETPLACE_URL ?? 'http://localhost:3000'), resolveBrowserAppUrl(process.env.NEXT_PUBLIC_MARKETPLACE_URL ?? 'http://localhost:3000/marketplace'),
) )
export const adminUrl = toAppOrigin( export const adminUrl = toAppBase(
resolveBrowserAppUrl(process.env.NEXT_PUBLIC_ADMIN_URL ?? 'http://localhost:3002'), resolveBrowserAppUrl(process.env.NEXT_PUBLIC_ADMIN_URL ?? 'http://localhost:3002/admin'),
) )
+2 -1
View File
@@ -11,7 +11,8 @@ function localJwtMiddleware(req: NextRequest): NextResponse {
// Check for employee_token cookie (set on login) OR allow if coming from sign-in // Check for employee_token cookie (set on login) OR allow if coming from sign-in
const token = req.cookies.get('employee_token')?.value const token = req.cookies.get('employee_token')?.value
if (!token) { if (!token) {
const signInUrl = new URL('/sign-in', req.url) const signInUrl = req.nextUrl.clone()
signInUrl.pathname = '/sign-in'
signInUrl.searchParams.set('redirect', req.nextUrl.pathname) signInUrl.searchParams.set('redirect', req.nextUrl.pathname)
return NextResponse.redirect(signInUrl) return NextResponse.redirect(signInUrl)
} }
+1
View File
@@ -1,5 +1,6 @@
/** @type {import('next').NextConfig} */ /** @type {import('next').NextConfig} */
const nextConfig = { const nextConfig = {
basePath: '/marketplace',
images: { images: {
domains: ['res.cloudinary.com'], domains: ['res.cloudinary.com'],
}, },
+20 -16
View File
@@ -84,30 +84,34 @@ services:
restart: unless-stopped restart: unless-stopped
labels: labels:
- traefik.enable=true - traefik.enable=true
# public site (port 3003) — owns both bare and www domains # marketplace (port 3000) — /marketplace path, priority 20
- traefik.http.routers.public-site.rule=Host(`${PUBLIC_SITE_DOMAIN}`) || Host(`www.${PUBLIC_SITE_DOMAIN}`) - traefik.http.routers.marketplace.rule=Host(`${PUBLIC_SITE_DOMAIN}`) && PathPrefix(`/marketplace`)
- traefik.http.routers.public-site.entrypoints=websecure - traefik.http.routers.marketplace.priority=20
- traefik.http.routers.public-site.tls.certresolver=letsencrypt
- traefik.http.routers.public-site.service=public-site-svc
- traefik.http.services.public-site-svc.loadbalancer.server.port=3003
# marketplace (port 3000) — should use its own subdomain
- traefik.http.routers.marketplace.rule=Host(`${MARKETPLACE_DOMAIN}`)
- traefik.http.routers.marketplace.entrypoints=websecure - traefik.http.routers.marketplace.entrypoints=websecure
- traefik.http.routers.marketplace.tls.certresolver=letsencrypt - traefik.http.routers.marketplace.tls.certresolver=letsencrypt
- traefik.http.routers.marketplace.service=marketplace-svc - traefik.http.routers.marketplace.service=marketplace-svc
- traefik.http.services.marketplace-svc.loadbalancer.server.port=3000 - traefik.http.services.marketplace-svc.loadbalancer.server.port=3000
# admin (port 3002) # dashboard (port 3001) — /dashboard path, priority 20
- traefik.http.routers.admin.rule=Host(`${ADMIN_DOMAIN}`) - traefik.http.routers.dashboard.rule=Host(`${PUBLIC_SITE_DOMAIN}`) && PathPrefix(`/dashboard`)
- traefik.http.routers.admin.entrypoints=websecure - traefik.http.routers.dashboard.priority=20
- traefik.http.routers.admin.tls.certresolver=letsencrypt
- traefik.http.routers.admin.service=admin-svc
- traefik.http.services.admin-svc.loadbalancer.server.port=3002
# dashboard (port 3001)
- traefik.http.routers.dashboard.rule=Host(`${DASHBOARD_DOMAIN}`)
- traefik.http.routers.dashboard.entrypoints=websecure - traefik.http.routers.dashboard.entrypoints=websecure
- traefik.http.routers.dashboard.tls.certresolver=letsencrypt - traefik.http.routers.dashboard.tls.certresolver=letsencrypt
- traefik.http.routers.dashboard.service=dashboard-svc - traefik.http.routers.dashboard.service=dashboard-svc
- traefik.http.services.dashboard-svc.loadbalancer.server.port=3001 - traefik.http.services.dashboard-svc.loadbalancer.server.port=3001
# admin (port 3002) — /admin path, priority 20
- traefik.http.routers.admin.rule=Host(`${PUBLIC_SITE_DOMAIN}`) && PathPrefix(`/admin`)
- traefik.http.routers.admin.priority=20
- traefik.http.routers.admin.entrypoints=websecure
- traefik.http.routers.admin.tls.certresolver=letsencrypt
- traefik.http.routers.admin.service=admin-svc
- traefik.http.services.admin-svc.loadbalancer.server.port=3002
# public site (port 3003) — root domain + tenant subdomains, priority 10
- traefik.http.routers.public-site.rule=Host(`${PUBLIC_SITE_DOMAIN}`) || Host(`www.${PUBLIC_SITE_DOMAIN}`) || HostRegexp(`{subdomain:[a-z0-9-]+}.${PUBLIC_SITE_DOMAIN}`)
- traefik.http.routers.public-site.priority=10
- traefik.http.routers.public-site.entrypoints=websecure
- traefik.http.routers.public-site.tls.certresolver=letsencrypt
- traefik.http.routers.public-site.service=public-site-svc
- traefik.http.services.public-site-svc.loadbalancer.server.port=3003
pgmanage: pgmanage:
image: cmdpromptinc/pgmanage-enterprise:latest image: cmdpromptinc/pgmanage-enterprise:latest