Phase 003: remove the coding-agent and ekko-agent runtimes

Every chat session now runs through the Hermes bridge, so the three chat
chains become feature-equivalent instead of three partially-maintained
dispatch paths. Keeping the coding-agent and in-house agent runtimes alive
meant every bridge change had to be mirrored into two more runtimes that
had already drifted.

Historical rows are read, not migrated: sessions stored with the retired
source normalize to cli on load, workflow graphs naming the retired agents
keep loading and run on the bridge, and the visible-source check plus
SOURCE_LABELS still recognize the old value so those sessions stay listed.

The public surface follows the code: the OpenAPI generator and the MCP
chat-run tool schema drop the six retired entry fields so external callers
are not told about runtimes that no longer exist.

harness-check gains a RETIRED_RUNTIME scan so the residual check is a
mechanical gate instead of a manual grep, with the two surviving read-side
compat sites recorded with reasons.

Refs: docs/phases/phase_003.md
This commit is contained in:
2026-10-16 13:27:50 +08:00
parent c93e1fe1bd
commit 8c1ddf415f
123 changed files with 567 additions and 23599 deletions
@@ -149,25 +149,6 @@ describe('branch session command', () => {
}))
})
it('rejects /fork for coding agent sessions', async () => {
const { handleSessionCommand, parseSessionCommand } = await import('../../packages/server/src/services/hermes/run-chat/session-command')
const { nsp, socket, namespaceEmit } = makeSocketHarness()
const sessionMap = new Map<string, any>([
['session-1', { messages: [], isWorking: false, events: [], queue: [] }],
])
getSessionMock.mockReturnValue(makeParentSession({ source: 'coding_agent', agent: 'codex' }))
await handleSessionCommand('session-1', parseSessionCommand('/fork side path')!, makeCtx(sessionMap, nsp, socket))
expect(createBranchedSessionMock).not.toHaveBeenCalled()
expect(namespaceEmit).toHaveBeenCalledWith('session.command', expect.objectContaining({
action: 'branch',
ok: false,
terminal: true,
message: expect.stringContaining('Cannot branch coding agent sessions'),
}))
})
it('rejects /fork when there are no visible conversation messages', async () => {
const { handleSessionCommand, parseSessionCommand } = await import('../../packages/server/src/services/hermes/run-chat/session-command')
const { nsp, socket, namespaceEmit } = makeSocketHarness()