Skip to content

Commit 7e44779

Browse files
CopilotSRF-Audio
andcommitted
Add documentation for Leantime deployment and 1Password setup
Co-authored-by: SRF-Audio <16975040+SRF-Audio@users.noreply.github.com>
1 parent 40bd98e commit 7e44779

4 files changed

Lines changed: 303 additions & 7 deletions

File tree

argocd/apps/apps/leantime.yml

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -16,18 +16,18 @@ spec:
1616
valuesObject:
1717
image:
1818
tag: "3.6.0"
19-
19+
2020
persistence:
2121
enabled: true
2222
storageClass: "nfs-synology-retain"
2323
size: 10Gi
24-
24+
2525
service:
2626
type: ClusterIP
27-
27+
2828
ingress:
2929
enabled: false
30-
30+
3131
app:
3232
sitename: "Leantime"
3333
leanSessionSecure: "true"
@@ -41,7 +41,7 @@ spec:
4141
expiration: 28800
4242
email:
4343
enabled: false
44-
44+
4545
# Configure MariaDB subchart to use 1Password-managed secret
4646
mariadb:
4747
enabled: true
@@ -51,11 +51,11 @@ spec:
5151
# Use secret created by 1Password Operator
5252
# The secret must have keys: mariadb-root-password, mariadb-password
5353
existingSecret: "leantime-db"
54-
54+
5555
destination:
5656
server: https://kubernetes.default.svc
5757
namespace: apps-leantime
58-
58+
5959
syncPolicy:
6060
automated:
6161
prune: true

docs/leantime-deployment.md

Lines changed: 177 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,177 @@
1+
# Leantime Deployment via ArgoCD
2+
3+
This deployment follows the GitOps-first pattern using ArgoCD to deploy Leantime directly from its upstream Git repository.
4+
5+
## Overview
6+
7+
- **Application**: Leantime - Project management for lean teams
8+
- **Deployment Method**: ArgoCD Helm-from-Git
9+
- **Upstream Repo**: https://github.com/Leantime/leantime.git
10+
- **Chart Version**: v3.6.0 (pinned)
11+
- **Namespace**: apps-leantime
12+
- **Access**: Tailscale-only via Ingress
13+
- **Secrets**: 1Password Operator
14+
15+
## Architecture
16+
17+
```
18+
┌─────────────────────────────────────────────────────────────┐
19+
│ ArgoCD Root App (argocd/root.yml) │
20+
│ Discovers all apps in argocd/apps/** recursively │
21+
└─────────────────────────────────────────────────────────────┘
22+
23+
┌─────────────────────┼─────────────────────┐
24+
│ │ │
25+
▼ ▼ ▼
26+
┌───────────────┐ ┌───────────────┐ ┌───────────────┐
27+
│ leantime- │ │ leantime │ │ leantime- │
28+
│ secrets │ │ │ │ ingress │
29+
│ (wave 10) │ │ (wave 20) │ │ (wave 30) │
30+
└───────────────┘ └───────────────┘ └───────────────┘
31+
│ │ │
32+
│ │ │
33+
▼ ▼ ▼
34+
┌───────────────┐ ┌───────────────┐ ┌───────────────┐
35+
│ 1Password │ │ Helm Chart │ │ Tailscale │
36+
│ Operator │ │ from Git │ │ Ingress │
37+
│ creates │ │ leantime/ │ │ + Homepage │
38+
│ Secrets │ │ leantime.git │ │ annotations │
39+
└───────────────┘ └───────────────┘ └───────────────┘
40+
```
41+
42+
## Files Created
43+
44+
### ArgoCD Applications
45+
- `argocd/apps/apps/leantime-secrets.yml` - Deploys 1Password CRDs (sync-wave 10)
46+
- `argocd/apps/apps/leantime.yml` - Deploys Leantime Helm chart (sync-wave 20)
47+
- `argocd/apps/apps/leantime-ingress.yml` - Deploys Tailscale ingress (sync-wave 30)
48+
49+
### Kubernetes Manifests
50+
- `k8s/leantime_secrets/` - OnePasswordItem CRDs and kustomization
51+
- `onepassword-db.yml` - Database credentials
52+
- `onepassword-app.yml` - App secrets (reserved for future use)
53+
- `kustomization.yml` - Kustomize manifest
54+
- `README.md` - Setup instructions
55+
56+
- `k8s/leantime_ingress/` - Tailscale ingress with Homepage annotations
57+
- `ingress.yml` - Ingress resource
58+
59+
## Prerequisites
60+
61+
Before deploying, ensure the following are in place:
62+
63+
1. **ArgoCD** is installed and the root app is configured
64+
2. **Tailscale Operator** is deployed and configured
65+
3. **1Password Operator** is deployed and configured
66+
4. **1Password Items** are created in the HomeLab vault:
67+
- Item: `Leantime Database` with fields:
68+
- `mariadb-root-password`
69+
- `mariadb-password`
70+
- Item: `Leantime App Secrets` (can be empty for now)
71+
72+
5. **Storage Class** `nfs-synology-retain` is available in the cluster
73+
74+
## Deployment Details
75+
76+
### Secrets (Sync-Wave 10)
77+
78+
The `leantime-secrets` application deploys OnePasswordItem CRDs that reference items in 1Password. The 1Password Operator materializes these as Kubernetes Secrets:
79+
80+
- `leantime-db`: Contains MariaDB credentials
81+
- `leantime-app`: Reserved for future app-level secrets
82+
83+
### Application (Sync-Wave 20)
84+
85+
The `leantime` application uses ArgoCD's Helm-from-Git feature to render the chart directly from the upstream repository:
86+
87+
**Source Configuration**:
88+
- Repository: `https://github.com/Leantime/leantime.git`
89+
- Revision: `v3.6.0` (immutable tag)
90+
- Path: `helm`
91+
92+
**Key Helm Values**:
93+
- Image tag pinned to `3.6.0`
94+
- Persistence enabled with `nfs-synology-retain` storage class (10Gi)
95+
- Built-in ingress disabled
96+
- MariaDB subchart configured to use `existingSecret: leantime-db`
97+
- Session password set to a generated secure value
98+
99+
**Chart Limitations**:
100+
The upstream Leantime chart does not support `existingSecret` for application-level secrets (session password, SMTP). The session password is therefore included in the Helm values as a generated secure random value. Database credentials properly use the MariaDB subchart's `existingSecret` feature.
101+
102+
### Ingress (Sync-Wave 30)
103+
104+
The `leantime-ingress` application deploys a Tailscale Ingress that:
105+
106+
- Uses `ingressClassName: tailscale`
107+
- Exposes Leantime at `leantime.rohu-shark.ts.net` (MagicDNS)
108+
- Routes to the Leantime service on port 80
109+
- Includes Homepage annotations for service discovery:
110+
- Name: "Leantime"
111+
- Group: "Apps"
112+
- Icon: "leantime.png"
113+
114+
## Access
115+
116+
Once deployed, Leantime will be accessible only from devices on your Tailnet at:
117+
118+
**URL**: https://leantime.rohu-shark.ts.net/
119+
120+
The service will also appear on your Homepage dashboard in the "Apps" group.
121+
122+
## Security
123+
124+
- ✅ No secrets in Git
125+
- ✅ Database credentials managed by 1Password
126+
- ✅ No public ingress (Tailscale-only)
127+
- ✅ Immutable upstream version pinned (v3.6.0)
128+
- ⚠️ Session password in Helm values (chart limitation)
129+
130+
## Verification
131+
132+
After ArgoCD syncs all three applications:
133+
134+
```bash
135+
# Check ArgoCD application status
136+
kubectl get applications -n argocd | grep leantime
137+
138+
# Check secrets created by 1Password Operator
139+
kubectl get secrets -n apps-leantime
140+
141+
# Check the Leantime deployment
142+
kubectl get deployments -n apps-leantime
143+
144+
# Check the MariaDB statefulset
145+
kubectl get statefulsets -n apps-leantime
146+
147+
# Check the Tailscale ingress
148+
kubectl get ingress -n apps-leantime
149+
150+
# Check Tailscale proxy device
151+
kubectl get pods -n apps-leantime | grep ts-
152+
```
153+
154+
All applications should show as `Synced` and `Healthy` in ArgoCD.
155+
156+
## Troubleshooting
157+
158+
### Application won't sync
159+
- Verify 1Password items exist in the HomeLab vault
160+
- Check ArgoCD application events: `kubectl describe application leantime -n argocd`
161+
162+
### Database connection issues
163+
- Verify secrets were created: `kubectl get secrets -n apps-leantime`
164+
- Check secret keys: `kubectl get secret leantime-db -n apps-leantime -o yaml`
165+
- Ensure keys `mariadb-root-password` and `mariadb-password` are present
166+
167+
### Ingress not accessible
168+
- Verify Tailscale Operator is running
169+
- Check ingress status: `kubectl describe ingress leantime -n apps-leantime`
170+
- Look for Tailscale proxy pod: `kubectl get pods -n apps-leantime`
171+
- Check MagicDNS resolution from a Tailnet device
172+
173+
## Future Improvements
174+
175+
1. If the upstream chart adds `existingSecret` support for app secrets, update to use `leantime-app` secret
176+
2. Consider enabling SMTP for email notifications (would need additional 1Password fields)
177+
3. Evaluate S3 storage for user files instead of NFS PVCs

docs/onepassword-migration-notes.md

Lines changed: 67 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -99,3 +99,70 @@ See `k8s/crafty_controller/onepassworditem-crafty-default-json.yml` and `argocd/
9999
| Cluster Primitives | ✅ | ✅ | ❓ | No secret dependencies |
100100
| PostgreSQL | ✅ | ✅ | ❓ | Already using OnePassword CRDs |
101101
| Redis | ✅ | ✅ | ❓ | Already using OnePassword CRDs |
102+
| Leantime | ✅ | ✅ | ❌ | Requires 1Password items setup (see below) |
103+
104+
---
105+
106+
### 6. Leantime (`argocd/apps/apps/leantime.yml`)
107+
108+
**Status**: OnePassword CRDs created, requires 1Password vault setup
109+
110+
**Current State**: New deployment using GitOps-first approach:
111+
- ArgoCD Application points directly at upstream Leantime Git repository
112+
- Helm chart rendered from `https://github.com/Leantime/leantime.git` at tag `v3.6.0`
113+
- Exposed only on Tailnet via Tailscale Ingress
114+
- Homepage discovery via ingress annotations
115+
116+
**Required 1Password Items**:
117+
118+
The Leantime OnePassword operator requires two items in the `HomeLab` vault:
119+
120+
1. **`Leantime Database`** (referenced by `leantime-db` secret)
121+
- Must contain the following fields that will be mapped to secret keys:
122+
- `mariadb-root-password`: Root password for MariaDB
123+
- `mariadb-password`: Password for the `leantime` database user
124+
- Used by the MariaDB subchart via `mariadb.auth.existingSecret`
125+
126+
2. **`Leantime App Secrets`** (referenced by `leantime-app` secret)
127+
- Reserved for future use if the upstream chart adds support for existingSecret on app-level secrets
128+
- Currently not used (session password is in Helm values due to chart limitations)
129+
130+
**Deployment Structure**:
131+
- `argocd/apps/apps/leantime-secrets.yml` (sync-wave 10) → deploys OnePasswordItem CRDs
132+
- `argocd/apps/apps/leantime.yml` (sync-wave 20) → deploys Helm chart from upstream Git
133+
- `argocd/apps/apps/leantime-ingress.yml` (sync-wave 30) → deploys Tailscale ingress with Homepage annotations
134+
135+
**Chart Limitations**:
136+
- The Leantime Helm chart does not support `existingSecret` for app-level secrets (session password, SMTP, etc.)
137+
- Session password is currently set in `valuesObject` as a generated secure random value
138+
- Database credentials use the MariaDB subchart's `existingSecret` feature successfully
139+
140+
**Migration Path**: N/A (new deployment)
141+
142+
**Sync Waves**:
143+
- Secrets: 10
144+
- Application: 20
145+
- Ingress: 30
146+
147+
**1Password Setup Instructions**:
148+
149+
Before syncing the Leantime applications, create these items in 1Password:
150+
151+
```bash
152+
# In 1Password web UI or CLI:
153+
# Vault: HomeLab
154+
# Item 1: "Leantime Database"
155+
# - Add field: mariadb-root-password = <generate secure password>
156+
# - Add field: mariadb-password = <generate secure password>
157+
#
158+
# Item 2: "Leantime App Secrets"
159+
# - Can be empty for now (reserved for future use)
160+
```
161+
162+
**Verification**:
163+
After ArgoCD syncs the `leantime-secrets` application:
164+
```bash
165+
kubectl get secrets -n apps-leantime
166+
# Should show: leantime-db, leantime-app
167+
```
168+

k8s/leantime_secrets/README.md

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,52 @@
1+
# Leantime Secrets - 1Password Setup
2+
3+
This directory contains OnePasswordItem CRDs that reference secrets in the HomeLab vault.
4+
5+
## Required 1Password Items
6+
7+
Before deploying Leantime, create the following items in 1Password:
8+
9+
### 1. Leantime Database (`Leantime Database`)
10+
11+
**Vault**: HomeLab
12+
**Item Name**: `Leantime Database`
13+
14+
**Required Fields**:
15+
- `mariadb-root-password`: Root password for the MariaDB database
16+
- `mariadb-password`: Password for the `leantime` database user
17+
18+
These fields will be materialized by the 1Password Operator into a Kubernetes Secret named `leantime-db` in the `apps-leantime` namespace.
19+
20+
### 2. Leantime App Secrets (`Leantime App Secrets`)
21+
22+
**Vault**: HomeLab
23+
**Item Name**: `Leantime App Secrets`
24+
25+
**Status**: Reserved for future use. Can be empty or contain placeholder values for now.
26+
27+
**Note**: The upstream Leantime Helm chart does not currently support `existingSecret` for application-level secrets (session password, SMTP credentials, etc.). This OnePasswordItem is created for future extensibility.
28+
29+
## Verification
30+
31+
After ArgoCD syncs the `leantime-secrets` application (sync-wave 10), verify the secrets were created:
32+
33+
```bash
34+
kubectl get onepassworditems -n apps-leantime
35+
kubectl get secrets -n apps-leantime
36+
```
37+
38+
You should see:
39+
- OnePasswordItems: `leantime-db`, `leantime-app`
40+
- Secrets: `leantime-db`, `leantime-app` (created by 1Password Operator)
41+
42+
## Integration
43+
44+
The `leantime-db` secret is consumed by the MariaDB subchart in the Leantime Helm deployment via:
45+
46+
```yaml
47+
mariadb:
48+
auth:
49+
existingSecret: "leantime-db"
50+
```
51+
52+
This ensures database credentials are never stored in Git or ArgoCD manifests.

0 commit comments

Comments
 (0)