From a66b9cea5fa692245d62bde966c4c9c06b3d3144 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Thomas=20Gra=CC=88fenstein?= Date: Sun, 22 Mar 2026 12:11:11 +0100 Subject: [PATCH] claude init --- CLAUDE.md | 53 +++++++++++++++++++++++++++++++++++++++++++++++++++++ review.md | 14 ++++++++++++++ 2 files changed, 67 insertions(+) create mode 100644 CLAUDE.md create mode 100644 review.md diff --git a/CLAUDE.md b/CLAUDE.md new file mode 100644 index 0000000..4a892f7 --- /dev/null +++ b/CLAUDE.md @@ -0,0 +1,53 @@ +# CLAUDE.md + +This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository. + +## Project Overview + +GitOps-style Docker Compose setup for a self-hosted VPS running Nextcloud, Gitea, and monitoring on domain `t-gstone.de`. Not a code project — it's infrastructure-as-config with shell scripts. + +## Architecture + +Four independent service stacks, each with its own `docker-compose.yml`: + +- **caddy/** — Reverse proxy with auto HTTPS. All services route through the shared `proxy` Docker network. +- **nextcloud/** — Nextcloud 29 + PostgreSQL 16 + Redis 7 + cron container. Has its own `.env` for DB credentials and Nextcloud config. Uses internal `nextcloud-internal` network for DB/Redis isolation. +- **gitea/** — Gitea (rootless, SQLite). Exposes SSH on port 2222. Has its own `.env`. +- **monitoring/** — Grafana Alloy collecting Docker logs (Loki) and node metrics (Prometheus) to Grafana Cloud. Has its own `.env` for cloud credentials. + +Key design patterns: +- All stacks share the external `proxy` Docker network for Caddy routing +- Each service's compose file requires `--env-file .env` (root-level) for `DATA_ROOT` and `DOMAIN` +- Service-specific secrets live in per-service `.env` files (loaded via `env_file:` in compose) +- All persistent data under `${DATA_ROOT}` (default `/opt/docker-data/`) + +## Common Commands + +```bash +# Deploy everything (installs Docker if needed, creates dirs, starts all stacks) +./scripts/deploy.sh + +# Manage individual services +docker compose -f /docker-compose.yml --env-file .env up -d +docker compose -f /docker-compose.yml --env-file .env logs -f +docker compose -f /docker-compose.yml --env-file .env down + +# Reload Caddy after Caddyfile changes +docker exec caddy caddy reload --config /etc/caddy/Caddyfile + +# Backup / Restore +./scripts/backup.sh +./scripts/restore.sh +``` + +## Adding a New Service + +1. Create `myapp/docker-compose.yml` joining the `proxy` external network, with data under `${DATA_ROOT}/myapp/` +2. Add reverse proxy entry in `caddy/Caddyfile` +3. Add data directory creation to `scripts/deploy.sh` +4. Add backup steps to `scripts/backup.sh` if it has persistent data +5. Create DNS A record for the subdomain + +## Environment Files + +Root `.env` provides `DOMAIN` and `DATA_ROOT`. Each service directory has its own `.env` (copied from `.env.example`) for service-specific secrets. The `.env` files are gitignored. diff --git a/review.md b/review.md new file mode 100644 index 0000000..29353f6 --- /dev/null +++ b/review.md @@ -0,0 +1,14 @@ +# Code Review Issues + +| # | Severity | File | Issue | Status | +|----|----------|---------------------------------|------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|--------| +| 1 | Critical | `scripts/deploy.sh` | `SCRIPT_DIR` resolves to `scripts/` but paths assume repo root (e.g. `$SCRIPT_DIR/caddy/docker-compose.yml`). All scripts broken after move to `scripts/`. Fix: use `REPO_ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"` | TODO | +| 2 | Critical | `scripts/backup.sh` | Same broken `SCRIPT_DIR` path issue | TODO | +| 3 | Critical | `scripts/restore.sh` | Same broken `SCRIPT_DIR` path issue | TODO | +| 4 | High | `scripts/backup.sh:20` | `pg_dumpall -U nextcloud` hardcodes DB username instead of reading from env | TODO | +| 5 | High | `scripts/restore.sh:68` | `psql -U nextcloud` hardcodes DB username instead of reading from env | TODO | +| 6 | High | `scripts/deploy.sh:13` | `source .env` in a root-privileged script can execute arbitrary commands. Consider safer parsing or variable validation | TODO | +| 7 | Medium | `monitoring/docker-compose.yml` | Docker socket + `/proc` + `/sys` + `/` mounted into Alloy container. Consider using a Docker socket proxy to limit API access | TODO | +| 8 | Medium | `caddy/Caddyfile` | No rate limiting configured at the reverse proxy layer | TODO | +| 9 | Low | `gitea/docker-compose.yml` | `gitea/gitea:latest-rootless` unpinned — pin to specific version like Nextcloud does | TODO | +| 10 | Low | `monitoring/docker-compose.yml` | `grafana/alloy:latest` unpinned — pin to specific version | TODO |