Files
2026-07-18 08:01:57 -07:00

3.2 KiB

AGENTS.md

Stack conventions

  • Every stack has at least 3 files: compose.yaml (dockhand style), sample.env, README.md
  • _dev = experimental, _notes = docs/minimal examples, no suffix = production-ready
  • _notes stacks are exempt from all conventions below — they hold notes, example commands, or minimal compose files only
  • Always references an external proxy network (managed by Nginx Proxy Manager; docker network create proxy once)
  • Volumes use ${VOL_PATH:-/data} as the base path (absolute /data, never ./data); project directories use ${VOL_PROJECTS:-/data}
  • Timezone defaults to America/Vancouver, but only include if the container requires it.
  • Restart policy, image tag, and port are configurable via env vars with sensible defaults
  • New stacks: copy from _docs/template-compose.md and _docs/template-readme.md
  • Compose section order: imagerestartvolumesenvironmentportsnetworksdepends_onhealthchecklabelscommanduser
  • Healthchecks are a future feature — do not add healthcheck blocks to stacks at this time (the section order above just reserves their place)
  • README section order: OverviewProject DetailsGetting StartedEnvironment Variable NotesVolume NotesNetwork NotesDocker RunAdditional Notes / GotchasDockhand Stack, Deploy from Git
  • Every compose file must declare the external proxy network at the root level:

networks: proxy: external: true

- Multi-service stacks also use a bridge network named `internal` (see `network.yml` at the repo root for the sample): databases and other backing services join `internal` only; the app service joins both `proxy` and `internal`
- Default secrets (passwords, keys, tokens) are always the literal `ChangeThisPassword` — same string everywhere so it is easy to grep. Users must change them; never ship a real-looking secret as a default
- Lint the repo with `python3 _docs/lint.py` before committing — it checks all of the conventions above

## Known exceptions

These deliberately violate the conventions above — do not "fix" them:

- `pihole` uses `network_mode: host` (it's a DNS server), so it has no `proxy` network
- `pangolin_dev` is itself an edge reverse proxy (Pangolin + gerbil + traefik), not a client of NPM; the `proxy` network is declared for convention but unused by its services, and `traefik` uses `network_mode: service:gerbil` instead of joining `internal`
- `zammad_dev` `zammad-init` service hardcodes `restart: on-failure` (init container)
- `nextcloud/compose-aio.yaml` follows the upstream AIO layout: fixed container/volume names, no env templating, no proxy network
- `opencode` and `vscode` default `VOL_PROJECTS` to `${VOL_PATH:-/data}/projects` (nested default), not plain `/data`
- `mailu_dev` passes env via `env_file: .env`, so its sample.env holds vars the compose file never references
- `headscale_dev` sample.env documents `HEADSCALE_DOMAIN`/`HEADSCALE_URL` for the config file even though compose doesn't use them

## No CI/CD, no dependency management

This is a Docker Compose file collection, not a code project. No tests, no build tools, no lockfiles.