diff --git a/docs/subagents/INDEX.md b/docs/subagents/INDEX.md index 7091b8a..fe6e30b 100644 --- a/docs/subagents/INDEX.md +++ b/docs/subagents/INDEX.md @@ -6,7 +6,7 @@ Read first. Keep concise. | ------------ | -------------- | ---------------------------------------------------- | --------- | ------------------------------------- | ---------------------- | | `codex-generate-minecard-image-20260220T112900Z-vsxr` | `codex-generate-minecard-image` | `Generate media fallbacks (GIF) from assets/minecard.webm and wire README/docs fallback markup` | `done` | `docs/subagents/agents/codex-generate-minecard-image-20260220T112900Z-vsxr.md` | `2026-02-20T11:35:30Z` | | `codex-main` | `planner-exec` | `Fix frequency/N+1 regression in plugin --start flow` | `in_progress` | `docs/subagents/agents/codex-main.md` | `2026-02-19T19:36:46Z` | -| `codex-task85-20260219T233711Z-46hc` | `codex-task85` | `Resume TASK-85 maintainability refactor from latest handoff point` | `in_progress` | `docs/subagents/agents/codex-task85-20260219T233711Z-46hc.md` | `2026-02-20T11:14:14Z` | +| `codex-task85-20260219T233711Z-46hc` | `codex-task85` | `Resume TASK-85 maintainability refactor from latest handoff point` | `in_progress` | `docs/subagents/agents/codex-task85-20260219T233711Z-46hc.md` | `2026-02-20T11:15:54Z` | | `codex-config-validation-20260219T172015Z-iiyf` | `codex-config-validation` | `Find root cause of config validation error for ~/.config/SubMiner/config.jsonc` | `completed` | `docs/subagents/agents/codex-config-validation-20260219T172015Z-iiyf.md` | `2026-02-19T17:26:17Z` | | `codex-task85-20260219T233711Z-46hc` | `codex-task85` | `Resume TASK-85 maintainability refactor from latest handoff point` | `in_progress` | `docs/subagents/agents/codex-task85-20260219T233711Z-46hc.md` | `2026-02-20T02:56:34Z` | | `codex-anilist-deeplink-20260219T233926Z` | `anilist-deeplink` | `Fix external subminer:// AniList callback handling from browser` | `done` | `docs/subagents/agents/codex-anilist-deeplink-20260219T233926Z.md` | `2026-02-19T23:59:21Z` | diff --git a/docs/subagents/agents/codex-task85-20260219T233711Z-46hc.md b/docs/subagents/agents/codex-task85-20260219T233711Z-46hc.md index 87af7aa..6a03979 100644 --- a/docs/subagents/agents/codex-task85-20260219T233711Z-46hc.md +++ b/docs/subagents/agents/codex-task85-20260219T233711Z-46hc.md @@ -9,6 +9,10 @@ ## Current Work (newest first) +- [2026-02-20T11:15:54Z] progress: extracted CLI command composition from `src/main.ts` into `src/main/runtime/cli-command-runtime-handler.ts`; `main.ts` now creates `handleCliCommand` via one runtime factory (precheck + context + runtime dispatch wiring). +- [2026-02-20T11:15:54Z] progress: added `src/main/runtime/cli-command-runtime-handler.test.ts` to lock composed behavior around texthooker precheck, context creation, and `'initial'` source forwarding. +- [2026-02-20T11:15:54Z] test: `bun run build` pass (expected macOS helper Swift cache fallback) + focused suites pass for `cli-command-runtime-handler*`, `cli-command-prechecks*`, `cli-command-context-factory*`, `initial-args-runtime-handler*`, and `startup-runtime-handlers*` (7/7). +- [2026-02-20T11:15:54Z] scope: staging `src/main.ts`, new cli-command runtime handler module/test, and subagent bookkeeping only. - [2026-02-20T11:14:14Z] progress: extracted startup/app-lifecycle composition from `src/main.ts` into `src/main/runtime/startup-runtime-handlers.ts`; rewired `main.ts` to inject `createAppLifecycleRuntimeRunner` + `createStartupBootstrapRuntimeDeps` into `createStartupRuntimeHandlers(...)`. - [2026-02-20T11:14:14Z] progress: extracted initial-args composition from `src/main.ts` into `src/main/runtime/initial-args-runtime-handler.ts`; `main.ts` now constructs `handleInitialArgsRuntimeHandler` with one runtime factory call. - [2026-02-20T11:14:14Z] progress: added parity tests `src/main/runtime/startup-runtime-handlers.test.ts` and `src/main/runtime/initial-args-runtime-handler.test.ts` (fixing previous `node:sqlite` test-import leak by removing direct runtime imports from startup handler module). diff --git a/src/main.ts b/src/main.ts index 2fe52e1..26833ca 100644 --- a/src/main.ts +++ b/src/main.ts @@ -243,9 +243,8 @@ import { createBuildStartJellyfinRemoteSessionMainDepsHandler, createBuildStopJellyfinRemoteSessionMainDepsHandler, } from './main/runtime/jellyfin-remote-session-main-deps'; +import { createCliCommandRuntimeHandler } from './main/runtime/cli-command-runtime-handler'; import { createInitialArgsRuntimeHandler } from './main/runtime/initial-args-runtime-handler'; -import { createHandleTexthookerOnlyModeTransitionHandler } from './main/runtime/cli-command-prechecks'; -import { createBuildHandleTexthookerOnlyModeTransitionMainDepsHandler } from './main/runtime/cli-command-prechecks-main-deps'; import { createGetFieldGroupingResolverHandler, createSetFieldGroupingResolverHandler, @@ -2190,8 +2189,8 @@ runAndApplyStartupState(); void refreshAnilistClientSecretState({ force: true }); anilistStateRuntime.refreshRetryQueueState(); -const handleTexthookerOnlyModeTransitionHandler = createHandleTexthookerOnlyModeTransitionHandler( - createBuildHandleTexthookerOnlyModeTransitionMainDepsHandler({ +const handleCliCommand = createCliCommandRuntimeHandler({ + handleTexthookerOnlyModeTransitionMainDeps: { isTexthookerOnlyMode: () => appState.texthookerOnlyMode, setTexthookerOnlyMode: (enabled) => { appState.texthookerOnlyMode = enabled; @@ -2199,15 +2198,11 @@ const handleTexthookerOnlyModeTransitionHandler = createHandleTexthookerOnlyMode commandNeedsOverlayRuntime: (inputArgs) => commandNeedsOverlayRuntime(inputArgs), startBackgroundWarmups: () => startBackgroundWarmups(), logInfo: (message: string) => logger.info(message), - })(), -); - -function handleCliCommand(args: CliArgs, source: CliCommandSource = 'initial'): void { - handleTexthookerOnlyModeTransitionHandler(args); - - const cliContext = createCliCommandContextHandler(); - handleCliCommandRuntimeServiceWithContext(args, source, cliContext); -} + }, + createCliCommandContext: () => createCliCommandContextHandler(), + handleCliCommandRuntimeServiceWithContext: (args, source, cliContext) => + handleCliCommandRuntimeServiceWithContext(args, source, cliContext), +}); const handleInitialArgsRuntimeHandler = createInitialArgsRuntimeHandler({ getInitialArgs: () => appState.initialArgs, diff --git a/src/main/runtime/cli-command-runtime-handler.test.ts b/src/main/runtime/cli-command-runtime-handler.test.ts new file mode 100644 index 0000000..45ae393 --- /dev/null +++ b/src/main/runtime/cli-command-runtime-handler.test.ts @@ -0,0 +1,33 @@ +import assert from 'node:assert/strict'; +import test from 'node:test'; +import { createCliCommandRuntimeHandler } from './cli-command-runtime-handler'; + +test('cli command runtime handler applies precheck and forwards command with context', () => { + const calls: string[] = []; + const handler = createCliCommandRuntimeHandler({ + handleTexthookerOnlyModeTransitionMainDeps: { + isTexthookerOnlyMode: () => true, + setTexthookerOnlyMode: () => calls.push('set-mode'), + commandNeedsOverlayRuntime: () => true, + startBackgroundWarmups: () => calls.push('warmups'), + logInfo: (message) => calls.push(`log:${message}`), + }, + createCliCommandContext: () => { + calls.push('context'); + return { id: 'ctx' }; + }, + handleCliCommandRuntimeServiceWithContext: (_args, source, context) => { + calls.push(`cli:${source}:${context.id}`); + }, + }); + + handler({ start: true } as never); + + assert.deepEqual(calls, [ + 'set-mode', + 'log:Disabling texthooker-only mode after overlay/start command.', + 'warmups', + 'context', + 'cli:initial:ctx', + ]); +}); diff --git a/src/main/runtime/cli-command-runtime-handler.ts b/src/main/runtime/cli-command-runtime-handler.ts new file mode 100644 index 0000000..1faeb15 --- /dev/null +++ b/src/main/runtime/cli-command-runtime-handler.ts @@ -0,0 +1,30 @@ +import type { CliArgs, CliCommandSource } from '../../cli/args'; +import { createHandleTexthookerOnlyModeTransitionHandler } from './cli-command-prechecks'; +import { createBuildHandleTexthookerOnlyModeTransitionMainDepsHandler } from './cli-command-prechecks-main-deps'; + +type HandleTexthookerOnlyModeTransitionMainDeps = Parameters< + typeof createBuildHandleTexthookerOnlyModeTransitionMainDepsHandler +>[0]; + +export function createCliCommandRuntimeHandler(deps: { + handleTexthookerOnlyModeTransitionMainDeps: HandleTexthookerOnlyModeTransitionMainDeps; + createCliCommandContext: () => TCliContext; + handleCliCommandRuntimeServiceWithContext: ( + args: CliArgs, + source: CliCommandSource, + cliContext: TCliContext, + ) => void; +}) { + const handleTexthookerOnlyModeTransitionHandler = + createHandleTexthookerOnlyModeTransitionHandler( + createBuildHandleTexthookerOnlyModeTransitionMainDepsHandler( + deps.handleTexthookerOnlyModeTransitionMainDeps, + )(), + ); + + return (args: CliArgs, source: CliCommandSource = 'initial'): void => { + handleTexthookerOnlyModeTransitionHandler(args); + const cliContext = deps.createCliCommandContext(); + deps.handleCliCommandRuntimeServiceWithContext(args, source, cliContext); + }; +}