hp-studios-ai-content-agent/deploy/README.md
DJP 7530f60007 Add deploy script, prod compose override, and Apache subpath proxy
For deployment to optical-dev.oliver.solutions under /hp-content-agent/.

- deploy/deploy.sh       idempotent bootstrap: secrets check, free-port
                         picker, build+up, migrations+seed, Apache Include
                         install + reload, UFW allow
- deploy/apache/*.conf.template   reverse-proxy snippet (API before SPA)
- deploy/README.md       runbook for first-time + re-deploy
- docker-compose.prod.yml  prod overrides: frontend target=prod (nginx),
                         uvicorn --workers 2, drops dev volume mounts
- docker-compose.yml     pinned project name (required on the shared
                         server per CLAUDE.md)
- frontend/nginx.conf    SPA fallback + asset caching, health endpoint
- frontend/Dockerfile    VITE_BASE_PATH build arg for subpath deploys
- frontend/vite.config.ts  reads VITE_BASE_PATH

Public: https://optical-dev.oliver.solutions/hp-content-agent/

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-04-22 15:23:51 -04:00

3.9 KiB
Raw Permalink Blame History

Deploy — HP Studios AI Content Agent

Idempotent deployment to optical-dev.oliver.solutions (or any shared Apache + Docker Linux box).

Public URL: https://optical-dev.oliver.solutions/hp-content-agent/

First-time setup on the server

# SSH in, clone the repo somewhere you want it to live
ssh you@optical-dev.oliver.solutions
sudo git clone git@bitbucket.org:zlalani/hp-studios-ai-content-agent.git /opt/hp-studios-ai-content-agent
cd /opt/hp-studios-ai-content-agent

# Bootstrap .env (will error and tell you what secrets to fill)
sudo ./deploy/deploy.sh
# Edit /opt/hp-studios-ai-content-agent/.env and fill:
#   ANTHROPIC_API_KEY=...
#   OPENAI_API_KEY=... (or VOYAGE_API_KEY)
# Everything else is auto-populated.

# Re-run to actually deploy
sudo ./deploy/deploy.sh

The script handles everything else:

  • Picks free host ports in 2000029999, stable across reruns
  • Builds + starts containers with project name hp-studios-ai-content-agent
  • Runs Alembic migrations + seeds admin user (first run prints credentials)
  • Renders the Apache snippet with the chosen ports
  • Adds an Include line to the vhost and reloads Apache
  • Ensures UFW allows 22/80

Re-deploy (after a git pull)

cd /opt/hp-studios-ai-content-agent
sudo git pull
sudo ./deploy/deploy.sh

Safe to re-run any time. Existing ports, secrets, and the admin user are preserved.

Apache integration

The script writes a rendered proxy snippet to deploy/apache/hp-content-agent.conf and adds an Include line inside the vhost at /etc/apache2/sites-available/optical-dev.oliver.solutions.conf. If the file doesn't exist, the script prints the Include line for manual addition.

The snippet proxies:

  • /hp-content-agent/api/127.0.0.1:$API_HOST_PORT
  • /hp-content-agent/127.0.0.1:$FRONTEND_HOST_PORT

Order matters in the rendered file — API rule precedes the catch-all frontend rule.

Common operations

# Status
docker compose -p hp-studios-ai-content-agent -f docker-compose.yml -f docker-compose.prod.yml ps

# Logs
docker compose -p hp-studios-ai-content-agent -f docker-compose.yml -f docker-compose.prod.yml logs -f api worker

# Shell into API container
docker compose -p hp-studios-ai-content-agent -f docker-compose.yml -f docker-compose.prod.yml exec api bash

# Rebuild just the frontend (after a merge that only changed frontend)
docker compose -p hp-studios-ai-content-agent -f docker-compose.yml -f docker-compose.prod.yml up -d --build frontend

# Tear down (keeps data volume; use -v to also wipe the DB)
docker compose -p hp-studios-ai-content-agent -f docker-compose.yml -f docker-compose.prod.yml down

Troubleshooting

  • 404 at /hp-content-agent/ — check the Include line is in the vhost and apache2ctl configtest passes. Check deploy/apache/hp-content-agent.conf points to the ports in docker compose ps.
  • API calls from the SPA 404 — open the browser Network tab. If requests go to /api/... instead of /hp-content-agent/api/..., the frontend wasn't rebuilt with VITE_API_URL=/hp-content-agent/api. Force a rebuild: docker compose … up -d --build frontend.
  • Port collisions — the script picks in 2000029999 and writes to .env. Delete the four *_HOST_PORT lines and re-run to reassign.
  • Cookies / auth fail — the JWT cookie is set on the root domain optical-dev.oliver.solutions with path /, so the subpath is fine. If requests fail with 401, check that CORS_ORIGIN=https://optical-dev.oliver.solutions is in .env (the script sets it).

What the script does not do

  • TLS / Let's Encrypt — handled by whatever already serves the vhost.
  • DNS — uses the existing optical-dev.oliver.solutions hostname, no record changes.
  • Backup — docker compose down keeps the Postgres data volume by default. Dump with docker compose … exec postgres pg_dump -U hp hp_content_agent > backup.sql if you want a snapshot before a risky change.