Skip to content

Generic per-harness cache pre-warm before sandboxing (first-launch plugin/dep fetch fails through omac's proxy; opencode is the first concrete case) #155

Description

@nhuelstng

Problem (general)

Any harness that fetches something from the network on its first launch — a plugin, a provider package, model metadata, a runtime component — breaks the first time it runs under omac start in a new workdir, because:

  1. Authenticated proxy not traversed. omac injects HTTP_PROXY/HTTPS_PROXY=http://omac:<token>@127.0.0.1:<port> and forces all egress through its filtering proxy. Installers/fetchers that don't send the proxy's basic-auth credentials fail silently — no net DENY line, because the request never becomes an allowed connection. --allow-domain on the registry does not help; it is not a filesystem grant issue either.
  2. Per-workdir cache. The tool cache is PreparePersistent(DomainWorkdir, …)~/.cache/omac/sha256(\"v1:workdir:\"+canonical-workdir), and omac start/serve inject XDG_CACHE_HOME=<scope>/xdg (internal/toolcache/cache.go, internal/cli/start.go). So the cache is per-workdir: every new project folder starts cold and re-hits the failing fetch. A one-time global warm does not help.

The harness works fine outside omac (direct fetch), but fails on the first omac start in any workdir the user has not already warmed. Since we cannot know in advance which folder the user will start omac in, a manual/install-time pre-warm of one workdir is not a reliable fix.

First concrete case: OpenCode @tngtech/opencode-skainet

OpenCode config declares plugin: [\"@tngtech/opencode-skainet@latest\"]; on startup it uses Bun's package installer to fetch the plugin, then loads it to register the skainet provider. Inside the sandbox the install fails (per above), so the provider is never registered:

ProviderModelNotFoundError: Model not found: skainet/zai-org/GLM-5.2

(surfaced as a generic UnknownError / Unexpected server error).

Reproduce

XDG_CACHE_HOME=$(mktemp -d)/xdg \
  omac sandbox run --profile tng-default --allow-domain chat.model.tngtech.com \
    --allow-env XDG_CACHE_HOME --write <config> --write <cache> \
    -- opencode run \"hello\"
# -> ProviderModelNotFoundError: Model not found: skainet/...

The cache dir is deterministic, so pre-warming a known workdir works and afterwards omac start there runs offline (verified) — but only for that one folder.

Other harnesses have analogous first-launch fetches (provider packages, model metadata, runtime components) that will hit the same wall; the fix should not be opencode-specific.

Proposed fix — a generic, harness-agnostic pre-warm

A per-harness declared warm step that omac runs in the prepared tool-cache scope, with direct network, before entering the sandbox. omac already prepares the toolcache scope (PreparePersistent) ahead of launch; run the harness's declared warm command against that scope first, then sandbox. Harness-agnostic: each harness (opencode, codex, copilot, future) declares its own warm command (e.g. opencode → opencode models); omac just runs whatever the active harness declares. One-time per workdir, automatic, no user action.

Alternatives (also harness-agnostic):

  • Proxy-aware fetch — make installs traverse omac's authenticated proxy (or have the proxy accept them), so no warm is needed at all.
  • Shared cache domain — let plugin/dep packages live in a cross-workdir shared cache so one warm covers every workdir.

Context

Found via the omac-tng-installer e2e suite (test/e2e), which reports OpenCode as a documented SKIP (known limitation) against a cold per-workdir cache rather than masking it with a same-workdir pre-warm. Claude Code, Codex, and the skainet/taia proxies all pass.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions