Remove what the connector's worker side left behind
Stacked on #821, which reworded the comments around this code and listed it as dead.
Why
#815 removed the connector's worker side, but left the code that worker side used. No command reaches it:
Ledger.Redispatchand its helpers (RedispatchResult,LiveWorker,authorizeBlocked,AuthorizedBlocked).- The ledger's whole write side for tasks and attempts:
LaunchTask,EndAttempt,CreateTask,SupersedeTask,DispatchwithTaskDispatch(the worker'sget_dispatch,ack_dispatchandcomplete_dispatch),MarkRunning,RecordTaker,ExposeEvent,JoinConversation,StartableRecords, adoption, refusals and still-running. - The outbox's readers and resolver (
Intents,Intent,ResolveIntent,IsLifecycleReceipt). The outbox table is now written only by its migrations and triggers. - The ledger's
Hooks. Only the removed dispatcher set them, so every call site ran a nil check and nothing more. OpenExistingLedgerandResolveStateDir(the worker's MCP server),Held(the outbox sender),UnfinishedFromOthers(dangerous mode).setup.TryLockandsetup.Duration.- Almost all of
internal/connector/driver:StartWorker, the preflight probe, the redactor, the environment builder,TerminateRecorded,ConfirmGroupGoneand the process-group signals.
make deadcode finds the driver package, TryLock and Duration. It does not find the ledger methods: *Ledger reaches reflect, so deadcode keeps every exported method alive (-whylive says "reachable only through reflection"). I found those with a reference walk that ignores reflection, and confirmed each one with grep.
What
Removed, with the tests that only tested them: about 8,900 lines out, 1,100 in, across 56 files.
internal/connector/driver is now internal/connector/procid. The package kept only the process-identity code: Process, OwnsWorker, LookupProcess, ErrGroupOutlivedLeader and ErrIdentityUnknown, with the per-platform start-time readers. "driver" named an agent boundary that no longer exists, so a small package named for what it does is easier to read. OwnsWorker sends only the zero signal now; the signals that ended process groups went with TerminateRecorded.
Simplified where a removal left a branch with no caller:
openLedgerloses its non-owner branch, becauseOpenExistingLedgerwas the only non-owner caller.operatorEdgeskeeps only the edges a discard and an import take (into discarded). The edges out of completed and held belonged to redispatch.eventTask, which a discard and an import read, keeps only the outcome and when it settled.setup.Lockinlines its helper, becauseTryLockwas the only other caller.InstructionReplyis nowHandoffReply, besideHandoffLine, which is the only thing that uses it. The JSON is the same.
Comments. The dispatch lifecycle in ledger_dispatch.go, the tasks header in ledger_tasks.go, the outbox invariants and the hold invariants now say what this build does and what an older build's ledger can hold. They no longer describe functions that are gone.
Also fixed: internal/commands tests did not compile for Windows (a pre-existing problem since #811). Two tests in connect_start_wait_test.go use Unix-only fixtures. They move to connect_start_wait_unix_test.go, so GOOS=windows go vet ./... is clean.
No behavior change.
What stays and why
- The schema, every migration, table, trigger and index, unchanged. Older ledgers hold tasks, attempts, task events, outbox intents and waiting redispatches, and the triggers still guard every write to those rows.
- Status and doctor reporting of worker-era state: tasks with their worker and token taker (through
procid.OwnsWorker), dispatches, intents,authorized_blockedandredispatch_pending.--jsonoutput is unchanged. discard,import,shadow promoteand the hold, including how they withdraw a redispatch an older build left waiting, and how they cancel a pending guard acknowledgement or holding reply.move's guard on records a worker was handed (ErrHeldByWorker) and the lifecycle's edges into dispatched, because older ledgers hold dispatched records.- The
IntentKind,IntentState,MessageKindandOutcomevocabularies, because status reads intents and outcomes through them.AttemptState,StopReasonandDeliveryhad no reader left and are removed. - Non-worker test seams that deadcode still reports (
Queue.Depth,Intake.CheckpointKey,admission.WithClockand others), andDropContent, which no command calls. These were dead before #815 and are not worker code, so this PR leaves them.
Tests
worker_era_test.gois new. It writes the rows the removed dispatcher wrote, with its statements and in its order, so the schema's triggers check them. The tests for status, discard, import, the hold, retention andmovenow build older-ledger state with it instead of calling the removed methods.- The tests that remain check behavior that still exists. For example: a hold, an import and a discard each withdraw a waiting redispatch; retention keeps a waiting redispatch's snapshot; status shows a worker-era task and an unaccounted token holder.
- The unreadable
connect.jsontest now waits for the record's timed retry instead of a redispatch. procidkeeps the identity tests: reused pid, no kernel start time, a group that outlived its leader, and zombie leaders on Linux and macOS.make deadcode, before and after, on all five release platforms. Shipped binary: 157 to 85 unreachable functions (151 to 85 on Windows);internal/connector: 79 to 7 (74 to 8 on Windows). The-tags devbuild drops the same set. The 7 that remain are the non-worker test seams above, andInstanceLock.Path. Windows adds the non-Unixprocid.OwnsWorkerstub: status asks about a recorded worker only on Unix, and the stub keeps the package's API the same on every platform.go vet ./...is clean for linux, darwin, windows, freebsd and openbsd, and with-tags dev.go test -racepasses forinternal/connector/...andinternal/commands.bin/ciis green.
Summary by cubic
Removes the code no command reaches since #815 removed the connector's worker side: the ledger's task and attempt writers, Redispatch and its helpers, the outbox readers and resolver, the never-installed ledger hooks, setup.TryLock and setup.Duration, and most of internal/connector/driver. No behavior change — about 8,900 lines out and 1,100 in, across 56 files.
What stays
- The schema, migrations and triggers are unchanged; ledgers an older build wrote still hold tasks, attempts, outbox intents and waiting redispatches.
- Status, doctor,
discard,import,shadow promoteand the hold still read and clear worker-era rows; the newworker_era_test.gowrites those rows the way the removed dispatcher did, so the schema's triggers check them. - The process-identity code moves into
internal/connector/procid, a package named for what it does. - Two Unix-only start-wait tests move behind a build tag, fixing a pre-existing Windows compile break.