- Restore blue PageHeader on Dashboard (/app-components) - Update homepage (/) with subtle header design without blue bar - Add uniform PageHeader styling to application edit page - Fix Rapporten link on homepage to point to /reports overview - Improve header descriptions spacing for better readability
18 KiB
Deployment Advies - CMDB Insight 🎯
Datum: {{ vandaag }}
Aanbeveling: Azure App Service (Basic Tier)
Geschatte kosten: ~€20-25/maand
📊 Analyse van Jouw Situatie
Jouw Requirements:
- ✅ Managed service (geen serverbeheer) - Jouw voorkeur
- ✅ Interne productie (niet bedrijfskritisch)
- ✅ 20 gebruikers (kleine team)
- ✅ Downtime acceptabel (kan zelfs 's avonds/weekend uit)
- ✅ Budget geen probleem (~€20-25/maand is prima)
- ✅ Monitoring via Elastic stack (kan geïntegreerd worden)
- ✅ NEN 7510 compliance (vereist)
- ✅ Updates: Initieel dagelijks, daarna wekelijks/maandelijks
Waarom Azure App Service Perfect Past:
-
Managed Service ⭐
- Geen serverbeheer, SSH, Linux configuratie
- Azure beheert alles (updates, security patches, scaling)
- Perfect voor jouw voorkeur: "liever niet als het niet hoeft"
-
Eenvoudig & Snel
- Setup in ~15 minuten
- Automatische SSL/TLS certificaten
- Integratie met Azure DevOps (je pipeline werkt al!)
-
Kosten-Effectief
- Basic B1 plan: ~€15-25/maand
- Voldoende voor 20 gebruikers
- Geen verborgen kosten
-
Flexibel
- Deployment slots voor testen (staging → productie)
- Eenvoudige rollback
- Integratie met Azure Key Vault voor secrets
-
Monitoring & Compliance
- Integratie met Azure Monitor → kan naar Elastic stack
- Logging en audit trails (NEN 7510 compliance)
- Health checks ingebouwd
🚀 Aanbevolen Architectuur
┌─────────────────────────────────────────┐
│ Azure App Service Plan (B1) │
│ │
│ ┌──────────────┐ ┌──────────────┐ │
│ │ Frontend │ │ Backend │ │
│ │ Web App │ │ Web App │ │
│ │ (Container) │ │ (Container) │ │
│ └──────────────┘ └──────┬───────┘ │
└──────────────────────────┼─────────────┘
│
┌──────────────┼──────────────┐
│ │ │
┌───────▼──────┐ ┌─────▼──────┐ ┌────▼─────┐
│ Azure Key │ │ Azure │ │ Elastic │
│ Vault │ │ Monitor │ │ Stack │
│ (Secrets) │ │ (Logs) │ │ (Export) │
└──────────────┘ └────────────┘ └──────────┘
Componenten:
- App Service Plan B1: 1 vCPU, 1.75GB RAM (voldoende voor 20 gebruikers)
- 2 Web Apps: Frontend + Backend (delen dezelfde plan = kostenbesparend)
- Azure Key Vault: Voor secrets (Jira credentials, session secrets)
- Azure Monitor: Logging → kan geëxporteerd worden naar Elastic stack
- Azure Storage: Voor SQLite database (als je SQLite blijft gebruiken)
Kosten Breakdown:
- App Service Plan B1: ~€15-20/maand
- Azure Key Vault: ~€1-2/maand
- Azure Storage (SQLite): ~€1-2/maand
- Totaal: ~€17-24/maand
📋 Stap-voor-Stap Deployment Plan
Fase 1: Basis Setup (15 minuten)
Stap 1.1: Resource Group Aanmaken
az group create \
--name rg-cmdb-gui-prod \
--location westeurope
Stap 1.2: App Service Plan Aanmaken
az appservice plan create \
--name plan-cmdb-gui-prod \
--resource-group rg-cmdb-gui-prod \
--sku B1 \
--is-linux
Waarom B1?
- 1 vCPU, 1.75GB RAM
- Voldoende voor 20 gebruikers
- Goede prijs/prestatie verhouding
Stap 1.3: Web Apps Aanmaken
# Backend Web App
az webapp create \
--name cmdb-backend-prod \
--resource-group rg-cmdb-gui-prod \
--plan plan-cmdb-gui-prod \
--deployment-container-image-name zdlas.azurecr.io/cmdb-insight/backend:latest
# Frontend Web App
az webapp create \
--name cmdb-frontend-prod \
--resource-group rg-cmdb-gui-prod \
--plan plan-cmdb-gui-prod \
--deployment-container-image-name zdlas.azurecr.io/cmdb-insight/frontend:latest
Fase 2: ACR Authentication (5 minuten)
Stap 2.1: Enable Managed Identity
# Backend
az webapp identity assign \
--name cmdb-backend-prod \
--resource-group rg-cmdb-gui-prod
# Frontend
az webapp identity assign \
--name cmdb-frontend-prod \
--resource-group rg-cmdb-gui-prod
Stap 2.2: Grant ACR Pull Permissions
# Get managed identity principal ID
BACKEND_PRINCIPAL_ID=$(az webapp identity show \
--name cmdb-backend-prod \
--resource-group rg-cmdb-gui-prod \
--query principalId -o tsv)
FRONTEND_PRINCIPAL_ID=$(az webapp identity show \
--name cmdb-frontend-prod \
--resource-group rg-cmdb-gui-prod \
--query principalId -o tsv)
# Get ACR resource ID
ACR_ID=$(az acr show \
--name zdlas \
--resource-group <acr-resource-group> \
--query id -o tsv)
# Grant AcrPull role
az role assignment create \
--assignee $BACKEND_PRINCIPAL_ID \
--role AcrPull \
--scope $ACR_ID
az role assignment create \
--assignee $FRONTEND_PRINCIPAL_ID \
--role AcrPull \
--scope $ACR_ID
Stap 2.3: Configure Container Settings
# Backend
az webapp config container set \
--name cmdb-backend-prod \
--resource-group rg-cmdb-gui-prod \
--docker-custom-image-name zdlas.azurecr.io/cmdb-insight/backend:latest \
--docker-registry-server-url https://zdlas.azurecr.io
# Frontend
az webapp config container set \
--name cmdb-frontend-prod \
--resource-group rg-cmdb-gui-prod \
--docker-custom-image-name zdlas.azurecr.io/cmdb-insight/frontend:latest \
--docker-registry-server-url https://zdlas.azurecr.io
Fase 3: Environment Variabelen (10 minuten)
Stap 3.1: Azure Key Vault Aanmaken
az keyvault create \
--name kv-cmdb-gui-prod \
--resource-group rg-cmdb-gui-prod \
--location westeurope \
--sku standard
Stap 3.2: Secrets Toevoegen aan Key Vault
# Jira Personal Access Token (of OAuth credentials)
az keyvault secret set \
--vault-name kv-cmdb-gui-prod \
--name JiraPat \
--value "your-jira-pat-token"
# Session Secret
az keyvault secret set \
--vault-name kv-cmdb-gui-prod \
--name SessionSecret \
--value "$(openssl rand -hex 32)"
# Jira Schema ID
az keyvault secret set \
--vault-name kv-cmdb-gui-prod \
--name JiraSchemaId \
--value "your-schema-id"
# Anthropic API Key (optioneel)
az keyvault secret set \
--vault-name kv-cmdb-gui-prod \
--name AnthropicApiKey \
--value "your-anthropic-key"
Stap 3.3: Grant Web Apps Access tot Key Vault
# Backend
az keyvault set-policy \
--name kv-cmdb-gui-prod \
--object-id $BACKEND_PRINCIPAL_ID \
--secret-permissions get list
# Frontend (als nodig)
az keyvault set-policy \
--name kv-cmdb-gui-prod \
--object-id $FRONTEND_PRINCIPAL_ID \
--secret-permissions get list
Stap 3.4: Configure App Settings met Key Vault References
# Backend App Settings
az webapp config appsettings set \
--name cmdb-backend-prod \
--resource-group rg-cmdb-gui-prod \
--settings \
NODE_ENV=production \
PORT=3001 \
JIRA_BASE_URL=https://jira.zuyderland.nl \
JIRA_SCHEMA_ID="@Microsoft.KeyVault(SecretUri=https://kv-cmdb-gui-prod.vault.azure.net/secrets/JiraSchemaId/)" \
JIRA_PAT="@Microsoft.KeyVault(SecretUri=https://kv-cmdb-gui-prod.vault.azure.net/secrets/JiraPat/)" \
SESSION_SECRET="@Microsoft.KeyVault(SecretUri=https://kv-cmdb-gui-prod.vault.azure.net/secrets/SessionSecret/)" \
ANTHROPIC_API_KEY="@Microsoft.KeyVault(SecretUri=https://kv-cmdb-gui-prod.vault.azure.net/secrets/AnthropicApiKey/)" \
FRONTEND_URL=https://cmdb-frontend-prod.azurewebsites.net
# Frontend App Settings
az webapp config appsettings set \
--name cmdb-frontend-prod \
--resource-group rg-cmdb-gui-prod \
--settings \
VITE_API_URL=https://cmdb-backend-prod.azurewebsites.net/api
Fase 4: SSL/TLS & Domain (10 minuten)
Stap 4.1: Gratis SSL via App Service
App Service heeft automatisch SSL voor *.azurewebsites.net:
- Frontend:
https://cmdb-frontend-prod.azurewebsites.net - Backend:
https://cmdb-backend-prod.azurewebsites.net
Geen configuratie nodig! SSL werkt automatisch.
Stap 4.2: Custom Domain (Optioneel - Later)
Als je later een custom domain wilt (bijv. cmdb.zuyderland.nl):
# Add custom domain
az webapp config hostname add \
--webapp-name cmdb-frontend-prod \
--resource-group rg-cmdb-gui-prod \
--hostname cmdb.zuyderland.nl
# Bind SSL certificate (App Service Certificate of Let's Encrypt)
az webapp config ssl bind \
--name cmdb-frontend-prod \
--resource-group rg-cmdb-gui-prod \
--certificate-thumbprint <thumbprint> \
--ssl-type SNI
Fase 5: Monitoring & Logging (15 minuten)
Stap 5.1: Enable Application Insights
# Create Application Insights
az monitor app-insights component create \
--app cmdb-gui-prod \
--location westeurope \
--resource-group rg-cmdb-gui-prod \
--application-type web
# Get Instrumentation Key
INSTRUMENTATION_KEY=$(az monitor app-insights component show \
--app cmdb-gui-prod \
--resource-group rg-cmdb-gui-prod \
--query instrumentationKey -o tsv)
# Configure App Settings
az webapp config appsettings set \
--name cmdb-backend-prod \
--resource-group rg-cmdb-gui-prod \
--settings \
APPINSIGHTS_INSTRUMENTATIONKEY=$INSTRUMENTATION_KEY \
APPLICATIONINSIGHTS_CONNECTION_STRING="InstrumentationKey=$INSTRUMENTATION_KEY"
Stap 5.2: Export naar Elastic Stack (Later)
Azure Monitor kan geëxporteerd worden naar Elastic stack via:
- Azure Monitor → Log Analytics Workspace → Export naar Elastic
- Of gebruik Azure Function om logs te streamen naar Elastic
Zie: docs/ELASTIC-STACK-INTEGRATION.md (te maken als nodig)
Fase 6: Test & Start (5 minuten)
Stap 6.1: Start Web Apps
az webapp start --name cmdb-backend-prod --resource-group rg-cmdb-gui-prod
az webapp start --name cmdb-frontend-prod --resource-group rg-cmdb-gui-prod
Stap 6.2: Test Health Endpoints
# Backend health check
curl https://cmdb-backend-prod.azurewebsites.net/api/health
# Frontend
curl https://cmdb-frontend-prod.azurewebsites.net
Stap 6.3: Check Logs
# Backend logs
az webapp log tail --name cmdb-backend-prod --resource-group rg-cmdb-gui-prod
# Frontend logs
az webapp log tail --name cmdb-frontend-prod --resource-group rg-cmdb-gui-prod
🔒 NEN 7510 Compliance
Wat App Service Biedt:
-
Encryption
- ✅ Data at rest: Azure Storage encryption
- ✅ Data in transit: TLS 1.2+ (automatisch)
- ✅ Secrets: Azure Key Vault (encrypted)
-
Access Control
- ✅ Azure AD integratie (RBAC)
- ✅ Managed Identity (geen credentials in code)
- ✅ Network isolation (optioneel via VNet integration)
-
Logging & Audit
- ✅ Application Insights (alle API calls)
- ✅ Azure Monitor (resource logs)
- ✅ Activity Logs (wie deed wat)
- ✅ Export naar Elastic stack mogelijk
-
Backup & Recovery
- ✅ App Service backups (optioneel)
- ✅ Key Vault soft delete (recovery)
- ⚠️ Opmerking: Jouw data wordt gesynchroniseerd vanuit Jira, dus backup is minder kritisch
Compliance Checklist:
- Secrets in Azure Key Vault (niet in code)
- HTTPS only (automatisch via App Service)
- Logging ingeschakeld (Application Insights)
- Access control (Azure AD RBAC)
- Audit trail (Activity Logs)
- Encryption at rest (Azure Storage)
- Encryption in transit (TLS 1.2+)
Zie: docs/NEN-7510-COMPLIANCE.md (te maken als nodig)
🔐 VPN/Private Network Opties (Voor Later)
Optie 1: App Service VNet Integration
Wat het doet:
- Web App verbindt met Azure Virtual Network
- Toegang tot resources in VNet (bijv. database, andere services)
- Niet: Maakt de app niet privé (app blijft publiek bereikbaar)
Wanneer gebruiken:
- Als je een database in VNet hebt
- Als je andere Azure services in VNet moet bereiken
Setup:
# Create VNet (als nog niet bestaat)
az network vnet create \
--name vnet-cmdb-gui \
--resource-group rg-cmdb-gui-prod \
--address-prefix 10.0.0.0/16
# Create subnet
az network vnet subnet create \
--name subnet-app-service \
--resource-group rg-cmdb-gui-prod \
--vnet-name vnet-cmdb-gui \
--address-prefix 10.0.1.0/24
# Integrate Web App with VNet
az webapp vnet-integration add \
--name cmdb-backend-prod \
--resource-group rg-cmdb-gui-prod \
--vnet vnet-cmdb-gui \
--subnet subnet-app-service
Optie 2: Private Endpoint (Maakt App Privé)
Wat het doet:
- Maakt de Web App alleen bereikbaar via private IP
- Vereist VPN/ExpressRoute om toegang te krijgen
- Kosten: ~€7-10/maand per Private Endpoint
Wanneer gebruiken:
- Als je de app alleen via VPN wilt bereiken
- Als je geen publieke toegang wilt
Setup:
# Create Private Endpoint
az network private-endpoint create \
--name pe-cmdb-backend \
--resource-group rg-cmdb-gui-prod \
--vnet-name vnet-cmdb-gui \
--subnet subnet-private-endpoint \
--private-connection-resource-id /subscriptions/<sub-id>/resourceGroups/rg-cmdb-gui-prod/providers/Microsoft.Web/sites/cmdb-backend-prod \
--group-id sites \
--connection-name pe-connection-backend
Optie 3: App Service Environment (ASE) - Enterprise
Wat het doet:
- Volledig geïsoleerde App Service omgeving
- Alleen bereikbaar via VNet
- Kosten: ~€1000+/maand (te duur voor jouw use case)
Niet aanbevolen voor jouw situatie (te duur, overkill).
🔄 Updates Deployen
Automatische Deployment (Via Pipeline)
Je Azure DevOps pipeline bouwt al automatisch images. Voor automatische deployment:
Optie A: Continuous Deployment (Aanbevolen)
# Enable continuous deployment
az webapp deployment container config \
--name cmdb-backend-prod \
--resource-group rg-cmdb-gui-prod \
--enable-cd true
# Configure deployment slot (staging)
az webapp deployment slot create \
--name cmdb-backend-prod \
--resource-group rg-cmdb-gui-prod \
--slot staging
# Swap staging → production (zero-downtime)
az webapp deployment slot swap \
--name cmdb-backend-prod \
--resource-group rg-cmdb-gui-prod \
--slot staging \
--target-slot production
Optie B: Manual Deployment (Eenvoudig)
# Pull nieuwe image en restart
az webapp restart --name cmdb-backend-prod --resource-group rg-cmdb-gui-prod
az webapp restart --name cmdb-frontend-prod --resource-group rg-cmdb-gui-prod
Workflow:
- Push code naar
mainbranch - Pipeline bouwt nieuwe images →
zdlas.azurecr.io/.../backend:88767 - Images worden getagged als
latest - Restart Web Apps → pull nieuwe
latestimage
📊 Monitoring Setup
Azure Monitor → Elastic Stack Export
Optie 1: Log Analytics Workspace Export
# Create Log Analytics Workspace
az monitor log-analytics workspace create \
--workspace-name law-cmdb-gui-prod \
--resource-group rg-cmdb-gui-prod \
--location westeurope
# Configure App Service to send logs
az webapp log config \
--name cmdb-backend-prod \
--resource-group rg-cmdb-gui-prod \
--application-logging filesystem \
--detailed-error-messages true \
--failed-request-tracing true \
--web-server-logging filesystem
# Export to Elastic (via Azure Function of Event Hub)
# Zie: docs/ELASTIC-STACK-INTEGRATION.md
Optie 2: Application Insights → Elastic
Application Insights kan geëxporteerd worden via:
- Continuous Export (deprecated, maar werkt nog)
- Azure Function die Application Insights API gebruikt
- Log Analytics Workspace → Export naar Elastic
✅ Deployment Checklist
Pre-Deployment:
- Resource Group aangemaakt
- App Service Plan aangemaakt (B1)
- Web Apps aangemaakt (backend + frontend)
- ACR authentication geconfigureerd
- Key Vault aangemaakt
- Secrets toegevoegd aan Key Vault
- App Settings geconfigureerd (met Key Vault references)
- Application Insights ingeschakeld
Post-Deployment:
- Health checks werken
- SSL/TLS werkt (automatisch)
- Logging werkt
- Monitoring ingesteld
- Team geïnformeerd over URLs
- Documentatie bijgewerkt
🎯 Volgende Stappen
- Start met Fase 1-3 (Basis setup + ACR + Environment variabelen)
- Test de applicatie (Fase 6)
- Configureer monitoring (Fase 5)
- Documenteer voor team (URLs, credentials, etc.)
📚 Gerelateerde Documentatie
- Quick Deployment Guide:
docs/QUICK-DEPLOYMENT-GUIDE.md - Production Deployment:
docs/PRODUCTION-DEPLOYMENT.md - Azure Deployment Summary:
docs/AZURE-DEPLOYMENT-SUMMARY.md
❓ Vragen?
Veelgestelde vragen:
Q: Moet ik PostgreSQL gebruiken of kan ik SQLite houden?
A: SQLite is prima voor 20 gebruikers. Als je later groeit, kun je migreren naar PostgreSQL.
Q: Hoe update ik de applicatie?
A: Push naar main → Pipeline bouwt images → Restart Web Apps (of gebruik deployment slots voor zero-downtime).
Q: Kan ik de app 's avonds/weekend uitzetten?
A: Ja! az webapp stop --name cmdb-backend-prod --resource-group rg-cmdb-gui-prod (bespaart kosten).
Q: Hoe integreer ik met Elastic stack?
A: Exporteer Azure Monitor logs via Log Analytics Workspace → Elastic (zie Fase 5).
🎉 Success!
Je hebt nu een compleet deployment plan voor Azure App Service!
Start met Fase 1 en laat me weten als je hulp nodig hebt bij een specifieke stap.