diff --git a/apps/pocket-id/README.md b/apps/pocket-id/README.md new file mode 100644 index 0000000..2362211 --- /dev/null +++ b/apps/pocket-id/README.md @@ -0,0 +1,53 @@ +# Pocket ID Deployment + +This directory contains the Kubernetes manifests for the Pocket ID deployment at https://auth.basicstack.de + +## Components + +- **deployment.yaml**: Main Pocket ID application deployment + - Image: `ghcr.io/pocket-id/pocket-id:v2.9.0` + - Resources: 100m CPU / 256Mi RAM (requests), 500m CPU / 512Mi RAM (limits) + - Healthchecks: liveness and readiness probes using built-in healthcheck command + +- **service.yaml**: ClusterIP service exposing port 1411 + +- **pvc.yaml**: PersistentVolumeClaim for application data + - **CRITICAL**: Has `argocd.argoproj.io/sync-options: Delete=false` annotation to prevent data loss + - Storage: 5Gi on local-path storage class + - Contains all user accounts, OIDC clients, and application configuration + +- **ingress.yaml**: Traefik ingress with TLS + - Host: auth.basicstack.de + - TLS certificate managed by cert-manager (letsencrypt-prod) + +- **pocket-id-secrets-sealed.yaml**: SealedSecret containing ENCRYPTION_KEY + - Managed by sealed-secrets controller + - Automatically unsealed to create `pocket-id-secrets` Secret + +## Migration to Argo CD + +This deployment was migrated from manual kubectl deployments to Argo CD GitOps on 2026-07-12. + +### Safety Measures + +1. **PVC Protection**: The PVC has `Delete=false` sync option to prevent accidental deletion +2. **Resource Adoption**: Existing resources are adopted by Argo CD without recreation +3. **Data Preservation**: The existing PVC volume is reused, preserving all data +4. **Secret Management**: Secrets are managed via SealedSecrets for secure GitOps +5. **TLS Certificate**: Managed by cert-manager, automatically renewed + +### Verification Steps + +After Argo CD sync: +1. Verify all resources are healthy in Argo CD UI +2. Check pod is running: `kubectl get pods -n pocket-id` +3. Verify web UI is accessible: https://auth.basicstack.de +4. Test OIDC login flow with an existing client +5. Verify all existing OIDC clients are still present in admin UI + +### Important Notes + +- **DO NOT** delete the PVC - it contains all application data +- The ENCRYPTION_KEY in the sealed secret must match the existing key to decrypt stored data +- All existing OIDC client IDs and secrets are preserved in the PVC data +- The TLS secret is managed by cert-manager and should NOT be committed to Git diff --git a/apps/pocket-id/deployment.yaml b/apps/pocket-id/deployment.yaml new file mode 100644 index 0000000..6c5fe57 --- /dev/null +++ b/apps/pocket-id/deployment.yaml @@ -0,0 +1,70 @@ +apiVersion: apps/v1 +kind: Deployment +metadata: + name: pocket-id + namespace: pocket-id +spec: + replicas: 1 + selector: + matchLabels: + app: pocket-id + strategy: + type: Recreate + template: + metadata: + labels: + app: pocket-id + spec: + containers: + - name: pocket-id + image: ghcr.io/pocket-id/pocket-id:v2.9.0 + imagePullPolicy: IfNotPresent + ports: + - containerPort: 1411 + name: http + protocol: TCP + env: + - name: APP_URL + value: https://auth.basicstack.de + - name: ENCRYPTION_KEY + valueFrom: + secretKeyRef: + key: ENCRYPTION_KEY + name: pocket-id-secrets + - name: TRUST_PROXY + value: "true" + - name: PUID + value: "1000" + - name: PGID + value: "1000" + volumeMounts: + - mountPath: /app/data + name: data + livenessProbe: + exec: + command: + - /app/pocket-id + - healthcheck + failureThreshold: 2 + initialDelaySeconds: 10 + periodSeconds: 90 + timeoutSeconds: 5 + readinessProbe: + exec: + command: + - /app/pocket-id + - healthcheck + initialDelaySeconds: 5 + periodSeconds: 10 + timeoutSeconds: 5 + resources: + limits: + cpu: 500m + memory: 512Mi + requests: + cpu: 100m + memory: 256Mi + volumes: + - name: data + persistentVolumeClaim: + claimName: pocket-id-data diff --git a/apps/pocket-id/ingress.yaml b/apps/pocket-id/ingress.yaml new file mode 100644 index 0000000..90c02ba --- /dev/null +++ b/apps/pocket-id/ingress.yaml @@ -0,0 +1,25 @@ +apiVersion: networking.k8s.io/v1 +kind: Ingress +metadata: + name: pocket-id + namespace: pocket-id + annotations: + cert-manager.io/cluster-issuer: letsencrypt-prod + traefik.ingress.kubernetes.io/router.entrypoints: web,websecure +spec: + ingressClassName: traefik + rules: + - host: auth.basicstack.de + http: + paths: + - path: / + pathType: Prefix + backend: + service: + name: pocket-id + port: + number: 1411 + tls: + - hosts: + - auth.basicstack.de + secretName: pocket-id-tls diff --git a/apps/pocket-id/pvc.yaml b/apps/pocket-id/pvc.yaml new file mode 100644 index 0000000..046f8ec --- /dev/null +++ b/apps/pocket-id/pvc.yaml @@ -0,0 +1,16 @@ +apiVersion: v1 +kind: PersistentVolumeClaim +metadata: + name: pocket-id-data + namespace: pocket-id + annotations: + # Prevent Argo CD from deleting this PVC to avoid data loss + argocd.argoproj.io/sync-options: Delete=false +spec: + accessModes: + - ReadWriteOnce + resources: + requests: + storage: 5Gi + storageClassName: local-path + volumeMode: Filesystem diff --git a/apps/pocket-id/service.yaml b/apps/pocket-id/service.yaml new file mode 100644 index 0000000..c676844 --- /dev/null +++ b/apps/pocket-id/service.yaml @@ -0,0 +1,14 @@ +apiVersion: v1 +kind: Service +metadata: + name: pocket-id + namespace: pocket-id +spec: + type: ClusterIP + ports: + - name: http + port: 1411 + protocol: TCP + targetPort: 1411 + selector: + app: pocket-id