Self-Hosting ArchonHQ
Deploy ArchonHQ on your own server with Docker, Coolify, and a Cloudflare tunnel.
Self-Hosting ArchonHQ
Run ArchonHQ on your own infrastructure. Requires Docker, PostgreSQL, and a Node.js environment.
Requirements
- Docker and Docker Compose
- PostgreSQL 15+ (or use the bundled Docker Compose service)
- A domain with HTTPS (required for NextAuth cookie security)
- Google OAuth credentials for sign-in
- Minimum 1 GB RAM, 1 vCPU
Quick start with Docker Compose
git clone https://github.com/MikeS071/Mission-Control.git
cd Mission-Control
cp .env.example .env.localEdit .env.local with your values (see Configuration →), then:
docker compose up -dThe dashboard is available at http://localhost:3000.
Environment variables
See the full reference at Configuration →. Minimum required:
# NextAuth
NEXTAUTH_URL=https://your-domain.com
NEXTAUTH_SECRET=<32+ char random string>
# Google OAuth
GOOGLE_CLIENT_ID=<from Google Cloud Console>
GOOGLE_CLIENT_SECRET=<from Google Cloud Console>
# Database
DATABASE_URL=postgresql://user:password@host:5432/mission_control
# ArchonHQ API secret (used by agents)
API_SECRET=<32+ char random string>Database details setup
Create the database and run migrations:
# Create database
psql -U postgres -c "CREATE DATABASE mission_control;"
# Run migrations (handled automatically on first start)
docker compose run --rm app npm run db:migrateGoogle OAuth setup
- Go to Google Cloud Console → APIs & Services → Credentials
- Create an OAuth 2.0 client ID (Web application)
- Add authorised redirect URI:
https://your-domain.com/api/auth/callback/google - Copy client ID and secret to
.env.local
Running behind a reverse proxy
ArchonHQ works behind nginx, Caddy, or Cloudflare Tunnel. The app must see HTTPS at the NEXTAUTH_URL level.
Recommended: Cloudflare Tunnel, zero-config TLS, no open inbound ports:
cloudflared tunnel --url http://localhost:3000Point the tunnel to https://your-domain.com in the Cloudflare dashboard.
AiPipe (optional)
AiPipe is a separate Go binary that handles AI routing. It runs alongside the dashboard.
# Download the latest binary
curl -L https://github.com/MikeS071/AiPipe/releases/latest/download/aipipe-linux-amd64 \
-o /usr/local/bin/aipipe && chmod +x /usr/local/bin/aipipe
# Create config
mkdir -p ~/.config/aipipe
cat > ~/.config/aipipe/env << 'EOF'
OPENAI_API_KEY=sk-...
ANTHROPIC_API_KEY=sk-ant-...
AIPIPE_ADMIN_SECRET=<32+ char random string>
EOF
# Run as systemd service
aipipe --install-service
systemctl --user enable aipipe
systemctl --user start aipipeSet AIPIPE_URL=http://127.0.0.1:8082 in your .env.local to connect.
Updating
git pull origin main
docker compose down
docker compose up -d --buildMigrations run automatically on startup.
Backup
Back up the PostgreSQL database:
pg_dump mission_control > backup_$(date +%Y%m%d).sqlNo file system state beyond the database is required, all data lives in Postgres.
Troubleshooting
Login redirects loop:
- Verify
NEXTAUTH_URLmatches the exact URL you're accessing (including https) - Check that the Google OAuth redirect URI matches exactly
Dashboard loads but shows "Unauthorized":
- Confirm
API_SECRETmatches in both.env.localand anywhere agents sendAuthorization: Bearer
AiPipe not routing:
- Check
aipipe healthz:curl http://127.0.0.1:8082/healthz - Verify
AIPIPE_URLis set in.env.local - Confirm
AIPIPE_ADMIN_SECRETis set and matches in both services