Skip to content

investigate: OpenCode native scheduled tasks — creation, route choice, independence from Muse tokens #2019

Open

Description

@dezren39

LIST 4a. How are scheduled tasks created and managed inside OpenCode? Do they run fully independently (no Muse tokens spent)? Can the route be chosen per task (summit/specialist instead of workhorse)? What does Muse's management surface look like — creating schedules, checking other OpenCode sessions aren't crashing, adjusting routes? Deliverable: capability report with a worked example schedule created and observed.

Program: Drew's 2026-10-28 directive (full text: hatch-personal memory/topics/id-program-2026-10-28.md).
Working pattern: parallel investigations, then the named synthesis issue merges them into a full design. Route guidance: Workhorse by default; Specialist/Summit for synthesis and ramification-heavy work. A result that says "done" is not the endpoint — the orchestrator reviews it and may commission another round. Deliverables: a markdown design/investigation doc (mermaid/SVG diagrams welcome) linked from this issue, plus follow-up issues for anything buildable. Build a proof of concept where the design calls for one, but do NOT build the permanent feature on top of an unreviewed PoC.

Activity

  1. developing-today commented on Oct 29, 2026

    @developing-today
    Contributor
  2. dezren39 commented on Oct 29, 2026

    @dezren39
    MemberAuthor

    Parent epic: #2055 — fleet expansion & placement program (2026-10-28 directive).

  3. added
    priority/highImportant and time-sensitive
    queue/queuedHas a queued task in the Supabase agent queue
    on Oct 29, 2026
  4. dezren39 commented on Oct 29, 2026

    @dezren39
    MemberAuthor

    Top priority — ID program wave-1. Drew directed this be picked up in the next runs (2026-10-29): enqueued directly as triage task 3338 in repo-health-code-pilot at queue priority 20 (only breakage-class work at priority 10 outranks it). Wave-1 is the ungated investigations and designs; syntheses and PoCs stay gated on their named inputs. Investigation route: Workhorse.

  5. added
    work/assignedQueue worker lifecycle state
    queue/claimedQueue worker lifecycle state
    and removed
    queue/queuedHas a queued task in the Supabase agent queue
    on Oct 29, 2026
  6. dezren39 commented on Oct 29, 2026

    @dezren39
    MemberAuthor

    🤖 Agent note · picked up

    • Agent: queue worker (repo-worker-code), Lane D shift
    • Session / ID: queue task 3338 (repo-health-code-pilot), claimed 2026-10-29T10:13Z
    • Found via: queue claim
    • Task: Triage/investigation for investigate: OpenCode native scheduled tasks — creation, route choice, independence from Muse tokens #2019 — OpenCode native scheduled tasks: creation/management, independence from Muse tokens, per-task route choice, and Muse's management surface; record capability report on the issue and route follow-on work.
    • Expectation: effort class m — done = investigation result recorded on this issue (comment/doc) + follow-on work routed in the same pass, gated syntheses left gated.
    • Links: queue task 3338
  7. dezren39 commented on Oct 29, 2026

    @dezren39
    MemberAuthor

    Investigation result — OpenCode native scheduled tasks (LIST 4a)

    Worker: queue task 3338 (repo-health-code-pilot), Lane D, 2026-10-29. Method: local CLI/source checks on the fleet fork (v2.0.30) on sandbox + laptop, upstream docs/issues, ecosystem review, and a live worked example (below).

    Verdict in one paragraph

    OpenCode has no native scheduler today — not upstream, not in the fleet fork. What exists is a proven composition: an OS scheduler (systemd timer / launchd / cron) firing opencode run with a per-job --model route. That composition runs with zero Muse tokens in both trigger and execution, supports per-task route choice (workhorse / specialist / summit are just the job's --model value), and gives Muse a file-based management surface. Scheduling is not supervision: no mechanism watches for stalls — that remains the babysitter's job (see #2021).

    1. Is there a native scheduler? No.

    • Fleet fork CLI (v2.0.30, verified on laptop + sandbox 2026-10-29): subcommands are upgrade, acp, api, debug, auth, mcp, plugin, models, stats, mini, run, session, msg, service, reload, pair, serve — no schedule/cron. A grep of the fork's packages finds no scheduler subsystem (hits are unrelated UI/timeline uses of the word).
    • Upstream: feature request [FEATURE]: /schedule — run recurring background tasks (cron-like routines) anomalyco/opencode#41906 ("[FEATURE]: /schedule — run recurring background tasks") is OPEN. A community prototype (SQLite-backed automations; once/interval/5-field cron; CLI create/list/show/run/pause/resume/history/remove; restart recovery) was described there on 2026-09-08 but has not merged. Do not plan on it.

    2. The three real mechanisms today

    • (a) OS scheduler + opencode run — the de-facto pattern, recommended. The ecosystem plugin different-ai/opencode-scheduler (listed on opencode.ai's ecosystem page) wraps exactly this: natural language → 5-field cron; job JSON persisted under ~/.config/opencode/scheduler/scopes/<workdir-hash>/jobs/; generates a systemd .timer (Linux) / launchd plist (macOS) / schtasks / crontab entry; a supervisor wrapper enforces no-overlap (lock file), non-interactive permissions (OPENCODE_PERMISSION), and optional hard timeout. Management tools: schedule_job, list_jobs, get_job, job_logs, run_job. Fleet caveat: it is a v1 plugin (@opencode-ai/plugin); the fleet's v2 fork cannot run v1 plugins (the deployed config's plugin array is emptied for exactly this reason), so adopting it means a port — the underlying OS-timer pattern needs no plugin at all.
    • (b) GitHub Actions schedule: event with the official anomalyco/opencode/github action: cron in the workflow file, model: chosen per workflow, output to logs/PRs. Fits repo-scoped periodic chores; does not reach laptop sessions or local state.
    • (c) Third-party daemons (e.g. an opencode-cron CLI with a launchd ticker; MCP cron servers): they exist, are unvetted, and are not recommended as a fleet foundation without a review round.

    3. Independence from Muse tokens — YES for execution

    A scheduled OpenCode run spends only the provider plan its route resolves to. Verified live in the worked example: the run resolved opencode-route/workhorse → opencode-go DeepSeek V4.1 Flash; no Muse process or token was involved between timer creation and completion. Note the inversion in today's fleet: execution already spends plan quotas, but the triggers and supervision are Muse cron jobs (dispatcher, babysitter) spending Muse tokens. OS-level scheduling is precisely the piece that moves the trigger off Muse.

    4. Per-task route choice — YES

    Route is a property of the job definition, not the scheduler: each unit carries its own opencode run --model opencode-route/<workhorse|specialist|summit|speed> (fleet route ids from opencode.jsonc; effort variants via #low/#high/#max). Changing one job's route = editing one unit. The GitHub Actions path takes model: per workflow the same way. This matches Drew's route guidance directly: scheduled tasks run on a single route pool chosen per task.

    5. Muse's management surface

    • Create / adjust / retire: write or remove systemd user units (or job JSON where a wrapper is used). Units are files — diffable and committable, unlike opaque in-app state.
    • Health / crash visibility: systemctl --user list-timers / status, per-job run logs; for live sessions, the OpenCode server API (/api/*) and OpenChamber session views — the surfaces the dispatcher/babysitter already use. Caveat found during the worked example: opencode session list did not surface the just-run session on its first page (paginated/unordered in practice) — directory-scoped server-API reads are the reliable surface, not the CLI list.
    • What no scheduler provides: stall detection, answering a stuck session's questions, escalation. A timer fires and forgets. The babysitter function still needs an owner — a scheduled OpenCode preliminary babysitter (the design: scheduled OpenCode preliminary babysitter — sweep sessions, fix easy stalls, escalate the rest #2021 design) or Muse at reduced cadence.

    6. Worked example — created and observed 2026-10-29

    On the laptop (amd), a one-shot systemd user timer:

    • Created 10:19:03Z: systemd-run --user --unit=oc-sched-example-3338 --on-active=60s --collect ~/tmp/oc-sched-3338/run.sh
    • Fired 10:20:03Z; the service ran opencode run --auto --title oc-sched-example-3338 --model opencode-route/workhorse "Create a file named SCHEDULED-RUN.md …" in ~/tmp/oc-sched-3338
    • Log: route resolved to deepseek-v4.1-flash (build agent), file created with the exact requested two lines, exit 0 at 10:20:14Z (~10 s of execution)
    • Artifacts retained on the laptop: ~/tmp/oc-sched-3338/{run.sh, run.log, SCHEDULED-RUN.md}; transient units auto-collected.

    This is a proof of the pattern, not a permanent feature — no fleet job was migrated onto it by this investigation.

    7. Fit guidance (feeds #2018 and the #2024 placement synthesis)

    8. Follow-on routing

    Implementation follow-on filed as a separate issue (linked below when posted): implement: fleet OpenCode scheduled-task pattern — systemd timer units + opencode run with per-job route, a small job registry, and a log surface — adopting the v1 plugin (after a v2 port) and waiting on upstream #41906 are recorded there as considered-and-deferred alternatives. The placement synthesis #2024 stays gated on its named inputs; this report is one of them.

    — Sources: fork CLI --help output (laptop + sandbox, 2026-10-29); upstream issue anomalyco/opencode#41906 (state OPEN, read 2026-10-29); opencode.ai/docs/github (schedule event) and /docs/ecosystem (opencode-scheduler listing); different-ai/opencode-scheduler docs via DeepWiki; fleet quota picture from the dispatcher log (2026-10-29 ~05:20 CDT: Workhorse OPEN via opencode-go).

  8. dezren39 commented on Oct 29, 2026

    @dezren39
    MemberAuthor

    🤖 Agent note · done

  9. 3 remaining items

  10. added
    source/creatorFiled by the new-issue-creator job
    task/triageQueue packet kind: verify, reproduce, and route this item
    on Nov 3, 2026
  11. developing-today commented on Nov 3, 2026

    @developing-today
    Contributor

    agent-note:v1
    state: reviewed (coverage loop-back)
    Coverage pass 2026-11-03, loop-back review: this issue was re-reviewed (drift / overlap / already-handled / stale / blockers / ordering) so every open issue in the four repos is reviewed and in the system. Verdict: still live; in the system as task 7263 (triage, queued, priority 50) in repo-health-code-pilot. Labels audited and synced. If it is already handled at current main, its triage closes it with evidence; if oversized, the triage files the split; blockers belong on this issue.
    Found via: coverage loop-back 2026-11-03

  12. added
    work/assignedQueue worker lifecycle state
    queue/claimedQueue worker lifecycle state
    and removed
    queue/queuedHas a queued task in the Supabase agent queue
    on Nov 3, 2026
  13. dezren39 commented on Nov 3, 2026

    @dezren39
    MemberAuthor

    🤖 Agent note · picked up

  14. dezren39 commented on Nov 3, 2026

    @dezren39
    MemberAuthor

    🤖 Agent note · done (triage)

    • Agent: queue worker (repo-worker-code), Lane P shift (lane code-p)
    • Session / ID: queue task 7263 (repo-health-code-pilot)

    Triage verdict — #2019 at current main (verified fresh 2026-11-03T23:09Z)

    State verified: issue #2019 is OPEN. No hard-stop labels (held, user/owned, do-not-merge, do-not-auto-edit all absent).

    The investigation this issue asks for is already delivered. Queue task 3338 (Lane D, 2026-10-29) posted the full capability report on this issue and observed a live worked example. All four LIST 4a questions are answered there:

    1. Creation/management: OpenCode (upstream + fleet fork v2.0.30) has no native scheduler — upstream request [FEATURE]: /schedule — run recurring background tasks (cron-like routines) anomalyco/opencode#41906 is still the open tracker. The proven pattern is an OS scheduler (systemd timer / launchd / cron) firing opencode run.
    2. Independence from Muse tokens: YES for execution — the worked example (laptop systemd user timer, fired 2026-10-29T10:20:03Z, exit 0) resolved opencode-route/workhorse → DeepSeek V4.1 Flash with no Muse process or token in the loop.
    3. Per-task route choice: YES — route is a property of the job definition (--model opencode-route/<workhorse|specialist|summit|speed> per unit/workflow).
    4. Muse's management surface: file-based — systemd user units / job JSON, systemctl --user + per-job logs, OpenCode server API / OpenChamber session views for live sessions. Scheduling is not supervision; stall detection stays with the babysitter function (design: scheduled OpenCode preliminary babysitter — sweep sessions, fix easy stalls, escalate the rest #2021).

    Correction already on record (Drew, 2026-10-31): the "no native scheduler" verdict covers OpenCode only — OpenChamber does have native scheduled tasks, and #3026 uses them as its mechanism, with this investigation's systemd pattern as fallback.

    Blockers / gates named: none blocking the investigation itself. The remaining consumers are gated by design: the placement synthesis #2024 is gated on its named inputs (this report is one of them), under epic #2055.

    Fix path already enqueued (no new task needed from this triage):

    Disposition: triage complete. This issue stays open as the investigation record feeding synthesis #2024 / epic #2055; its buildable follow-ons are already filed and queued as #2232 and #2174, so no duplicate issue or task is created here.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

Labels

priority/highImportant and time-sensitivesource/creatorFiled by the new-issue-creator jobtask/triageQueue packet kind: verify, reproduce, and route this item

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions