5.2 KiB
🎯 Overdrachtsdocument – Productie-deployment van Respellion Learning Platform met Portainer
Doel – Dit document geeft een complete handleiding zodat een ontwikkelaar of AI-agent de Respellion Learning Platform applicatie kan bouwen, configureren en in productie draaien op een Hetzner-VPS via Portainer.
1. Project-structuur
learning-platform/
│
├─ Dockerfile # Productie Dockerfile (Nginx + React/Vite)
├─ nginx.conf # Nginx configuratie voor Anthropic API proxy
├─ docker-compose.prod.yml # Productie-compose configuratie (Caddy SSL + Frontend)
└─ src/ # React frontend broncode
Opmerking: Deze applicatie is een 100% frontend applicatie ("Single Page Application"). De interne state wordt opgeslagen in
localStorage. Er is geen externe backend of database (zoals Postgres) nodig. De enige netwerk calls gaan via de interne Nginx proxy direct naar de Anthropic API.
2. Kernbestanden – inhoud & rationale
2.1 docker-compose.prod.yml
services:
frontend:
build: .
restart: always
expose:
- "80"
caddy:
image: caddy:2-alpine
restart: always
ports:
- "80:80"
- "443:443"
environment:
- DOMAIN_NAME=${DOMAIN_NAME}
entrypoint:
- /bin/sh
- -c
- |
# Build Caddyfile on container start
CLEAN_DOMAIN=$(printf '%s' "$DOMAIN_NAME" | tr -d ';')
cat > /etc/caddy/Caddyfile <<EOF
${CLEAN_DOMAIN} {
reverse_proxy /* frontend:80
}
EOF
# Run Caddy with the generated file
caddy run --config /etc/caddy/Caddyfile --adapter caddyfile
volumes:
- caddy_data:/data
- caddy_config:/config
depends_on:
- frontend
volumes:
caddy_data:
caddy_config:
Belangrijkste punten
| Item | Waarom |
|---|---|
frontend (Nginx) |
Bevat de React applicatie en proxy-configuratie voor Anthropic. Exposeert intern poort 80. |
caddy (Reverse Proxy) |
Ontvangt alle externe requests op poort 80 en 443 en haalt volautomatisch een SSL Let's Encrypt certificaat op voor DOMAIN_NAME. Stuurt verkeer door naar frontend:80. |
Volumes caddy_data/config |
Slaan de SSL certificaten persistent op zodat Caddy niet bij elke herstart de rate-limits van Let's Encrypt overschrijdt. |
2.2 Dockerfile (Productie)
De applicatie wordt in 2 fasen ("multi-stage") gebouwd:
- Node.js Build:
npm installennpm run buildworden uitgevoerd om de statische Vite applicatie te compileren naar dedist/map. - Nginx Serve: Een lightweight Nginx Alpine image wordt gestart. Het pakt de
dist/bestanden en pastnginx.conftoe om API-aanroepen (CORS blokkades) te omzeilen door als proxy te fungeren.
3. Omgevingsvariabelen (te definiëren in Portainer)
| Variabele | Voorbeeld | Toelichting |
|---|---|---|
DOMAIN_NAME |
leren.mijndomein.nl |
De domeinnaam die Caddy zal beveiligen met HTTPS. Zorg dat je DNS A-record naar je VPS-IP wijst. |
(De Anthropic API key wordt ingevuld via de instellingen in de applicatie (Settings menu) door een admin, en veilig opgeslagen in localStorage van de gebruiker. Hij hoeft dus niet in Portainer te staan!)
4. Deploy-procedure (stap-voor-stap)
Portainer – stack aanmaken / bijwerken
| Stap | Actie | Details |
|---|---|---|
| 1 | Navigeer naar Stacks → + Add stack | Geef een herkenbare naam (bijv. respellion-platform). |
| 2 | Repository URL invullen | https://github.com/<gebruiker>/learning-platform.git |
| 3 | Compose path = docker-compose.prod.yml |
Zorg dat dit exact overeenkomt met de bestandsnaam in de repo. |
| 4 | Environment variables toevoegen | Voeg DOMAIN_NAME toe. |
| 5 | Deploy the stack | Portainer start de applicatie en Caddy haalt direct het SSL certificaat op (max. 60 sec). |
| 6 | Controle | Surf naar https://jouw-domein.nl. Je zou de Respellion inlogscherm moeten zien. |
Handmatige Force-Rebuild
Wanneer de repo is geüpdatet en je wil de nieuwe versie afdwingen via command-line:
docker compose -f docker-compose.prod.yml up -d --build --no-cache
5. Veelvoorkomende valkuilen & Fixes
| Symptom | Oorzaak | Oplossing |
|---|---|---|
| SSL Error / ERR_CONNECTION_REFUSED | DNS is nog niet actief of poort 443 staat dicht in je firewall (Hetzner). | Check Hetzner Cloud Console en open TCP poort 80 & 443 in de Inbound Firewall. |
| Anthropic API Werkt Niet | Foute key of Nginx proxy mist configuratie. | Open de app, ga naar Admin -> Settings en vul je Anthropic Key in. Controleer ook of nginx.conf correct wordt ingeladen in Nginx. |
| Witte pagina na deploy | Oude Docker image wordt gebruikt. | Doe een force-rebuild (--build --no-cache) in Portainer of via de console. |
6. Checklist voor een nieuwe implementatie
- Repository up-to-date en gepusht naar
main. docker-compose.prod.ymlis gedefinieerd in Portainer.- Environment variable
DOMAIN_NAMEis correct ingesteld. - DNS A-Record staat op de juiste server.
- Na eerste inlog: Open "Admin" -> "Settings" en voeg de Anthropic API Key toe, klik op Opslaan.