Apply a consistent naming convention to the Make target inventory so
every target is grouped by its domain:
- compose-* (compose-up/down/restart/stop/exec/inner-run)
- network-* (network-dns-setup/remove, network-ipv6-disable/restore,
network-refresh, network-trust-ca)
- security-* (security-apparmor-restore/teardown)
- diagnose-* (diagnose-network, diagnose-disk-usage)
- fix-* (fix-chmod, fix-dockerignore)
- clean-* (clean-cache, clean-pycache-dirs)
- install-* (install-agent)
- meta-* (meta-list, meta-tree, meta-mig)
Drop the stale debug-network target and reintroduce its functionality
as diagnose-network. Cascade renames through:
- Makefile (.PHONY entries, prereqs, recursive $(MAKE) calls)
- contributor docs, agent-iteration docs, role-level docs
- bundle README, environment scripts, install/lint/test wrappers
- AGENTS.md, CLAUDE.md, compose/cache.override.yml, .github/workflows
Historical entries under docs/requirements/ and changelog/ stay
untouched as audit logs.
Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
7.8 KiB
compose.yml 🐳
This page documents the rules that govern the top-level compose.yml and the environment variables it consumes. For general documentation rules (links, writing, RFC 2119 keywords), see documentation.md. For CI debugging workflows that use these variables, see ci.md.
Purpose 🎯
The top-level compose.yml is scoped to local development and CI testing only.
It MUST NOT be used to deploy or run a live Infinito.Nexus stack.
Production deployments MUST go through the Ansible roles and their own rendered compose files under roles/<role>/templates/.
Within its scope, compose.yml MUST stay a thin orchestration surface for the infinito runner container and its CoreDNS sidecar.
It MUST NOT host application roles, fixtures, or test harnesses.
Structure 📐
- You MUST consume tunable runtime parameters via strict substitution
${VAR:?Run 'make dotenv' to generate the .env single source of truth}; the default lives in default.env. Inline${VAR:-default}forms are forbidden and enforced by test_no_default_substitutions.py. - You MUST NOT hardcode values that differ between operators (paths, image tags, CPU or memory caps).
- You SHOULD annotate non-obvious keys with a short inline comment that explains why they exist, not what they do.
- You MUST document every new env var by adding the row below AND committing a one-line
# ...comment above its key in default.env.
Environment Variables 📋
All variables consumed by compose.yml. The per-variable default + comment lives next to the key in default.env; the tables below stay scoped to "what role does this variable play in compose.yml" and stop duplicating the default.
Image and Runtime
| Variable | Purpose |
|---|---|
INFINITO_IMAGE |
Image reference used by the infinito service. Composed at runtime by the env generator on GHA, empty locally so the build: block builds from source. |
INFINITO_PULL_POLICY |
Compose pull_policy. Defaults to never for local builds, generator overrides to always on GHA. |
INFINITO_CONTAINER |
Used directly as container_name. Derived from INFINITO_DISTRO by infinito_container.py. |
NIX_CONFIG |
Build-arg forwarded to the Dockerfile for Nix configuration. Pass-through if set in the calling shell. |
Resource Caps (OOM Reproduction)
These variables cap the infinito container so local runs can reproduce GitHub-hosted runner pressure.
Each default is 0, which Docker interprets as "unlimited" and is identical to omitting the key.
See ci.md for runner specs and reproduction profiles.
| Variable | Compose key | Example override |
|---|---|---|
INFINITO_MEM_LIMIT |
mem_limit |
16g |
INFINITO_MEMSWAP_LIMIT |
memswap_limit |
16g |
INFINITO_CPUS |
cpus |
4 |
You SHOULD set INFINITO_MEMSWAP_LIMIT to the same value as INFINITO_MEM_LIMIT to disable swap inflation.
Allowing swap masks OOM conditions that the real runner would hit.
Storage
| Variable | Purpose |
|---|---|
INFINITO_DOCKER_VOLUME |
Named volume (or host path) backing the nested Docker directory. Generator overrides to /mnt/docker on GHA. |
INFINITO_DOCKER_MOUNT |
Mount point inside the container for the nested Docker data. |
Caches
For activation, coverage, and operations of the registry-cache, package-cache, and package-cache-frontend services, see cache.md.
The env-var contracts each service expects strictly via ${VAR:?…} (consumed in compose.yml and compose/cache.override.yml):
| Variable | Purpose |
|---|---|
INFINITO_CACHE_REGISTRY_HOST_PATH |
Host path bind-mounted into registry-cache for blob/manifest persistence. |
INFINITO_CACHE_REGISTRY_CA_HOST_PATH |
Host path holding the proxy MITM CA bundle. Mounted writable into registry-cache, read-only into infinito. |
INFINITO_CACHE_REGISTRY_MAX_SIZE |
Maximum on-disk size. Computed by infinito_registry_cache_max_size.py as half the free disk at the cache path, floor 1g, fallback 2g. |
INFINITO_CACHE_REGISTRY_PROXY_CONF |
Bind source for the systemd drop-in inside infinito. Set by the dev tooling to the real proxy.conf under the cache profile. Driver-injected; not produced by make dotenv. |
INFINITO_CACHE_PACKAGE_HOST_PATH |
Host path bind-mounted at /nexus-data. |
INFINITO_CACHE_PACKAGE_HEAP |
JVM heap (-Xms/-Xmx). Computed as half free RAM, capped 2g, floor 1g. |
INFINITO_CACHE_PACKAGE_DIRECT_MEM |
MaxDirectMemorySize. Mirrors INFINITO_CACHE_PACKAGE_HEAP. |
INFINITO_CACHE_PACKAGE_BLOBSTORE_MAX |
Soft quota for the default blobstore. Computed as half free disk at the cache path, floor 2g. |
INFINITO_CACHE_PACKAGE_MAX_AGE_MIN |
Cache freshness window in minutes, applied to every Nexus proxy repo (contentMaxAge/metadataMaxAge/negative-cache TTL). Stays strictly below the 7-day Valid-Until window Debian / Ubuntu generate in their apt Release files, so apt-get update never aborts with "Release file ... is expired". |
INFINITO_CACHE_PACKAGE_ADMIN_PASSWORD |
Target value for the rotated Nexus admin password. Default is a stable per-host hash. |
INFINITO_CACHE_PACKAGE_PORT |
Host-side port mapped to Nexus REST/UI. Bound to ${INFINITO_BIND_IP} only. |
INFINITO_CACHE_PACKAGE_PIP_CONF |
Bind source for /etc/pip.conf. Driver-injected by make compose-up under the cache profile. |
INFINITO_CACHE_PACKAGE_NPMRC |
Bind source for /root/.npmrc. Driver-injected. |
INFINITO_CACHE_PACKAGE_APT_LIST |
Bind source for /etc/apt/sources.list.d/package-cache.list. Driver-injected. |
INFINITO_CACHE_PACKAGE_FRONTEND_CA_DIR |
Host directory for the frontend CA. |
INFINITO_CACHE_PACKAGE_FRONTEND_CERTS_DIR |
Host directory for per-hostname leaf certs. |
INFINITO_CACHE_PACKAGE_FRONTEND_IP |
Static IPv4 address for the frontend on the compose default network. |
INFINITO_CACHE_PACKAGE_FRONTEND_CA_FILE |
Bind source for /opt/package-frontend-ca.crt inside the runner. Driver-injected. |
Networking
| Variable | Purpose |
|---|---|
INFINITO_DNS_IP |
Static IP assigned to the CoreDNS sidecar and used as the DNS server. Default lives in default.env. |
INFINITO_IP4 |
Static IPv4 address assigned to the infinito container. Default in default.env. |
INFINITO_DOMAIN |
Base domain exported into the container environment. Default in default.env. |
INFINITO_BIND_IP |
Host address that all published ports bind to. |
INFINITO_SUBNET |
IPAM subnet for the default bridge network. |
INFINITO_GATEWAY |
IPAM gateway for the default bridge network. |
INFINITO_OUTER_NETWORK_MTU |
MTU for the bridge network. Lower when the host network is tunneled. |
Adding a Variable ➕
When you introduce a new env var in compose.yml, you MUST:
- Add the default + one-line
# ...comment to default.env; defaults never live incompose.yml. - Consume the variable strictly via
${VAR:?Run 'make dotenv' to generate the .env single source of truth}; bare${VAR}is acceptable only when the value is optional (e.g.NIX_CONFIG). - Add a row to the matching table above with its compose-side purpose.
- Cross-link the variable from the relevant workflow page when it exists only to drive a specific workflow (e.g. resource caps link to ci.md).