diff --git a/helm/garage-ui/README.md b/helm/garage-ui/README.md index 80632c9..6a14b63 100644 --- a/helm/garage-ui/README.md +++ b/helm/garage-ui/README.md @@ -1,182 +1,225 @@ # Garage UI Helm Chart -A Helm chart for deploying Garage UI, a web interface for [Garage](https://garagehq.deuxfleurs.fr/) S3 object storage. +A Helm chart for deploying [Garage UI](https://github.com/Noooste/garage-ui), a modern web interface for managing [Garage](https://garagehq.deuxfleurs.fr/) distributed object storage systems. -## Introduction +[![Version](https://img.shields.io/badge/version-0.1.1-blue.svg)](Chart.yaml) +[![App Version](https://img.shields.io/badge/app%20version-v0.0.6-green.svg)](Chart.yaml) -This chart bootstraps a Garage UI deployment on a Kubernetes cluster using the Helm package manager. Garage UI provides a user-friendly web interface for managing your Garage S3 storage, including buckets, objects, users, and cluster monitoring. +## Table of Contents + +- [Overview](#overview) +- [Prerequisites](#prerequisites) +- [Quick Start](#quick-start) +- [Installation](#installation) +- [Configuration](#configuration) +- [Examples](#examples) +- [Upgrading](#upgrading) +- [Accessing the Application](#accessing-the-application) +- [Monitoring](#monitoring) +- [Troubleshooting](#troubleshooting) +- [Uninstalling](#uninstalling) + +## Overview + +Garage UI provides an intuitive web interface for managing your Garage S3 storage cluster, featuring: + +- **Bucket Management** - Create, delete, and configure S3 buckets +- **Object Operations** - Upload, download, and delete objects through the UI +- **User Access Control** - Manage users, access keys, and permissions +- **Cluster Monitoring** - View cluster health, status, and statistics +- **Authentication** - Support for no auth, basic auth, and OIDC/SSO ## Prerequisites -- Kubernetes 1.19+ -- Helm 3.0+ -- A running Garage S3 instance with Admin API access +Before installing this chart, ensure you have: -## Installing the Chart +- **Kubernetes** `1.19+` or later +- **Helm** `3.0+` or later +- **Garage S3** instance running and accessible +- **Garage Admin Token** - Required for administrative operations -To install the chart with the release name `my-garage-ui`: +### Required Information -```bash -helm install my-garage-ui ./helm/garage-ui -``` +You will need the following information from your Garage installation: -The command deploys Garage UI on the Kubernetes cluster with default configuration. The [Parameters](#parameters) section lists the parameters that can be configured during installation. +1. **Garage S3 Endpoint** - The Garage S3 API endpoint (default port: `3900`) +2. **Garage Admin Endpoint** - The Garage Admin API endpoint (default port: `3903`) +3. **Admin Token** - Bearer token for authenticating with the Admin API -## Uninstalling the Chart +To find your admin token, check your Garage server's configuration file. -To uninstall/delete the `my-garage-ui` deployment: +## Quick Start -```bash -helm uninstall my-garage-ui -``` +The fastest way to get started with Garage UI: -The command removes all the Kubernetes components associated with the chart and deletes the release. +### Step 1: Create a values file -## Parameters - -### Common Parameters - -| Parameter | Description | Default | -|-----------|-------------|---------| -| `replicaCount` | Number of Garage UI replicas | `1` | -| `image.repository` | Garage UI image repository | `noooste/garage-ui` | -| `image.tag` | Garage UI image tag (overrides Chart appVersion) | `""` | -| `image.pullPolicy` | Image pull policy | `IfNotPresent` | -| `imagePullSecrets` | Image pull secrets | `[]` | -| `nameOverride` | Override chart name | `""` | -| `fullnameOverride` | Override full resource names | `""` | - -### Service Parameters - -| Parameter | Description | Default | -|-----------|-------------|---------| -| `service.type` | Kubernetes service type | `ClusterIP` | -| `service.port` | Service port | `80` | - -### Configuration Parameters - -| Parameter | Description | Default | -|-----------|-------------|---------| -| `config` | Complete config.yaml content as multiline string | See `values.yaml` | - -**Important:** The `config` parameter contains the entire application configuration including Garage endpoints, authentication settings, CORS, and logging. You must customize this section with your Garage S3 endpoints and admin token. - -### Ingress Parameters - -| Parameter | Description | Default | -|-----------|-------------|---------| -| `ingress.enabled` | Enable ingress controller resource | `false` | -| `ingress.className` | Ingress class name | `nginx` | -| `ingress.annotations` | Ingress annotations | `{}` | -| `ingress.hosts` | Ingress hosts configuration | See `values.yaml` | -| `ingress.tls` | Ingress TLS configuration | `[]` | - -### Monitoring Parameters - -| Parameter | Description | Default | -|-----------|-------------|---------| -| `serviceMonitor.enabled` | Create ServiceMonitor resource (requires Prometheus Operator) | `false` | -| `serviceMonitor.interval` | Scrape interval | `30s` | -| `serviceMonitor.path` | Metrics endpoint path | `/api/v1/monitoring/metrics` | -| `serviceMonitor.labels` | Additional labels for ServiceMonitor | `{}` | - -### Network Policy Parameters - -| Parameter | Description | Default | -|-----------|-------------|---------| -| `networkPolicy.enabled` | Enable NetworkPolicy | `false` | -| `networkPolicy.policyTypes` | Policy types | `["Ingress", "Egress"]` | - -### Resource Management Parameters - -| Parameter | Description | Default | -|-----------|-------------|---------| -| `resources.limits.cpu` | CPU limit | `500m` | -| `resources.limits.memory` | Memory limit | `512Mi` | -| `resources.requests.cpu` | CPU request | `100m` | -| `resources.requests.memory` | Memory request | `128Mi` | - -### Health Check Parameters - -| Parameter | Description | Default | -|-----------|-------------|---------| -| `livenessProbe.enabled` | Enable liveness probe | `true` | -| `readinessProbe.enabled` | Enable readiness probe | `true` | - -### Other Parameters - -| Parameter | Description | Default | -|-----------|-------------|---------| -| `podAnnotations` | Pod annotations | `{}` | -| `podSecurityContext` | Pod security context | See `values.yaml` | -| `securityContext` | Container security context | See `values.yaml` | -| `nodeSelector` | Node labels for pod assignment | `{}` | -| `tolerations` | Tolerations for pod assignment | `[]` | -| `affinity` | Affinity for pod assignment | `{}` | - -## Configuration Examples - -### Example 1: Basic Installation with Custom Garage Endpoints - -Create a file named `custom-values.yaml`: +Create a file named `my-values.yaml` with your Garage configuration: ```yaml -config: | - server: - host: "0.0.0.0" - port: 8080 - environment: "production" - +config: garage: - endpoint: "http://garage-s3.garage.svc.cluster.local:3900" - region: "us-east-1" - admin_endpoint: "http://garage-admin.garage.svc.cluster.local:3903" - admin_token: "YOUR_ADMIN_TOKEN_HERE" + endpoint: "http://garage:3900" # Your Garage S3 endpoint + admin_endpoint: "http://garage:3903" # Your Garage Admin endpoint + admin_token: "YOUR_ADMIN_TOKEN_HERE" # Your admin token + region: "garage" # S3 region (can be any value) +``` +### Step 2: Install the chart + +```bash +helm install garage-ui ./helm/garage-ui -f my-values.yaml +``` + +### Step 3: Access the UI + +```bash +# Forward port to access locally +kubectl port-forward svc/garage-ui 8080:80 + +# Open in your browser +open http://localhost:8080 +``` + +That's it! You should now have Garage UI running and accessible. + +## Installation + +### Installing from local chart + +If you've cloned the repository: + +```bash +helm install garage-ui ./helm/garage-ui -f my-values.yaml +``` + +### Installing with inline values + +You can also set values directly on the command line: + +```bash +helm install garage-ui ./helm/garage-ui \ + --set config.garage.endpoint=http://garage:3900 \ + --set config.garage.admin_endpoint=http://garage:3903 \ + --set config.garage.admin_token=your-token-here +``` + +### Verify installation + +Check that the pod is running: + +```bash +kubectl get pods -l app.kubernetes.io/name=garage-ui +``` + +View the logs: + +```bash +kubectl logs -l app.kubernetes.io/name=garage-ui +``` + +## Configuration + +### Configuration Structure + +The chart uses a structured `config` section that maps directly to the application's configuration file. You can override any value using Helm's standard methods. + +### Minimal Configuration + +The absolute minimum configuration requires only the Garage endpoints and admin token: + +```yaml +config: + garage: + endpoint: "http://garage:3900" + admin_endpoint: "http://garage:3903" + admin_token: "your-admin-token" +``` + +### Common Configuration Options + +#### Server Settings + +```yaml +config: + server: + port: 8080 # Application port + environment: production # Environment (production/development/staging) +``` + +#### Authentication Modes + +**No Authentication** (default, suitable for private networks): +```yaml +config: auth: mode: "none" +``` +**Basic Authentication**: +```yaml +config: + auth: + mode: "basic" + basic: + username: "admin" + password: "your-secure-password" +``` + +**OIDC/SSO** (recommended for production): +```yaml +config: + auth: + mode: "oidc" + oidc: + enabled: true + provider_name: "Keycloak" + client_id: "garage-ui" + client_secret: "your-oidc-secret" + issuer_url: "https://auth.example.com/realms/master" + # ... additional OIDC settings +``` + +#### CORS Configuration + +```yaml +config: cors: enabled: true allowed_origins: - - "*" - - logging: - level: "info" - format: "json" + - "https://garage-ui.example.com" # Recommended: specific origins + # - "*" # Or: allow all origins (less secure) ``` -Install the chart: - -```bash -helm install my-garage-ui ./helm/garage-ui -f custom-values.yaml -``` - -### Example 2: With Ingress and TLS +#### Logging ```yaml -config: | - server: - host: "0.0.0.0" - port: 8080 - environment: "production" - - garage: - endpoint: "http://garage:3900" - region: "garage" - admin_endpoint: "http://garage:3903" - admin_token: "YOUR_ADMIN_TOKEN" - - auth: - mode: "none" - - cors: - enabled: true - +config: logging: - level: "info" - format: "json" + level: info # debug, info, warn, error + format: json # json (recommended for production), text +``` +### Kubernetes Resource Configuration + +#### Ingress + +Enable external access with Ingress: + +```yaml +ingress: + enabled: true + className: nginx + hosts: + - host: garage-ui.example.com + paths: + - path: / + pathType: Prefix +``` + +With TLS: + +```yaml ingress: enabled: true className: nginx @@ -193,49 +236,140 @@ ingress: - garage-ui.example.com ``` +#### Resource Limits + +```yaml +resources: + limits: + cpu: 500m + memory: 512Mi + requests: + cpu: 100m + memory: 128Mi +``` + +#### Replicas and High Availability + +```yaml +replicaCount: 3 + +affinity: + podAntiAffinity: + preferredDuringSchedulingIgnoredDuringExecution: + - weight: 100 + podAffinityTerm: + labelSelector: + matchExpressions: + - key: app.kubernetes.io/name + operator: In + values: + - garage-ui + topologyKey: kubernetes.io/hostname +``` + +### Complete Parameters Reference + +For a complete list of all available parameters, see the [values.yaml](values.yaml) file which includes detailed comments for every configuration option. + +## Examples + +### Example 1: Basic Installation (In-Cluster Garage) + +For Garage running in the same Kubernetes cluster: + +```yaml +# values-basic.yaml +config: + garage: + endpoint: "http://garage.garage-system.svc.cluster.local:3900" + admin_endpoint: "http://garage.garage-system.svc.cluster.local:3903" + admin_token: "GgJLd9J...your-token-here" + region: "garage" +``` + +Install: +```bash +helm install garage-ui ./helm/garage-ui -f values-basic.yaml +``` + +### Example 2: External Access with Ingress + +```yaml +# values-ingress.yaml +config: + garage: + endpoint: "http://garage:3900" + admin_endpoint: "http://garage:3903" + admin_token: "your-admin-token" + +ingress: + enabled: true + className: nginx + annotations: + cert-manager.io/cluster-issuer: letsencrypt-prod + nginx.ingress.kubernetes.io/force-ssl-redirect: "true" + hosts: + - host: garage-ui.example.com + paths: + - path: / + pathType: Prefix + tls: + - secretName: garage-ui-tls + hosts: + - garage-ui.example.com +``` + +Install: +```bash +helm install garage-ui ./helm/garage-ui -f values-ingress.yaml +``` + ### Example 3: With Basic Authentication ```yaml -config: | - server: - host: "0.0.0.0" - port: 8080 - environment: "production" - +# values-basic-auth.yaml +config: garage: endpoint: "http://garage:3900" - region: "garage" admin_endpoint: "http://garage:3903" - admin_token: "YOUR_ADMIN_TOKEN" + admin_token: "your-admin-token" auth: mode: "basic" basic: username: "admin" - password: "your-secure-password" + password: "super-secret-password-change-me" - cors: - enabled: true - - logging: - level: "info" - format: "json" +ingress: + enabled: true + className: nginx + hosts: + - host: garage.local + paths: + - path: / + pathType: Prefix ``` -### Example 4: With OIDC Authentication (Keycloak) +Install: +```bash +helm install garage-ui ./helm/garage-ui -f values-basic-auth.yaml +``` + +### Example 4: Production Setup with OIDC (Keycloak) ```yaml -config: | +# values-production.yaml +replicaCount: 3 + +config: server: - host: "0.0.0.0" - port: 8080 - environment: "production" + environment: production garage: - endpoint: "http://garage:3900" - region: "garage" - admin_endpoint: "http://garage:3903" - admin_token: "YOUR_ADMIN_TOKEN" + endpoint: "https://s3.garage.example.com" + admin_endpoint: "https://admin.garage.example.com" + admin_token: "your-admin-token" + region: "us-east-1" auth: mode: "oidc" @@ -243,49 +377,81 @@ config: | enabled: true provider_name: "Keycloak" client_id: "garage-ui" - client_secret: "YOUR_OIDC_CLIENT_SECRET" + client_secret: "your-oidc-client-secret" scopes: - openid - email - profile - issuer_url: "https://keycloak.example.com/realms/master" - auth_url: "https://keycloak.example.com/realms/master/protocol/openid-connect/auth" - token_url: "https://keycloak.example.com/realms/master/protocol/openid-connect/token" - userinfo_url: "https://keycloak.example.com/realms/master/protocol/openid-connect/userinfo" + issuer_url: "https://auth.example.com/realms/production" + auth_url: "https://auth.example.com/realms/production/protocol/openid-connect/auth" + token_url: "https://auth.example.com/realms/production/protocol/openid-connect/token" + userinfo_url: "https://auth.example.com/realms/production/protocol/openid-connect/userinfo" cookie_secure: true + cookie_http_only: true + cookie_same_site: "lax" cors: enabled: true + allowed_origins: + - "https://garage-ui.example.com" logging: - level: "info" - format: "json" + level: info + format: json + +ingress: + enabled: true + className: nginx + annotations: + cert-manager.io/cluster-issuer: letsencrypt-prod + nginx.ingress.kubernetes.io/force-ssl-redirect: "true" + nginx.ingress.kubernetes.io/proxy-body-size: "100m" + hosts: + - host: garage-ui.example.com + paths: + - path: / + pathType: Prefix + tls: + - secretName: garage-ui-tls + hosts: + - garage-ui.example.com + +resources: + limits: + cpu: 1000m + memory: 1Gi + requests: + cpu: 200m + memory: 256Mi + +affinity: + podAntiAffinity: + preferredDuringSchedulingIgnoredDuringExecution: + - weight: 100 + podAffinityTerm: + labelSelector: + matchExpressions: + - key: app.kubernetes.io/name + operator: In + values: + - garage-ui + topologyKey: kubernetes.io/hostname +``` + +Install: +```bash +helm install garage-ui ./helm/garage-ui -f values-production.yaml ``` ### Example 5: With Prometheus Monitoring ```yaml -config: | - server: - host: "0.0.0.0" - port: 8080 - environment: "production" - +# values-monitoring.yaml +config: garage: endpoint: "http://garage:3900" - region: "garage" admin_endpoint: "http://garage:3903" - admin_token: "YOUR_ADMIN_TOKEN" - - auth: - mode: "none" - - cors: - enabled: true - - logging: - level: "info" - format: "json" + admin_token: "your-admin-token" serviceMonitor: enabled: true @@ -294,103 +460,399 @@ serviceMonitor: prometheus: kube-prometheus ``` -## Accessing the Application - -### Via Port Forward (Development) - +Install: ```bash -kubectl port-forward svc/my-garage-ui 8080:80 +helm install garage-ui ./helm/garage-ui -f values-monitoring.yaml ``` -Then visit http://localhost:8080 in your browser. +### Example 6: Using Kubernetes Secrets for Admin Token (Recommended) -### Via Ingress (Production) +For improved security, store the admin token in a Kubernetes secret instead of in values files: -If you've enabled Ingress, access the application at the configured hostname (e.g., https://garage-ui.example.com). +**Option A: Use an existing secret** + +First, create a Kubernetes secret: +```bash +kubectl create secret generic garage-admin-token \ + --from-literal=admin-token='your-admin-token-here' +``` + +Then configure the chart to use it: +```yaml +# values-with-secret.yaml +config: + garage: + endpoint: "http://garage:3900" + admin_endpoint: "http://garage:3903" + # Leave admin_token empty when using existingSecret + admin_token: "" + + # Reference the existing secret + existingSecret: + name: "garage-admin-token" + key: "admin-token" +``` + +Install: +```bash +helm install garage-ui ./helm/garage-ui -f values-with-secret.yaml +``` + +**Option B: Let the chart create the secret** + +If you provide `admin_token` in values but don't configure `existingSecret`, the chart will automatically create a secret for you: + +```yaml +# values-auto-secret.yaml +config: + garage: + endpoint: "http://garage:3900" + admin_endpoint: "http://garage:3903" + # Chart will create a secret with this value + admin_token: "your-admin-token" +``` + +This approach keeps the token out of the ConfigMap while still allowing you to manage it through Helm values. ## Upgrading -To upgrade the `my-garage-ui` deployment: +### Upgrade to a new version ```bash -helm upgrade my-garage-ui ./helm/garage-ui -f custom-values.yaml +helm upgrade garage-ui ./helm/garage-ui -f my-values.yaml ``` -## Configuration Details +### Upgrade with new values -### Garage Endpoints +```bash +helm upgrade garage-ui ./helm/garage-ui \ + --set config.logging.level=debug \ + --reuse-values +``` -The application requires two Garage endpoints: +### Check upgrade history -- **S3 API Endpoint** (`garage.endpoint`): The Garage S3 API endpoint (default port 3900) -- **Admin API Endpoint** (`garage.admin_endpoint`): The Garage Admin API endpoint (default port 3903) -- **Admin Token** (`garage.admin_token`): Bearer token for Admin API authentication (required) +```bash +helm history garage-ui +``` -### Authentication Modes +### Rollback to previous version -The application supports three authentication modes: +```bash +helm rollback garage-ui +``` -1. **None** (`auth.mode: "none"`): No authentication required -2. **Basic** (`auth.mode: "basic"`): HTTP Basic authentication with username/password -3. **OIDC** (`auth.mode: "oidc"`): OpenID Connect for enterprise SSO +## Accessing the Application + +### Method 1: Port Forward (Development) + +Quick access for testing: + +```bash +kubectl port-forward svc/garage-ui 8080:80 +``` + +Then open: http://localhost:8080 + +### Method 2: Ingress (Production) + +If you've enabled Ingress with a domain: + +```bash +# Access via your configured domain +open https://garage-ui.example.com +``` + +### Method 3: NodePort (Alternative) + +Change service type to NodePort: + +```yaml +service: + type: NodePort + port: 80 +``` + +Find the assigned port: + +```bash +kubectl get svc garage-ui +``` + +### Method 4: LoadBalancer (Cloud Environments) + +For cloud providers with LoadBalancer support: + +```yaml +service: + type: LoadBalancer + port: 80 +``` + +Get the external IP: + +```bash +kubectl get svc garage-ui +``` + +## Monitoring + +### Prometheus ServiceMonitor + +Enable Prometheus metrics scraping (requires Prometheus Operator): + +```yaml +serviceMonitor: + enabled: true + interval: 30s + path: /api/v1/monitoring/metrics + labels: + prometheus: kube-prometheus +``` + +### Metrics Endpoint + +The application exposes metrics at: +- Path: `/api/v1/monitoring/metrics` +- Format: Prometheus format (proxies Garage Admin API metrics) ### Health Checks -The application exposes a health check endpoint at `/health` which is used for: -- Kubernetes liveness probes -- Kubernetes readiness probes -- Manual health verification +Health endpoint available at: +- Path: `/health` +- Response: `{"status": "ok", "version": "0.1.0"}` -### Metrics - -When ServiceMonitor is enabled, Prometheus will scrape metrics from `/api/v1/monitoring/metrics`. This endpoint proxies metrics from the Garage Admin API. +Used by Kubernetes liveness and readiness probes. ## Troubleshooting -### Pods not starting +### Pods Not Starting + +Check pod status and logs: -Check if the config is valid: ```bash +kubectl get pods -l app.kubernetes.io/name=garage-ui +kubectl describe pod -l app.kubernetes.io/name=garage-ui kubectl logs -l app.kubernetes.io/name=garage-ui ``` Common issues: -- Missing or invalid `garage.admin_token` -- Unreachable Garage endpoints -- Invalid OIDC configuration when using `auth.mode: "oidc"` +- **Missing admin token**: Ensure `config.garage.admin_token` is set or `config.garage.existingSecret.name` points to a valid secret +- **Secret not found**: If using `existingSecret`, verify the secret exists: `kubectl get secret ` +- **Unreachable Garage**: Verify endpoints are accessible from within the cluster +- **Invalid OIDC config**: Check all OIDC URLs and credentials when using `auth.mode: oidc` -### Can't access the UI +### Cannot Access the UI + +For Ingress issues: -If using Ingress: ```bash kubectl get ingress -kubectl describe ingress +kubectl describe ingress garage-ui ``` -If using port-forward: -```bash -kubectl get pods -kubectl port-forward 8080:8080 -``` - -### Configuration not updating - -The deployment includes a checksum annotation for the ConfigMap. Changes to the config will automatically trigger a pod restart. If not: +Check Ingress controller logs: ```bash -kubectl rollout restart deployment/my-garage-ui +kubectl logs -n ingress-nginx -l app.kubernetes.io/name=ingress-nginx ``` -## License +Common issues: +- **DNS not configured**: Ensure your domain points to the Ingress controller +- **Certificate issues**: Check cert-manager logs if using automatic TLS +- **Ingress class mismatch**: Verify `ingress.className` matches your controller -This Helm chart is open source and available under the same license as Garage UI. +### Configuration Not Updating + +The deployment includes a ConfigMap checksum annotation that automatically triggers pod restarts when configuration changes. If it's not working: + +```bash +kubectl rollout restart deployment/garage-ui +``` + +### Connection to Garage Fails + +Test connectivity from within the pod: + +```bash +kubectl exec -it deployment/garage-ui -- sh + +# Inside the pod: +curl http://garage:3900 +curl http://garage:3903/health +``` + +### Authentication Issues + +**Basic Auth:** +- Verify username/password in `config.auth.basic` +- Check browser developer tools for 401 errors + +**OIDC:** +- Verify all OIDC URLs are accessible +- Check OIDC provider logs +- Ensure redirect URI is registered: `https://your-domain/auth/callback` +- Verify client ID and secret + +### View Application Logs + +```bash +# Follow logs +kubectl logs -f -l app.kubernetes.io/name=garage-ui + +# View recent logs +kubectl logs --tail=100 -l app.kubernetes.io/name=garage-ui + +# Export logs +kubectl logs -l app.kubernetes.io/name=garage-ui > garage-ui.log +``` + +### Debug Mode + +Enable debug logging: + +```yaml +config: + logging: + level: debug +``` + +## Uninstalling + +### Remove the release + +```bash +helm uninstall garage-ui +``` + +This removes all Kubernetes components associated with the chart. + +### Clean up completely + +If you want to remove all associated resources: + +```bash +# Uninstall the release +helm uninstall garage-ui + +# Remove any remaining ConfigMaps +kubectl delete configmap -l app.kubernetes.io/name=garage-ui + +# Remove any remaining Secrets +kubectl delete secret -l app.kubernetes.io/name=garage-ui +``` + +## Advanced Configuration + +### Using Secrets for Sensitive Data + +The chart supports using Kubernetes secrets for sensitive data to avoid storing credentials in values files. + +#### Admin Token from Secret + +The chart has built-in support for storing the admin token in a Kubernetes secret: + +**Method 1: Use an existing secret** (recommended) + +```bash +# Create the secret +kubectl create secret generic garage-admin-token \ + --from-literal=admin-token='your-admin-token-here' +``` + +Configure in values: +```yaml +config: + garage: + existingSecret: + name: "garage-admin-token" + key: "admin-token" +``` + +**Method 2: Let the chart create the secret** + +Simply provide the `admin_token` in values, and the chart will automatically create a secret: + +```yaml +config: + garage: + admin_token: "your-admin-token" +``` + +The chart will: +1. Create a secret named `-admin-token` with the token +2. Remove the token from the ConfigMap +3. Inject it into the pod via environment variable + +This keeps sensitive data out of ConfigMaps while maintaining easy Helm-based management. + +#### OIDC Client Secret + +For OIDC credentials, you can similarly use secrets (requires manual template modification): + +```bash +kubectl create secret generic garage-oidc \ + --from-literal=client-secret='your-oidc-secret' +``` + +### Network Policies + +Enable network policies for enhanced security: + +```yaml +networkPolicy: + enabled: true + policyTypes: + - Ingress + - Egress +``` + +This restricts network traffic to/from the pods. Requires a CNI that supports NetworkPolicy (e.g., Calico, Cilium). + +### Custom Container Images + +Use a custom or private registry: + +```yaml +image: + repository: myregistry.example.com/garage-ui + tag: "v1.0.0" + pullPolicy: Always + +imagePullSecrets: + - name: myregistrykey +``` + +## Version Compatibility + +| Chart Version | App Version | Kubernetes | Garage | +|--------------|-------------|------------|--------| +| 0.1.1 | v0.0.6 | 1.19+ | 0.8+ | + +## Additional Resources + +- **GitHub Repository**: https://github.com/Noooste/garage-ui +- **Garage Documentation**: https://garagehq.deuxfleurs.fr/ +- **Issue Tracker**: https://github.com/Noooste/garage-ui/issues +- **Helm Documentation**: https://helm.sh/docs/ ## Support -For issues and questions: -- GitHub Issues: https://github.com/Noooste/garage-ui/issues -- Garage Documentation: https://garagehq.deuxfleurs.fr/ +For help and support: + +1. **Documentation**: Check this README and the [values.yaml](values.yaml) file +2. **GitHub Issues**: Report bugs or request features at https://github.com/Noooste/garage-ui/issues +3. **Garage Community**: Visit https://garagehq.deuxfleurs.fr/ for Garage-specific questions ## Contributing -Contributions are welcome! Please submit pull requests to the Garage UI repository. +Contributions are welcome! Please: + +1. Fork the repository +2. Create a feature branch +3. Make your changes +4. Submit a pull request + +## License + +This Helm chart is open source and distributed under the same license as Garage UI. diff --git a/helm/garage-ui/templates/configmap.yaml b/helm/garage-ui/templates/configmap.yaml index a6fbc29..cf655c7 100644 --- a/helm/garage-ui/templates/configmap.yaml +++ b/helm/garage-ui/templates/configmap.yaml @@ -6,4 +6,6 @@ metadata: {{- include "garage-ui.labels" . | nindent 4 }} data: config.yaml: | -{{- .Values.config | toYaml | nindent 4 }} +{{- $config := deepCopy .Values.config }} +{{- $_ := unset $config.garage "admin_token" }} +{{- $config | toYaml | nindent 4 }} diff --git a/helm/garage-ui/templates/deployment.yaml b/helm/garage-ui/templates/deployment.yaml index 138406b..c9cafe1 100644 --- a/helm/garage-ui/templates/deployment.yaml +++ b/helm/garage-ui/templates/deployment.yaml @@ -35,6 +35,17 @@ spec: - name: http containerPort: 8080 protocol: TCP + env: + - name: GARAGE_UI_GARAGE_ADMIN_TOKEN + valueFrom: + secretKeyRef: + {{- if .Values.config.garage.existingSecret.name }} + name: {{ .Values.config.garage.existingSecret.name }} + key: {{ .Values.config.garage.existingSecret.key }} + {{- else }} + name: {{ include "garage-ui.fullname" . }}-admin-token + key: admin-token + {{- end }} {{- if .Values.livenessProbe.enabled }} livenessProbe: httpGet: diff --git a/helm/garage-ui/templates/secret.yaml b/helm/garage-ui/templates/secret.yaml new file mode 100644 index 0000000..5dba027 --- /dev/null +++ b/helm/garage-ui/templates/secret.yaml @@ -0,0 +1,11 @@ +{{- if and (not .Values.config.garage.existingSecret.name) .Values.config.garage.admin_token }} +apiVersion: v1 +kind: Secret +metadata: + name: {{ include "garage-ui.fullname" . }}-admin-token + labels: + {{- include "garage-ui.labels" . | nindent 4 }} +type: Opaque +data: + admin-token: {{ .Values.config.garage.admin_token | b64enc | quote }} +{{- end }} diff --git a/helm/garage-ui/values.yaml b/helm/garage-ui/values.yaml index ede94e3..5d8570b 100644 --- a/helm/garage-ui/values.yaml +++ b/helm/garage-ui/values.yaml @@ -87,8 +87,22 @@ config: # REQUIRED: Obtain this from your Garage server configuration # This token grants administrative access - keep it secure! # To generate: See Garage documentation for admin token setup + # NOTE: If existingSecret is configured, this value will be ignored admin_token: "" + # Use an existing Kubernetes secret for the admin token (recommended for production) + # When configured, this takes precedence over the admin_token value above + # The secret should contain a key with the admin token value + existingSecret: + # Name of the existing secret containing the admin token + # Leave empty to use the admin_token value above instead + # Example: "garage-admin-token" + name: "" + + # Key within the secret that contains the admin token value + # Default: "admin-token" + key: "admin-token" + # ======================================== # Authentication Configuration # ========================================