···1111## Commands
1212- `nix develop --impure --accept-flake-config` - Enter dev shell (flags required; --impure for devenv CWD detection, --accept-flake-config activates the Cachix binary cache in nixConfig — without it, a cold build takes 20+ minutes)
1313- `nix build .#relay --accept-flake-config` - Build relay binary (output at ./result/bin/relay)
1414-- `nix build .#docker-image --accept-flake-config` - Build Docker image tarball (Linux only; `docker-image` is not exposed on macOS — use a remote Linux builder or CI)
1414+- `nix build .#docker-image --accept-flake-config` - Build Docker image tarball (Linux only; output at `./result`; load with `docker load < result`; `docker-image` is not exposed on macOS — use a remote Linux builder or CI)
1515- `cargo build` - Build all crates
1616- `cargo test` - Run all tests
1717- `cargo clippy` - Lint
+1-1
docs/design-plans/2026-03-08-MM-66.md
···5454- **`TZDIR`**: An environment variable recognised by the C library and Rust's `time`/`chrono` crates that points to the timezone database directory. Set in the Docker image config to the tzdata store path.
5555- **`cargoArtifacts`**: Crane's name for the pre-built dependency artifact set produced by `buildDepsOnly`. Passed into `buildPackage` so incremental rebuilds skip recompiling dependencies.
5656- **closure**: In Nix, the full set of store paths that a derivation depends on transitively. The Docker image's closure is exactly what ends up in its filesystem layers.
5757-- **`self.shortRev`**: A flake variable holding the short git commit hash of the repository at build time. Mentioned in the tag strategy as a future replacement for `"latest"` to produce traceable image tags.
5757+- **`self.shortRev`**: A flake variable holding the short git commit hash of the repository at build time. Mentioned in the tag strategy as a future replacement for `"latest"` to produce traceable image tags. Note: `self.shortRev` is absent on dirty trees (uncommitted changes), causing a flake evaluation error unless guarded as `self.shortRev or "dev"`.
5858- **stub**: Used in this document to mean the relay binary currently compiles and exits but does not serve HTTP traffic. The Docker packaging is tested against this stub rather than a fully functional server.
59596060## Architecture
···33set -euo pipefail
4455PROJECT_ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
66+cd "$PROJECT_ROOT"
6778echo "=================================================="
89echo "MM-66 Automated Verification Tests"
910echo "=================================================="
1011echo
11121212-# Track pass/fail status
1313FAILED=0
14141515-# AC1.3: Verify docker-image is absent for Darwin systems
1515+# AC1.3: Verify docker-image is absent for Darwin systems, present for Linux.
1616+#
1717+# Uses `nix eval` to inspect package attribute names per system — structurally
1818+# reliable and avoids parsing `nix flake show` tree output with brittle grep -A
1919+# heuristics. --accept-flake-config activates the Cachix binary cache; without
2020+# it, evaluation on a cold machine may trigger a 20+ minute build.
1621echo "AC1.3: Checking docker-image platform availability..."
17221818-# First, try nix flake show
1919-if nix flake show --accept-flake-config 2>/dev/null | grep -q docker-image; then
2020- echo " nix flake show: Available"
2121- # Check that docker-image only appears under Linux systems
2222- DARWIN_DOCKER=$(nix flake show --accept-flake-config 2>/dev/null | grep -A 5 "aarch64-darwin\|x86_64-darwin" | grep -c "docker-image" || true)
2323- LINUX_DOCKER=$(nix flake show --accept-flake-config 2>/dev/null | grep -A 5 "aarch64-linux\|x86_64-linux" | grep -c "docker-image" || true)
2424-2525- if [ "$DARWIN_DOCKER" -eq 0 ] && [ "$LINUX_DOCKER" -gt 0 ]; then
2626- echo " PASS: docker-image present only on Linux systems (aarch64-linux, x86_64-linux)"
2727- else
2828- echo " FAIL: docker-image incorrectly appearing on Darwin or missing from Linux"
2929- FAILED=1
3030- fi
2323+DARWIN_PACKAGES=$(nix eval --json --accept-flake-config ".#packages.aarch64-darwin" --apply 'builtins.attrNames')
2424+if echo "$DARWIN_PACKAGES" | grep -q "docker-image"; then
2525+ echo " FAIL: docker-image incorrectly present on aarch64-darwin"
2626+ FAILED=1
3127else
3232- # Fallback: Use nix eval to check package attributes per system
3333- echo " nix flake show: Unavailable (expected due to devenv CWD detection issue), using fallback"
3434-3535- # Check Darwin systems do NOT have docker-image
3636- DARWIN_PACKAGES=$(nix eval --json ".#packages.aarch64-darwin" --apply 'builtins.attrNames' 2>/dev/null || echo "[]")
3737- if echo "$DARWIN_PACKAGES" | grep -q "docker-image"; then
3838- echo " FAIL: docker-image incorrectly present on aarch64-darwin"
3939- FAILED=1
4040- else
4141- echo " PASS: docker-image absent from aarch64-darwin"
4242- fi
2828+ echo " PASS: docker-image absent from aarch64-darwin"
2929+fi
43304444- # Check Linux systems DO have docker-image
4545- LINUX_PACKAGES=$(nix eval --json ".#packages.x86_64-linux" --apply 'builtins.attrNames' 2>/dev/null || echo "[]")
4646- if echo "$LINUX_PACKAGES" | grep -q "docker-image"; then
4747- echo " PASS: docker-image present on x86_64-linux"
4848- else
4949- echo " WARN: docker-image not detected on x86_64-linux (may be due to evaluation context)"
5050- fi
3131+LINUX_PACKAGES=$(nix eval --json --accept-flake-config ".#packages.x86_64-linux" --apply 'builtins.attrNames')
3232+if echo "$LINUX_PACKAGES" | grep -q "docker-image"; then
3333+ echo " PASS: docker-image present on x86_64-linux"
3434+else
3535+ echo " FAIL: docker-image missing from x86_64-linux"
3636+ FAILED=1
5137fi
52385339echo
54405555-# AC3.4: Verify nix/docker.nix is tracked by git
4141+# AC3.4: Verify nix/docker.nix is tracked by git.
5642echo "AC3.4: Checking nix/docker.nix git tracking..."
5757-5858-cd "$PROJECT_ROOT"
59436044if git ls-files nix/docker.nix | grep -q "nix/docker.nix"; then
6145 echo " PASS: nix/docker.nix is tracked by git"
···6549fi
66506751echo
5252+5353+# Docker smoke test (Linux only — docker-image is not exposed on Darwin).
5454+# Runs when Docker is available and relay:latest is already loaded, confirming
5555+# the relay binary and libsqlite3.so are present in the image closure. The relay
5656+# is a stub and may exit non-zero; that is acceptable. Only linker/missing-file
5757+# errors indicate a broken image.
5858+if command -v docker >/dev/null 2>&1 && docker image inspect relay:latest >/dev/null 2>&1; then
5959+ echo "Docker smoke test: relay:latest found — verifying binary and dynamic linking..."
6060+ OUTPUT=$(docker run --rm relay:latest 2>&1 || true)
6161+ if echo "$OUTPUT" | grep -qE "no such file|error while loading shared libraries"; then
6262+ echo " FAIL: linker or missing-binary error detected"
6363+ echo " $OUTPUT"
6464+ FAILED=1
6565+ else
6666+ echo " PASS: relay:latest ran without linker or missing-binary errors"
6767+ fi
6868+ echo
6969+fi
68706971# Summary
7072echo "=================================================="