Skip to content

Sandbox

sandbox

Compose terok-sandbox install with executor-side route generation.

Routes come from the YAML agent roster — sandbox (correctly) doesn't know about rosters, so the pair that makes a runnable sandbox lives here. One entry point means every frontend that wants a functional runtime reaches for the same composition.

ensure_sandbox_ready(*, cfg=None, no_vault=False, **aggregator_kwargs)

Generate vault routes, then run the sandbox install aggregator.

Regenerating routes.json up front is what makes routing config current before any launch — the per-container supervisor reads it at container start. A bare aggregator call would leave a stale routes.json in place and credential fetch would break on the next terok-executor run until the operator remembers to run vault routes.

no_vault gates the routes pre-step (if vault isn't being touched, don't regenerate); other no_* flags flow through to the aggregator.

Routes regeneration renders a Vault routes stage line so it sits in the same column as the aggregator's own output rather than failing silently above it — a corrupt YAML roster is the most plausible reason for setup to fail before the aggregator even starts, and a stage-shaped failure beats an unframed traceback.

Source code in src/terok_executor/sandbox.py
def ensure_sandbox_ready(
    *,
    cfg: SandboxConfig | None = None,
    no_vault: bool = False,
    **aggregator_kwargs: Any,
) -> None:
    """Generate vault routes, then run the sandbox install aggregator.

    Regenerating ``routes.json`` up front is what makes routing config
    current before any launch — the per-container supervisor reads it
    at container start.  A bare aggregator call would leave a stale
    ``routes.json`` in place and credential fetch would break on the
    next ``terok-executor run`` until the operator remembers to run
    ``vault routes``.

    ``no_vault`` gates the routes pre-step (if vault isn't being
    touched, don't regenerate); other ``no_*`` flags flow through to
    the aggregator.

    Routes regeneration renders a ``Vault routes`` stage line so it
    sits in the same column as the aggregator's own output rather
    than failing silently above it — a corrupt YAML roster is the
    most plausible reason for setup to fail before the aggregator
    even starts, and a stage-shaped failure beats an unframed
    traceback.
    """
    from terok_executor.integrations.sandbox import _handle_sandbox_setup, stage_line
    from terok_executor.roster import AgentRoster

    if not no_vault:
        with stage_line("Vault routes") as s:
            AgentRoster.shared().ensure_vault_routes(cfg=cfg)
            s.ok("regenerated")
    _handle_sandbox_setup(cfg=cfg, no_vault=no_vault, **aggregator_kwargs)