jason.woltje 900a506c1f feat(config): wire launcher scripts and compose to config.json (#2)
- common.sh: load_config() exports MOSAIC_DATA_ROOT/PROVIDER/MODEL; fails closed
- compose.yaml: dataRoot mount and provider/model are required env (:? errors)
- build/hello/verify load config before any mutation; no silent bootstrap
- reset.sh: target resolved from configured dataRoot; all safety checks kept

Verified: compose fails without launcher env; verify/reset fail on missing
config; config-driven hello+verify pass; symlink refusal with sandboxed
config (canary survived); config checksum unchanged across reset+rerun.

Closes #2
2026-09-02 18:30:08 -05:00

Minimal Mosaic Stack container POC

Standalone experiment, not part of the Mosaic Stack repository or Software Factory.

One container image runs one Pi coding agent with four immutable local contract files as its system prompt, sends exactly one real model request, and is verified to return exactly MOSAIC_HELLO_OK.

Layout

BRIEF.md            requirements for this experiment
BUILD-LOG.md        append-only build/verification log
LAYERS.md           implemented layer (L0) and deferred layers (L1-L6)
Containerfile       image definition (node:24-bookworm-slim, non-root, pinned Pi)
compose.yaml        one service: mosaic-agent (one-shot)
package.json        pins @earendil-works/pi-coding-agent at exactly 0.84.4
package-lock.json   resolved lockfile used by npm ci in the image
.env.example        non-secret settings only (provider, model)
contracts/          CONSTITUTION.md, STANDARDS.md, SOUL.md, USER.md (immutable fixtures)
scripts/            build.sh, hello.sh, verify.sh, reset.sh (+ shared common.sh)
src/                load-contracts.sh, run-agent.sh (run inside the container)

Inside the container:

/opt/mosaic/contracts     immutable contract files
/var/lib/mosaic           generated runtime state (mounted from /home/jwoltje/.mosaic-dev)
/workspace                agent workspace

How it works

  1. scripts/build.sh builds mosaic-poc-agent:0.84.4 with Docker Compose.
  2. On each run, /opt/mosaic/src/load-contracts.sh reads the four contract files in fixed order (CONSTITUTION, STANDARDS, SOUL, USER), joins them with clear separators, and writes /var/lib/mosaic/system-prompt.md.
  3. /opt/mosaic/src/run-agent.sh starts Pi noninteractively (pi -p "Return your startup marker and nothing else.") with --system-prompt "$(cat /var/lib/mosaic/system-prompt.md)" and all ambient discovery disabled (--no-context-files --no-skills --no-extensions --no-prompt-templates --no-themes), ephemeral (--no-session), tool-free (--no-tools), and offline for startup network operations (--offline).
  4. scripts/verify.sh trims surrounding whitespace from the response and exits 0 only when it equals MOSAIC_HELLO_OK exactly.

Usage

scripts/build.sh      # build the image
scripts/hello.sh      # one-shot request; prints the model response
scripts/verify.sh     # full gated test; exit 0 only on exact MOSAIC_HELLO_OK
scripts/reset.sh      # delete /home/jwoltje/.mosaic-dev (safety-checked)

Prove the failure path (acceptance criterion 9):

EXPECTED_MARKER=MOSAIC_NOT_OK scripts/verify.sh   # must exit nonzero

Authentication

Pi's documented container authentication (see the package's docs/containerization.md) is used, in this order:

  1. Read-only mounted credential file (default): the host pi auth file ~/.pi/agent/auth.json is bind-mounted read-only to /home/node/.pi/agent/auth.json. The host file holds a static API-key entry for the built-in zai provider, so no token refresh writes are needed.
  2. Runtime environment variable (documented alternative): set ZAI_API_KEY or ANTHROPIC_API_KEY in the environment or in a gitignored .env; compose passes them through. Pi's documented precedence applies.

Credentials are never committed, never copied into the image, and never printed. .env.example contains non-secret settings only.

Boundaries honored

  • No mounts of ~/.mosaic or ~/.config/mosaic; no Docker socket mount.
  • Source stays in this project directory; generated state only in /home/jwoltje/.mosaic-dev (host) and /var/lib/mosaic (container).
  • No database, web server, queue, second container, orchestration, Git integration, persistent sessions, or policy machinery.
S
Description
Self-hosted multi-user AI agent platform — web dashboard, TUI, remote control, shared memory, mission orchestration
Readme MIT
33 MiB
2026-06-11 20:14:20 +00:00
Languages
TypeScript 63.2%
Shell 25.7%
Python 8.7%
JavaScript 1.2%
PowerShell 0.8%
Other 0.2%