Skip to content

Latest commit

 

History

History
702 lines (635 loc) · 35.6 KB

File metadata and controls

702 lines (635 loc) · 35.6 KB

AGENTS.md

these rules define the engineering contract for emel.cpp. they are aligned with docs/rules/sml.rules.md. if a rule here conflicts with docs/rules/sml.rules.md, the doc wins and this file must be updated.

boost.SML actor model (aligned with docs/sml.rules.md)

ALWAYS follow the RTC actor model and no-queue invariant from docs/sml.rules.md. NEVER use sml::process_queue, sml::defer_queue, or any mailbox/post-for-later mechanism. ALWAYS keep dispatch run-to-completion and single-writer per actor. NEVER call an actor's own process_event from guards/actions/entry/exit. ALWAYS model internal multi-step flows with sml::completion<TEvent>, anonymous transitions, and/or entry actions. ALWAYS keep anonymous transition graphs acyclic or statically bounded. ALWAYS propagate originating event data across internal phases via typed completion transitions (sml::completion<TEvent>) when needed. NEVER use sml::completion<TEvent> or anonymous transitions as data-plane iteration loops (for example per-logit, per-token, or per-tensor-element scans). ALWAYS keep completion/anonymous chains phase-level only with a small, statically bounded number of transitions per top-level dispatch. ALWAYS implement bulk numeric iteration in allocation-free action/detail kernels within a single transition per phase. NEVER copy event payload into context just to bridge internal phases. ALWAYS keep guards pure predicates of (event, context) with no side effects. ALWAYS keep actions bounded and non-blocking during dispatch. ALWAYS keep hot-path actions allocation-free. ALWAYS keep any allowed one-time construction or initialization heap allocation before any process_event(...) dispatch. NEVER perform dynamic allocation during dispatch, including in guards, actions, entry/exit handlers, or anonymous/completion progress. ALWAYS model runtime behavior choice as explicit guards or explicit choice states/transitions. NEVER hide runtime behavior selection in actions, state machine member functions, or functions called from them. Treat "runtime behavior selection" semantically, not syntactically. It includes any helper-local branching, table lookup, flag dispatch, dtype dispatch, backend dispatch, modality dispatch, model-family dispatch, fallback selection, block-kind selection, activation-mode selection, skip/residual selection, buffer-lane selection, callback/error-channel selection, or other runtime choice that changes which algorithm, path, variant, or externally observable behavior executes. NEVER put runtime branching statements (if, else if, switch, ?:) in actions, state machine member functions, or functions called from them. NEVER put validation-path branching in actions or in functions called from actions; model validation outcomes with guards and explicit transitions. NEVER emulate runtime branching with loop constructs in actions, detail helpers, state machine member methods, or functions called from them. NEVER use single-pass loop patterns such as for (bool cond = ...; cond; cond = false) to choose control paths. NEVER use branch-case loop patterns such as for (size_t emel_case_* = emel_branch_*; ...) to choose control paths. NEVER use runtime-indexed handler/candidate arrays (including function-pointer tables) as a substitute for explicit guards/states/transitions. ALWAYS use loops in actions/detail only for data-plane iteration with monotonic progress and bounded work. Compile-time conditionals (if constexpr, #if) are allowed inside actions, state machine member methods, or functions called from actions. NEVER perform I/O waits, mutex waits, or sleeps inside guards/actions. ALWAYS inject time via event payloads; NEVER read wall-clock time in guards or actions. ALWAYS keep publicly exposed events immutable and small; prefer trivially copyable payloads when copies are cheap and not on a hot path. INTERNAL-only events that are not publicly exposed MAY use mutable pointers/references for synchronous same-RTC handoff. NEVER expose mutable internal-event payload via public API types. NEVER retain mutable internal-event payload beyond the top-level dispatch call. NEVER put owning pointers or dynamic containers in events unless you can prove no allocation during dispatch. ALWAYS validate runtime event IDs before using sml::utility::make_dispatch_table. ALWAYS inject a component-local context via SML constructor dependency injection. NEVER rely on constructor parameter order; prefer a single context aggregate. ALWAYS use visit_current_states or is(...) for state inspection. NEVER allow re-entrancy into the same actor within one RTC chain. ALWAYS keep cross-actor synchronous calls acyclic and deterministically ordered. callbacks (emel::callback) are allowed only for immediate synchronous replies within the same RTC chain; invoke before dispatch returns, never store in context, and never call process_event inside the callback. ALWAYS define explicit behavior for unexpected events; NEVER drop them silently. ALWAYS use sml::unexpected_event for unexpected-event handling (never event<sml::_>). sml::unexpected_event<_> is only raised for unhandled external events; it already excludes internal events. do NOT guard it to exclude boost::sml::back::internal_event, or you will suppress the unexpected event itself. ALWAYS reproduce a reported bug by adding a failing unit test before making fixes. ALWAYS keep tracing deterministic, bounded, and allocation-free; use sml::logger<...> when needed.

architecture and composition

ALWAYS use boost.SML for orchestration state machines. ALWAYS define transition tables in struct model and expose using sm = boost::sml::sm<model>;. ALWAYS write transition rows in destination-first form: sml::state<dst> <= src + event [guard] / action. NEVER write source-first rows in new or modified code (src + event [guard] / action = dst). ALWAYS keep the destination state and <= on the same line. ALWAYS organize large transition tables into explicit visual sections using phase labels and divider comments (for example //------------------------------------------------------------------------------//). ALWAYS use leading-comma row style after the first row inside make_transition_table(...). ALWAYS use narrowly scoped // clang-format off/on around transition tables when formatting would reduce readability. ALWAYS use this canonical transition-table skeleton for readability and consistency: return make_transition_table( then one first row, then each additional row prefixed with ,, with destination-first <= rows only. NEVER use macros in models. ALWAYS keep canonical machine types in component namespaces as emel::<component>::sm. ALWAYS provide additive top-level PascalCase aliases (e.g. emel::Model). ALWAYS map directory layout to namespaces. ALWAYS keep component files limited to the canonical bases any, context, actions, guards, errors, events, sm, or detail, with either .hpp or .cpp extensions as needed. ALWAYS structure machine docs and code namespaces using the pattern <domain>/<component>/<type> for variant families (for example memory/coordinator/kv, text/tokenizer/preprocessor/bpe). ALWAYS colocate machine definition, data, guards, actions, and events within the same component directory. NEVER place orchestration logic in data-only files. ALWAYS treat domains as ownership boundaries, not naming decoration. A domain-specific implementation MAY depend inward on shared kernel, model, text, speech, memory, or runtime primitives, but shared layers MUST NOT include or name downstream domain runtime internals. NEVER create top-level runtime domains for model families unless explicitly approved by the user. For example, Whisper speech runtime belongs under src/emel/speech/encoder/whisper/** and src/emel/speech/decoder/whisper/**, model binding belongs under src/emel/model/whisper/**, and tokenizer policy belongs under src/emel/speech/tokenizer/whisper/**; never add src/emel/whisper/**, src/emel/speech/asr/whisper/**, or src/emel/kernel/whisper/**. NEVER expose emel::model::whisper contracts from speech encoder/decoder events, contexts, guards, or actions. Speech encoder/decoder runtime contracts must be speech-owned and constructed at the variant boundary after model binding validation. NEVER put model-family runtime contracts in generic public recognizer, generator, event, or context headers. Keep variant contracts in variant routes, variant detail events, or dispatch-local construction at the variant boundary. ALWAYS name variant-specific routes/components with the variant or domain name when they directly include variant detail, tokenizer, or model contracts; a generic-sounding route MUST NOT hardcode a model family. ALWAYS add or maintain domain-leak checks when adding or moving domain-specific code. At minimum, check for forbidden model-family roots such as rg 'emel/whisper|namespace emel::whisper|kernel/whisper|kernel::whisper' src tests CMakeLists.txt and check generic public headers for variant names they should not expose. ALWAYS run scripts/check_domain_boundaries.sh for any phase that touches variant/model-family placement, recognizer/generator public headers, tokenizer policy, model-family contracts, or kernel ownership. ALWAYS put runtime behavior choice in sm.hpp transitions using guards from guards.hpp. NEVER put runtime behavior choice in actions.hpp, detail.hpp, or detail.cpp. ALWAYS treat guards.hpp as the home for runtime predicates that decide which transition or behavior path is taken. ALWAYS treat actions.hpp as the home for bounded execution of an already-chosen behavior path. ALWAYS use state_, event_, guard_, effect_, enter_, and exit_ prefixes for newly introduced state-machine symbols in new or modified code. ALWAYS treat "symbols" here as transition-table aliases and helper identifiers such as local state/event aliases, guard/effect functors or functions, and entry/exit action names. NEVER rename existing repository state or event type names solely to satisfy this convention; apply it forward to new symbols you introduce or when touching code already being refactored. ALWAYS treat detail.hpp and detail.cpp as the home for shared hidden private non-control-flow helpers only. ONLY put a helper in detail.hpp or detail.cpp when it is used more than once. If logic is used by only one owning function or one actor, inline it into that owner. A helper used only once belongs in the owning guards.hpp or actions.hpp, not in detail.hpp or detail.cpp. Helpers called from effect_*, enter_*, exit_*, or detail code MUST NOT choose behavior, route fallback, mode selection, success/error outcome, or which path runs next. Those decisions belong only in guard_* predicates and sm.hpp transitions. If a helper inspects runtime dtype, backend support, architecture/model name, tensor layout, modality kind, block flags (for example has_skip, has_expand, has_dw_mid, has_se), activation kind, or scratch-buffer lane/destination to choose which computation or behavior runs, that helper is choosing behavior and MUST NOT live in detail.hpp or detail.cpp. NEVER put runtime support probing, route fallback, block-kind selection, or other behavior-selection control flow in detail.hpp or detail.cpp; model it in guards.hpp and sm.hpp. ALWAYS keep detail.hpp and detail.cpp helpers non-routing and non-orchestrating. ALWAYS keep detail helpers called from actions or state machine member methods limited to compile-time conditionals and data-plane iteration. Compile-time conditionals and data-plane iteration are allowed in detail.hpp and detail.cpp. Data-plane branching inside detail.hpp / detail.cpp is allowed only for the already-chosen algorithm's local numeric work, bounds handling, padding, clamping, or monotonic loop progress. It is NOT allowed to select the algorithm, path, variant, or behavior family itself. ALWAYS treat "what happens next" as orchestration behavior for detail.hpp and detail.cpp review. Helper output includes return values, out-parameters, reference mutation, pointer mutation, callback selection, and written context fields. NEVER use any detail.hpp or detail.cpp helper output to decide what happens next. If a helper affects which guard passes, which action runs, which callback fires, which event/state/error path is taken, or whether a dispatch is accepted, rejected, done, or failed, that helper MUST live in guards.hpp, actions.hpp, or sm.hpp, not in detail.hpp or detail.cpp. Superficial cleanup does NOT satisfy these rules. Removing if statements from actions.hpp while moving the same runtime choice into detail.hpp, helper return values, helper-selected buffer lanes, or helper-selected variants is still a rule violation. Shared non-control-flow helpers in detail.hpp or detail.cpp MUST use truthful non-routing verb prefixes such as compute_, validate_, bind_, scan_, append_, or reset_. Use compute_ only for data-plane or numeric work, never as a generic prefix for all helpers. NEVER use routing or selection verbs for non-guard helpers. ALWAYS give each machine its own process_event wrapper and context ownership. SHARE behavior via actions.hpp/detail.hpp helpers or sm_any, not inheritance. ALWAYS keep child-machine data owned by the parent-machine data when composing machines, and inject parent context into children by reference. ALWAYS communicate between machines through events and explicit interfaces only. NEVER call another machine's actions, guards, or functions directly. NEVER mutate another machine's context directly. ALWAYS dispatch cross-machine events only via machine->process_event(...). ALWAYS keep operator arithmetic, lowering, packing, quant/dequant, and backend-specific numeric work in the owning kernel layer (src/emel/kernel/** or a component-local kernel module when that component explicitly owns execution). ALWAYS keep higher layers limited to orchestration, metadata shaping, buffer binding, and dispatch into kernels. NEVER add ad hoc operator implementations, backend-specialized loops, lowering code, or packing helpers throughout generators, planners, loaders, graph orchestration, wrappers, tests, or tools just to bridge a missing kernel path. If existing code contains ad hoc compute outside kernel ownership, ALWAYS migrate that work into the owning kernel surface instead of extending the ad hoc path. ALWAYS make plans land new or changed ops in kernel-owned files first; non-kernel plan tasks may only wire, dispatch, validate, benchmark, or prove those kernels. NEVER duplicate code if it's used more than once; put it somewhere it can be shared.

events, outcomes, and errors

ALWAYS define trigger intent events in the event namespace using noun-like, domain-action names without cmd_ prefixes. ALWAYS define machine outcome events in the events namespace with explicit _done and _error suffixes. INTERNAL-only _done/_error events MAY carry mutable payload references when they are not publicly exposed outside the component boundary. ALWAYS use references for required event fields. NEVER model ordinary required event fields as pointers. ONLY use event payload pointers for optional/nullable fields or C ABI boundary types that cannot use references. ONLY allow optional _done/_error request back-pointers used only for same-RTC correlation to be nullable pointers under the optional-field rule. NEVER use cmd_*-prefixed event names. ALWAYS model failures via explicit error states and _error events. NEVER add synthetic fault-injection knobs to production events or actions. NEVER add test-only control fields to src/ machine/event payloads. ALWAYS encode retries and one-shot attempts in the transition graph, not in mutable context flags. NEVER mirror explicit state/event outcomes into context members. NEVER add redundant status_code fields when errors are modeled by states/events. NEVER store per-invocation API output pointers in machine context.

context rules

ALWAYS define a component-local state-machine context type (e.g. action::context). ALWAYS mutate context inside actions or internal transitions when needed. NEVER mutate context in guards. NEVER read or write context directly from state machine member functions. ALWAYS keep context focused on machine-owned runtime data required across internal phase events. NEVER store dispatch-local data in context. Dispatch-local data includes: current request/event pointers or refs, output pointers, phase flags, step indexes, temporary counts, and transient error/status codes. NEVER add context fields named or purposed like: request, event, phase, step, index, count, err, error, status, last_error, *_out, *_ptr. ALWAYS pass per-dispatch data across internal phases via typed internal events only (events::*_done / events::*_error or typed completion payloads), not context. ALWAYS keep context fields to persistent actor-owned state meaningful across top-level dispatch calls. If a machine has no persistent actor-owned state, context MUST be an empty struct. NEVER mirror per-dispatch request/event payload fields into context only for phase handoff. NEVER store orchestration phase/attempt/failure flags in context. NEVER add string/pointer error members to machine data.

API boundaries

ALWAYS use extern \"C\" for public API function signatures. ALWAYS use fixed-width integer types at API boundaries. ALWAYS return error codes across API boundaries. NEVER throw exceptions across API boundaries. NEVER expose C++ templates, classes, or STL containers directly in the public C ABI.

performance and allocation

ALWAYS treat performance as a top-level priority. NEVER use dynamic dispatch in inference hot paths unless explicitly justified. ALWAYS prefer compile-time polymorphism in hot paths. NEVER allocate in inference or sampling hot paths. NEVER use heap allocation by default. ALWAYS allow one-time heap allocation during construction, initialization, or other non-hot-path setup work when necessary. ALWAYS reuse unavoidable heap allocations. ALWAYS document rationale for unavoidable heap allocation in code. ALWAYS keep telemetry non-blocking and optional. NEVER use exceptions for control flow in hot paths. NEVER rely on try/catch inside state machine actions/guards; avoid exceptions unless absolutely necessary. ALWAYS keep actor models independent; do not share a model between actors unless explicitly authorized by the user. Only common actions/guards that are not variant-specific may be shared.

naming, style, and portability

ALWAYS use snake_case for functions, variables, and namespaces. ALWAYS use PascalCase for exported/public C++ types only (not C API types). ALWAYS use lower_snake_case for non-exported/internal types, SML state names, and events. ALWAYS use SCREAMING_SNAKE_CASE for constants and macros. ALWAYS keep line length near 100 columns and use 2-space indentation. NEVER use using namespace in headers. ALWAYS keep code portable across linux, macOS, and windows. NEVER use platform-specific APIs unless wrapped behind an abstraction. ALWAYS write scripts to work on any Unix-based OS.

build, tests, and CI gates

ALWAYS work on a feature branch and submit changes via a pull request. NEVER push directly to main. NEVER commit tmp/llama.cpp. ALWAYS use zig toolchain (zig cc and zig c++) for default development and production builds. ALWAYS use native clang or gcc for coverage builds. ALWAYS use doctest for unit tests. ALWAYS use SML introspection for machine assertions and testing. ALWAYS name test files by machine or domain (e.g. tests/inference/sampler_tests.cpp). NEVER use arbitrary or ad-hoc test file names. NEVER create monolithic test files. ALWAYS scope each test file to one machine, one system, or one behavior. ALWAYS keep one machine benchmark per tools/bench source file. ALWAYS keep snapshot baselines under snapshots/ and lint baselines under snapshots/lint/. NEVER update snapshots without explicit user consent. ALWAYS hard-fail runs when required tools are missing. ALWAYS enforce line coverage >= 90%. ALWAYS run scripts/quality_gates.sh after each implementation change. ALWAYS use the default changed-file scoped quality gate for normal phase iteration so unrelated dirty-tree benchmarks, docs, parity, or fuzz lanes do not make the phase gate stale or all-day by default. ALWAYS pass EMEL_QUALITY_GATES_CHANGED_FILES when the worktree contains unrelated user or agent changes, and scope it to the files actually changed by the current implementation. ALWAYS use EMEL_QUALITY_GATES_BENCH_SUITE when a phase has a known benchmark domain, for example diarization_sortformer, instead of running unrelated benchmark suites during local iteration. ALWAYS use EMEL_QUALITY_GATES_SCOPE=full scripts/quality_gates.sh before milestone closeout, release readiness, or cross-cutting changes that can affect multiple runtime domains. NEVER weaken coverage, parity, benchmark, fuzz, or docs checks to save time. If a lane is irrelevant to the scoped changed files it may be skipped by the gate, but if it is relevant it must run against the maintained implementation path. NEVER ignore benchmark snapshot failures in quality gates by default. Only use EMEL_QUALITY_GATES_ALLOW_BENCH_REGRESSION=1 for an explicitly documented transitional run, never for milestone closeout. ALWAYS use ctest targets emel_tests and lint_snapshot for test execution. ALWAYS reference docs/rules/sml.rules.md for SML semantics and testing guidance.

reference policy

ALWAYS treat src/ boost.SML machines as the single source of truth for architecture and orchestration. ALWAYS treat milestone-closeout claims about maintained runtime, fixture, contract, parity, benchmark, or benchmark-document truth as source-backed claims, not artifact-backed claims. ALWAYS verify those claims by tracing the actual repo codepath from the pinned fixture/model contract through the maintained loader/builder into the runtime, parity, benchmark, and publication entrypoints that make the claim. NEVER mark a requirement, audit, milestone, benchmark claim, parity proof, or closeout ledger as satisfied from ROADMAP.md, STATE.md, REQUIREMENTS.md, SUMMARY.md, VERIFICATION.md, or VALIDATION.md alone when the claim depends on which runtime path, model contract, fixture, or tool entrypoint actually runs. If code inspection shows a synthetic, fabricated, tool-only, or test-only contract/fixture/path is still feeding the claimed maintained runtime, ALWAYS treat the claim as unsatisfied until the maintained codepath is wired end to end. ALWAYS use src/emel/gbnf as the default architectural reference for new Boost.SML machine organization, decomposition, and transition-table layout, unless the current task explicitly requires a different reference family. NEVER maintain parallel machine-definition markdown specs under docs/architecture/*. ALWAYS document state purpose, key invariants, guard semantics, and action side effects. ALWAYS treat the reference implementation as the functional logic reference for allocator and behavioral parity work. NEVER port reference control flow, branching structure, lifecycle semantics, or orchestration decisions verbatim from llama.cpp/ggml. ALWAYS define EMEL behavior and orchestration semantics in boost.SML machines as source of truth. ALWAYS port llama.cpp/ggml arithmetic, kernels, and instruction behavior into this codebase when implementing equivalent EMEL functionality. ALWAYS preserve or improve performance when porting logic from the reference implementation. ALWAYS implement equivalent functionality natively without external llama.cpp or ggml linkage. NEVER link "emel" against llama.cpp or ggml outside tools/bench or tools/paritychecker. ALWAYS keep any llama.cpp/ggml linkage in tools/bench and tools/paritychecker confined to the explicit reference-side comparison path only. NEVER let the EMEL side of tools/bench or tools/paritychecker call into, bootstrap from, or otherwise depend on llama.cpp/ggml for vocab state, tokenizer state, formatter state, model loading, tensor metadata, runtime execution, or output generation. NEVER share llama.cpp/ggml-created model, vocab, tokenizer, formatter, context, or cache objects with the EMEL side in benchmark or parity harnesses. ALWAYS keep benchmark and parity harnesses split into two clearly separated lanes: an EMEL-owned lane using only EMEL-owned code for the EMEL result, and a reference lane using llama.cpp/ggml only for the comparison result. NEVER let parity harnesses or benchmarks reach into actor actions.hpp, detail.hpp, or detail.cpp helpers directly; drive them through the owning state machines via process_event(...) and public event interfaces only. NEVER use llama_ or ggml_ prefixes in identifiers, symbols, files, or APIs outside tools/bench or tools/paritychecker. ALWAYS use emel_ or EMEL_ prefixes for project-owned identifiers, symbols, files, and APIs. ALWAYS prefer porting the exact reference arithmetic and kernel operand path into EMEL-owned src/ code when the user asks for parity, benchmarking, or performance comparison against llama.cpp or ggml. ALWAYS treat reference-kernel parity work as incomplete until the corresponding EMEL-owned kernel consumes the same effective operand format as the reference path. NEVER replace a missing native packed or quantized kernel in a hot inference path with a dequantize-to-f32 fallback unless the user explicitly approves that fallback as an interim milestone. If an interim fallback is explicitly approved, ALWAYS label it interim in code comments, tests, milestone docs, and user updates, and ALWAYS state which exact reference operand or kernel path is still missing. NEVER present parity or benchmark results as kernel parity when EMEL and the reference implementation are not executing materially equivalent operand pipelines. ALWAYS ask the user before landing an implementation that changes the performance contract of a milestone by substituting a simpler fallback kernel, helper backend, or tool-local scaffold for the intended src/ runtime path. For quantized inference work, "done" means:

  1. EMEL-owned code in src/
  2. no tool-only compute fallback
  3. no whole-tensor dequantize-to-f32 substitution in the hot path
  4. benchmark claims based on the same effective operand class as the reference path When an implementation is architecturally narrower than the user's stated goal, ALWAYS stop and get explicit approval before proceeding, even if the narrower implementation is faster to complete.
# Role - ROLE: integration-checker

atmux Rules

  • Use plain atmux ... commands; do not prefix them with inherited session environment.

Managed Agent Rules

  • ALWAYS acknowledge manager messages quickly with a short plan.
  • ALWAYS send a message to your manager when stuck or after completing any task.
  • ALWAYS message your manager with atmux send --to agent-0 "...".
  • ALWAYS coordinate with peer agents using atmux send --to <agent> "...".
  • ALWAYS check atmux list agents --all --status before creating new agents.
  • ALWAYS reuse idle capable agents before creating new ones.
  • ALWAYS spawn agents to decompose your todos if necessary.
  • ALWAYS use --reply-required when a manager decision is needed.
  • NEVER poll agent panes unless absolutely necessary.
  • NEVER silently change scope; ask your manager first.
  • NEVER report task completion without validation evidence.
  • NEVER leave blockers unreported; escalate immediately.

atmux help

create

Usage: atmux create --agent --role --intelligence <0-100> [--team ] [--adapter ] [--no-worktree] [--task --description --todo ...] [-- <adapter-args...>] atmux create --team atmux create --issue --title <title> [--description ] [--todo ...] [--repo ] atmux create --pr --title <title> [--description ] [--source ] [--target ] [--todo ...] [--repo ]

Description: Unified create entrypoint for agents, teams, issues, and pull requests. For agents, --team defaults to ATMUX_TEAM when set (for example after atmux create --team <name> in a tmux session).

list

Usage: atmux list teams atmux list sessions atmux list agents [--all] [--status] atmux list issues [--repo ] atmux list prs [--repo ] atmux list messages [--unread]

Description: Listings are implemented by scripts under bin/(atmux)/(list)/.

send

Usage: atmux send --to <name|session> [--reply-required] [--interrupt] "message"

Description: Send XML messages to a single agent or every agent in a team. Resolution order for --to: 1) Team session/name 2) Agent session/name --interrupt Submit using the adapter's interrupt key (processed after current tool) instead of the default queue key (processed when idle).

Examples: atmux send --to planner "run tests" atmux send --to platform --reply-required "status check-in" atmux send --to worker --interrupt "stop and check this"

message

Usage: atmux message read [--repo ] atmux message list [--unread]

Description: Read or list filesystem-backed messages. Messages are stored at: ~/.atmux/messages///

schedule

Usage: atmux schedule (--interval | --once ) [--no-detach] --notification atmux schedule (--interval | --once ) [--no-detach] -- [args...]

Description: Schedule a future or repeating action. Use --notification to queue an ATMUX notification to the current session, or use -- <command...> to run any command after the delay.

Notification mode: - Always targets the current agent/session. - Use this for self reminders, ticks, and status checks.

Command mode: - Runs the provided command in the current environment. - Only schedule atmux send when the target is another agent or team: atmux schedule --once 10m -- atmux send --to worker "status check" - Never schedule atmux send --to <self>; use --notification instead.

--no-detach Run in the foreground (blocking). By default, the scheduled task runs in a detached tmux window and the command returns immediately.

Durations: Supports integer values with optional unit suffix: ms milliseconds s seconds m minutes h hours d days If no suffix is provided, seconds are assumed.

Examples: atmux schedule --interval 30m --notification "check on long-running jobs" atmux schedule --once 45s --notification "tick" atmux schedule --once 45s -- atmux send --to atmux-myrepo-worker "follow up"

assign

Usage: atmux assign --to <agent|session> --title <title> [--description ] [--given ] [--when ] [--then ] [--todo ]... [--repo ] atmux assign --issue --to <agent|session> [--repo ]

Description: Assign work using filesystem issues.

  • Without --issue: creates a new issue, then assigns it.
  • With --issue: assigns an existing issue id.

comment

Usage: atmux comment "message" --issue [--repo ] atmux comment "message" --pr [--repo ]

Description: Add a comment to a filesystem issue or pull request. Notifies watchers, assignee, and assigner.

capture

Usage: atmux capture --agent <name|session> [--lines ] atmux capture --team <name|session> [--lines ] atmux capture --all [--lines ]

Description: Capture tmux pane output for agents or team sessions.

Examples: atmux capture --agent planner atmux capture --agent atmux-myrepo-planner --lines 300 atmux capture --team platform atmux capture --team atmux-myrepo-team-platform --lines 500 atmux capture --all --lines 200

kill

Usage: atmux kill --pid [--timeout ] [--signal ] atmux kill --watcher [--timeout ] atmux kill --agent <name|pattern> [name|pattern...] atmux kill --all [--yes]

Description: --pid Stop an atmux exec-tracked child process for this repo, wait for executor notifications (including watcher fan-out) to finish, then remove metadata under ~/.atmux/exec///. --watcher Remove a watcher registration by id. Supports watcher ids emitted by atmux watch --pr and atmux watch --issues. --agent Kill agent sessions and clean up their worktrees and branches. Accepts agent names, session names, or glob patterns. --all Kill every atmux session, worktree, and branch for this repo. Prompts for y/N confirmation; use --yes to skip. Refuses to run from inside an atmux session.

Examples: atmux kill --pid 12345 atmux kill --pid 12345 --timeout 30 --signal TERM atmux kill --watcher pr:owner_repo_pr_123:atmux-myrepo-worker-_12 atmux kill --watcher issues:owner_repo_issues:atmux-myrepo-worker-_12 atmux kill --agent worker atmux kill --agent 'agent-*' atmux kill --agent worker planner atmux kill --all atmux kill --all --yes

exec

Usage: atmux exec [--detach] [--] [args...]

Description: Execute a command with passthrough stdio and unchanged exit behavior. After the command exits or is interrupted, send an ATMUX notification back to the current agent pane with the exit code.

--detach Run the command in a new tmux window. Returns immediately. The process pane is stored so watchers can capture its output. Notification is sent to the agent pane when the process exits.

Examples: atmux exec sleep 30 atmux exec -- make test atmux exec --detach -- make test

watch

Usage: atmux watch --target --text [--scope pane|window|session] [--timeout ] [--interval ] [--lines ] atmux watch --pid [--timeout ] [--interval ] atmux watch --pid --stdio [--duration ] [--timeout ] [--interval ] [--lines ] atmux watch --path [--timeout ] [--interval ] atmux watch --issue [--repo ] [--timeout ] [--interval ] atmux watch --issues <repo|url> [--timeout ] [--interval ] atmux watch --pr <id|atmux-uri|github-url> [--repo ] [--timeout ] [--interval ] atmux watch --pull-request [--repo ] [--timeout ] [--interval ] atmux watch --agent <name|session> [--idle ] [--timeout ] [--interval ] [--lines ]

Description: Pane mode: poll tmux output until text appears, non-zero on timeout. PID mode: wait for an atmux exec process (see ~/.atmux/exec///) and receive the same exit notification XML as the executor when it finishes. Stdio mode: monitor a detached exec process pane for output changes. Sends a notification each time new output is detected. Exits when --duration expires, --timeout (no new output) expires, or the process exits. Path mode: watch filesystem paths matching a glob and exit when the matched set or file metadata changes. Issue mode: wait for the next filesystem issue update and receive the same notification XML as issue assign/claim fan-out. Issues mode: keep watching a GitHub repository for newly created issues and queue notifications to the current pane until the watcher is stopped. PR mode: with a GitHub URL, keep watching a remote pull request discussion; otherwise wait for the next filesystem pull request update. --pull-request is kept as a compatibility alias for local filesystem pull requests. Agent mode: wait until an agent's pane output has been stable for --idle seconds (default 30). Exits 0 when idle, 124 on timeout.

Implementations: bin/(atmux)/[watch]/text, [watch]/pid, [watch]/stdio, [watch]/path, [watch]/issue, [watch]/issues, [watch]/pull-request, [watch]/pr, [watch]/agent.

env

Usage: atmux env atmux env get

Description: Inspect ATMUX_* environment variables in the current process.

Examples: atmux env atmux env get repo atmux env get ATMUX_WORKTREE