# Docker Compose — Home Server ## Services | Container | Image | Purpose | |-----------|-------|---------| | `duckdns` | `lscr.io/linuxserver/duckdns` | Dynamic DNS — keeps `*.duckdns.org` pointed at the home IP | | `caddy` | `caddy` (custom build) | HTTPS reverse proxy with automatic Let's Encrypt certificates via DuckDNS DNS-01 | | `homeassistant` | `homeassistant/home-assistant` | Home automation, reachable at `https://ha-padriano.duckdns.org` | | `timemachine` | `mbentley/timemachine:smb` | Time Machine backup server over SMB | | `samba` | `dperson/samba` | General SMB file share for Mac and Linux clients | | `forgejo` | `codeberg.org/forgejo/forgejo` | Self-hosted Git server at `https://git-padriano.duckdns.org`, SSH at `:2222` | ## Initial Setup 1. Copy and fill in the environment file: ```bash cp .env.example .env nano .env ``` 2. Register the required DuckDNS subdomains at [duckdns.org](https://www.duckdns.org): `ha-padriano`, `padrianoha`, `padriano`, `git-padriano`. 3. Create the required host directories if they don't exist: ```bash mkdir -p /home/padriano/projects/forgejo mkdir -p /home/padriano/share ``` The Samba container runs as UID/GID 1001 internally, so the share directory must be owned by that user: ```bash sudo chown 1001:1001 /home/padriano/share ``` 4. Add the reverse proxy trusted header config to Home Assistant: ```bash sudo tee -a /home/padriano/projects/ha/config/configuration.yaml > /dev/null << 'EOF' http: use_x_forwarded_for: true trusted_proxies: - 172.16.0.0/12 EOF ``` 5. Bring the full stack up (first run builds the custom Caddy image): ```bash cd /home/padriano/projects/composer docker compose up -d --build ``` --- ## Common Docker Compose Commands ### Stack management ```bash # Start all services (detached) docker compose up -d # Stop all services (containers remain) docker compose stop # Stop and remove all containers (data volumes are preserved) docker compose down # Restart all services docker compose restart # Restart a single service docker compose restart homeassistant ``` ### Viewing status and logs ```bash # Show running containers and their status docker compose ps # Follow logs for all services docker compose logs -f # Follow logs for a single service docker compose logs -f forgejo # Show last 50 lines for a service docker compose logs --tail=50 timemachine ``` ### Updating images ```bash # Pull latest images for all services docker compose pull # Pull for a single service docker compose pull forgejo # Recreate containers that have a newer image docker compose up -d --pull always # Recreate a single service after pulling docker compose up -d --force-recreate forgejo ``` ### Inspecting containers ```bash # Open a shell inside a running container docker exec -it homeassistant bash docker exec -it forgejo sh # alpine-based, use sh not bash # Show resource usage (CPU, RAM, network) docker stats # Inspect container configuration docker inspect forgejo ``` --- ## Service Notes ### duckdns - Config stored at `/home/padriano/projects/duckdns/config` - Domains managed: `ha-padriano`, `padrianoha`, `padriano`, `git-padriano` (all `.duckdns.org`) - Subdomains must be registered manually at [duckdns.org](https://www.duckdns.org) before they can be updated ### caddy - Custom image built from `caddy/Dockerfile` — adds the [DuckDNS DNS provider plugin](https://github.com/caddy-dns/duckdns) to the official Caddy image - Config at `caddy/Caddyfile`; TLS certificates stored in the `caddy_data` Docker volume - Obtains free Let's Encrypt certificates via **DNS-01 challenge** (no extra ports needed, no cost) - Listens on `:80` (redirects to HTTPS) and `:443` - Routes: - `ha-padriano.duckdns.org` → Home Assistant `:8123` - `git-padriano.duckdns.org` → Forgejo `:3000` - To reload config without restarting: `docker exec caddy caddy reload --config /etc/caddy/Caddyfile` ### homeassistant - Config stored at `/home/padriano/projects/ha/config` - Web UI: `https://ha-padriano.duckdns.org` (via Caddy) or `http://server:8123` on the LAN - Runs on the `internal` bridge network so Caddy can reach it by container name - `configuration.yaml` must include `http.use_x_forwarded_for: true` and `trusted_proxies` for the Docker bridge range so HA accepts forwarded headers from Caddy - Has a healthcheck — status shows `(health: starting)` for ~60s on first boot ### timemachine - Backup data stored at `/home/padriano/backup/timemachine` - Uses `network_mode: host` and a fixed `hostname: timemachine` — the stable hostname prevents macOS from losing the backup destination after container restarts - On your Mac: **System Settings → General → Time Machine → Add Backup Disk** ### samba - Shared directory on the host: `/home/padriano/share` — must be owned by `1001:1001` (the UID/GID the container uses internally); without this, the share mounts on the Mac but files cannot be written - Uses a macvlan network with static IP `192.168.1.247` — avoids port 445 conflict with the `timemachine` container - Config stored at `samba/smb.conf`; the `[Share]` section is the only exported share - Avahi service file at `samba/avahi-smb.service` advertises the share for Finder sidebar discovery (installed to `/etc/avahi/services/samba.service` on the host) - **Connecting from a Mac**: open Finder → Go → Connect to Server → `smb://192.168.1.247/Share` - **Connecting from Linux**: `smbclient //192.168.1.247/Share -U samba` or mount with `mount -t cifs //192.168.1.247/Share /mnt/share -o username=samba` - Username and password are set via `SAMBA_USERNAME` / `SAMBA_PASSWORD` in `.env` ### forgejo - All data (repos, config, SQLite DB) stored at `/home/padriano/projects/forgejo` - Backing up this single directory is sufficient for a full restore - Port 3000 is no longer exposed on the host — access is via Caddy only #### First-run setup Visit `http://server:3000` on first start (LAN only) and complete the install wizard: - **Base URL**: `https://git-padriano.duckdns.org` - **SSH domain**: `git-padriano.duckdns.org` - **SSH port**: `2222` #### Access | Method | Local network | External (via DuckDNS) | |--------|---------------|------------------------| | Web UI | `http://server:3000` | `https://git-padriano.duckdns.org` | | Git SSH | `ssh://git@server:2222` | `ssh://git@git-padriano.duckdns.org:2222` | For external access, forward these ports on your router to the server IP: - TCP `443` → Caddy (HTTPS — serves both HA and Forgejo) - TCP `2222` → Forgejo SSH #### Git remote URL examples ```bash # Add remote via HTTPS git remote add origin https://git-padriano.duckdns.org/padriano/my-repo.git # Add remote via SSH git remote add origin ssh://git@git-padriano.duckdns.org:2222/padriano/my-repo.git # Clone via SSH (local) git clone ssh://git@server:2222/padriano/my-repo.git ``` --- ## Disk Space ```bash # Free space on the main filesystem df -h / # Free space on all mounted filesystems df -h # Space used by each service's data directory du -sh /home/padriano/projects/* /home/padriano/backup/* ``` --- ## Data & Backup Summary | Service | Host path | Notes | |---------|-----------|-------| | `duckdns` | `/home/padriano/projects/duckdns/config` | Token cache, not critical | | `caddy` | Docker volume `caddy_data` | Issued TLS certificates — auto-reissued if lost | | `homeassistant` | `/home/padriano/projects/ha/config` | All HA config and automations | | `timemachine` | `/home/padriano/backup/timemachine` | Mac backup sparsebundles | | `samba` | `/home/padriano/share` | General file share — back up as needed | | `forgejo` | `/home/padriano/projects/forgejo` | All repos, DB, config |