Skip to content

Deployment

Backend

Environment Variables

# Production
DATABASE_URL=postgresql://user:pass@host:5432/saas_courier
SECRET_KEY=your-production-secret
ENVIRONMENT=production

# Optional
RESEND_API_KEY=your-resend-api-key
AERODATABOX_API_KEY=your-rapidapi-key

Running

# Build
uv run pip install -e .

# Run
uv run gunicorn main:app -w 4 -k uvicorn.workers.UvicornWorker -b 0.0.0.0:8000

Frontend

Build

cd saas-fronted
uv run flet build web
# Output in ./build/web

Environment

# .env
API_BASE_URL=https://api.saas-courier.com
WS_BASE_URL=wss://api.saas-courier.com

Documentation (Cloudflare Workers)

Architecture

The documentation site uses Cloudflare Workers with KV storage for serving static files.

┌─────────────┐     ┌──────────────────┐     ┌─────────────┐
│  GitHub     │────▶│  GitHub Actions │────▶│ Cloudflare  │
│  Push       │     │  mkdocs build   │     │   Workers   │
└─────────────┘     │  wrangler deploy│     │  + KV Store│
                   └──────────────────┘     └─────────────┘

Requirements

Requirement Version Notes
Node.js >= 22.0.0 Wrangler 4.x requires Node.js 22+
Python 3.12 For mkdocs
Wrangler 4.x Installed via npm

GitHub Actions Workflow

Location: .github/workflows/deploy-docs.yml

Trigger paths:

on:
  push:
    branches: [main]
    paths:
      - 'docs/**'
      - 'mkdocs.yml'
      - 'wrangler.toml'
      - '.github/workflows/**'
      - 'workers-site/**'

⚠️ Important: The workers-site/** and .github/workflows/** paths must be included in the trigger configuration. Without these, workflow may not trigger on workers-site changes or workflow modifications.

Wrangler Configuration

File: wrangler.toml

name = "saas-courier-docs"
compatibility_date = "2026-05-15"
main = "workers-site/index.js"

compatibility_flags = ["nodejs_compat"]

[[kv_namespaces]]
binding = "ASSETS"
id = "af529f0e7da645da9d39ed407c5a11f2"

[site]
bucket = "./site"
Field Description
main Entry point for Cloudflare Workers
[site] bucket Static files output directory (from mkdocs build)
[kv_namespaces] KV namespace for asset caching

Workers Site

The workers-site/index.js file handles KV-based asset serving:

import { getAssetFromKV } from '@cloudflare/kv-asset-handler';

addEventListener('fetch', event => {
  event.respondWith(handleEvent(event));
});

async function handleEvent(event) {
  try {
    return await getAssetFromKV(event);
  } catch (e) {
    console.error('Error serving asset:', e);
    return new Response('Error loading page', { status: 500 });
  }
}

Deploy

# Preview (develop)
git push origin develop

# Production (main)
git push origin main

Custom Domain

saas-courier-docs.juanant0ni0.workers.dev

Troubleshooting

Wrangler requires Node.js v22.0.0

Error:

Wrangler requires at least Node.js v22.0.0. You are using v20.20.2.

Solution: Update Node.js version in GitHub Actions workflow:

- name: Setup Node.js
  uses: actions/setup-node@v4
  with:
    node-version: '22.12.0'

Build failed - Could not resolve "@cloudflare/kv-asset-handler"

Cause: Missing or incorrect workers-site configuration.

Solution: Ensure: 1. workers-site/index.js exists in repository 2. main = "workers-site/index.js" is in wrangler.toml 3. @cloudflare/kv-asset-handler is in package.json dependencies

Workflow not triggering

Cause: Missing paths in workflow trigger configuration.

Solution: Ensure trigger includes:

paths:
  - 'docs/**'
  - 'mkdocs.yml'
  - 'wrangler.toml'
  - '.github/workflows/**'
  - 'workers-site/**'

Workers Sites deprecated warning

Warning:

Because you've defined a [site] configuration, we're defaulting to "workers-site"
for the deprecated `site.entry-point` field.

This is expected. The workers-site approach is still functional.


Environment Reference

Variable Description
DATABASE_URL PostgreSQL connection string
SECRET_KEY JWT signing key (min 32 chars)
ENVIRONMENT development or production
CORS_ORIGINS Allowed origins (comma-separated)