oh-my-opencode 4.2.3 → 4.3.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (171) hide show
  1. package/README.ja.md +1 -0
  2. package/README.ko.md +1 -0
  3. package/README.md +3 -2
  4. package/README.zh-cn.md +1 -0
  5. package/dist/agents/atlas/default-prompt-sections.d.ts +1 -1
  6. package/dist/agents/builtin-agents/available-skills.d.ts +1 -1
  7. package/dist/agents/builtin-agents/model-resolution.d.ts +1 -1
  8. package/dist/agents/prometheus/plan-generation.d.ts +1 -1
  9. package/dist/agents/prometheus/plan-template.d.ts +1 -1
  10. package/dist/agents/prometheus/spec-driven-mode.d.ts +7 -0
  11. package/dist/cli/doctor/checks/system-binary.d.ts +1 -1
  12. package/dist/cli/doctor/checks/tui-plugin-config.d.ts +14 -0
  13. package/dist/cli/doctor/constants.d.ts +1 -0
  14. package/dist/cli/index.js +3168 -2353
  15. package/dist/cli/provider-model-id-transform.d.ts +1 -1
  16. package/dist/config/index.d.ts +1 -1
  17. package/dist/config/schema/agent-overrides.d.ts +147 -1
  18. package/dist/config/schema/background-task.d.ts +1 -0
  19. package/dist/config/schema/default-mode.d.ts +6 -0
  20. package/dist/config/schema/hooks.d.ts +2 -0
  21. package/dist/config/schema/i18n.d.ts +5 -0
  22. package/dist/config/schema/keyword-detector.d.ts +8 -0
  23. package/dist/config/schema/oh-my-opencode-config.d.ts +163 -1
  24. package/dist/config/schema.d.ts +2 -0
  25. package/dist/create-hooks.d.ts +2 -0
  26. package/dist/features/background-agent/fallback-retry-handler.d.ts +3 -0
  27. package/dist/features/background-agent/manager.d.ts +0 -1
  28. package/dist/features/background-agent/parent-wake-notifier.d.ts +4 -0
  29. package/dist/features/background-agent/session-activity.d.ts +12 -0
  30. package/dist/features/background-agent/session-existence.d.ts +2 -0
  31. package/dist/features/background-agent/session-stream-activity.d.ts +18 -0
  32. package/dist/features/background-agent/task-activity-refresh.d.ts +11 -0
  33. package/dist/features/background-agent/task-poller.d.ts +2 -0
  34. package/dist/features/boulder-state/constants.d.ts +1 -10
  35. package/dist/features/boulder-state/format-duration.d.ts +1 -1
  36. package/dist/features/boulder-state/storage.d.ts +1 -83
  37. package/dist/features/boulder-state/top-level-task.d.ts +1 -2
  38. package/dist/features/boulder-state/types.d.ts +1 -100
  39. package/dist/features/task-toast-manager/manager.d.ts +1 -1
  40. package/dist/features/team-mode/team-state-store/locks.d.ts +7 -4
  41. package/dist/features/tmux-subagent/manager.d.ts +2 -0
  42. package/dist/hooks/atlas/system-reminder-templates.d.ts +1 -1
  43. package/dist/hooks/claude-code-hooks/config-loader.d.ts +7 -0
  44. package/dist/hooks/claude-code-hooks/config.d.ts +4 -1
  45. package/dist/hooks/claude-code-hooks/types.d.ts +17 -1
  46. package/dist/hooks/comment-checker/cli.d.ts +2 -22
  47. package/dist/hooks/comment-checker/types.d.ts +1 -31
  48. package/dist/hooks/directory-agents-injector/finder.d.ts +2 -7
  49. package/dist/hooks/directory-agents-injector/injector.d.ts +1 -18
  50. package/dist/hooks/index.d.ts +2 -0
  51. package/dist/hooks/keyword-detector/analyze/default.d.ts +1 -1
  52. package/dist/hooks/keyword-detector/constants.d.ts +10 -5
  53. package/dist/hooks/keyword-detector/detector.d.ts +2 -2
  54. package/dist/hooks/keyword-detector/hook.d.ts +2 -1
  55. package/dist/hooks/keyword-detector/hyperplan/default.d.ts +5 -0
  56. package/dist/hooks/notepad-write-guard/index.d.ts +2 -0
  57. package/dist/hooks/plan-format-validator/hook.d.ts +21 -0
  58. package/dist/hooks/plan-format-validator/index.d.ts +1 -0
  59. package/dist/hooks/prometheus-md-only/constants.d.ts +8 -0
  60. package/dist/hooks/rules-injector/constants.d.ts +1 -7
  61. package/dist/hooks/rules-injector/matcher.d.ts +2 -2
  62. package/dist/hooks/rules-injector/parser.d.ts +2 -2
  63. package/dist/hooks/rules-injector/project-root-finder.d.ts +1 -1
  64. package/dist/hooks/rules-injector/rule-distance.d.ts +1 -1
  65. package/dist/hooks/rules-injector/rule-file-finder.d.ts +2 -2
  66. package/dist/hooks/rules-injector/rule-file-scanner.d.ts +1 -1
  67. package/dist/hooks/rules-injector/rule-scan-cache.d.ts +2 -2
  68. package/dist/hooks/rules-injector/types.d.ts +1 -1
  69. package/dist/hooks/session-todo-status.d.ts +1 -0
  70. package/dist/hooks/sisyphus-junior-notepad/constants.d.ts +1 -1
  71. package/dist/hooks/start-work/context-info-builder.d.ts +1 -0
  72. package/dist/hooks/start-work/session-plan-affinity.d.ts +7 -0
  73. package/dist/hooks/todo-continuation-enforcer/types.d.ts +1 -0
  74. package/dist/index.js +17916 -15893
  75. package/dist/locales/en.d.ts +18 -0
  76. package/dist/locales/index.d.ts +6 -0
  77. package/dist/locales/zh.d.ts +17 -0
  78. package/dist/mcp/ast-grep.d.ts +2 -0
  79. package/dist/mcp/cli-suffix.d.ts +1 -0
  80. package/dist/mcp/index.d.ts +2 -0
  81. package/dist/mcp/lsp.d.ts +2 -0
  82. package/dist/mcp/runtime-executable.d.ts +11 -0
  83. package/dist/oh-my-opencode.schema.json +449 -1
  84. package/dist/plugin/hooks/create-core-hooks.d.ts +2 -0
  85. package/dist/plugin/hooks/create-tool-guard-hooks.d.ts +3 -1
  86. package/dist/plugin/system-transform.d.ts +2 -1
  87. package/dist/plugin/tool-definition.d.ts +9 -0
  88. package/dist/plugin-handlers/agent-key-remapper.d.ts +5 -1
  89. package/dist/plugin-handlers/hook-config-handler.d.ts +7 -0
  90. package/dist/plugin-handlers/index.d.ts +1 -0
  91. package/dist/plugin-handlers/plugin-components-loader.d.ts +2 -3
  92. package/dist/shared/agent-display-names.d.ts +10 -2
  93. package/dist/shared/command-executor/execute-hook-command.d.ts +2 -0
  94. package/dist/shared/contains-path.d.ts +1 -2
  95. package/dist/shared/context-limit-resolver.d.ts +2 -5
  96. package/dist/shared/deep-merge.d.ts +1 -13
  97. package/dist/shared/disabled-providers.d.ts +14 -0
  98. package/dist/shared/extract-semver.d.ts +1 -1
  99. package/dist/shared/fallback-chain-from-models.d.ts +1 -12
  100. package/dist/shared/file-utils.d.ts +1 -7
  101. package/dist/shared/frontmatter.d.ts +1 -7
  102. package/dist/shared/i18n.d.ts +9 -0
  103. package/dist/shared/index.d.ts +0 -1
  104. package/dist/shared/jsonc-parser.d.ts +1 -23
  105. package/dist/shared/model-availability.d.ts +18 -5
  106. package/dist/shared/model-capabilities/index.d.ts +6 -3
  107. package/dist/shared/model-capabilities-cache.d.ts +4 -8
  108. package/dist/shared/model-error-classifier.d.ts +4 -33
  109. package/dist/shared/model-format-normalizer.d.ts +1 -7
  110. package/dist/shared/model-normalization.d.ts +1 -2
  111. package/dist/shared/model-requirements.d.ts +2 -22
  112. package/dist/shared/model-resolution-pipeline.d.ts +5 -30
  113. package/dist/shared/model-resolution-types.d.ts +1 -36
  114. package/dist/shared/model-resolver.d.ts +8 -35
  115. package/dist/shared/model-sanitizer.d.ts +1 -3
  116. package/dist/shared/model-settings-compatibility.d.ts +2 -40
  117. package/dist/shared/model-string-parser.d.ts +1 -9
  118. package/dist/shared/model-suggestion-retry.d.ts +3 -7
  119. package/dist/shared/opencode-config-dir.d.ts +1 -0
  120. package/dist/shared/port-utils.d.ts +1 -9
  121. package/dist/shared/prompt-async-gate/pending-tool-turn.d.ts +9 -0
  122. package/dist/shared/prompt-async-gate/queue.d.ts +8 -0
  123. package/dist/shared/prompt-async-gate/reservations.d.ts +9 -0
  124. package/dist/shared/prompt-async-gate/session-idle-dispatch.d.ts +15 -0
  125. package/dist/shared/prompt-async-gate/timing.d.ts +8 -0
  126. package/dist/shared/prompt-async-gate/types.d.ts +120 -0
  127. package/dist/shared/prompt-async-gate.d.ts +3 -90
  128. package/dist/shared/provider-model-id-transform.d.ts +1 -1
  129. package/dist/shared/record-type-guard.d.ts +1 -1
  130. package/dist/shared/replace-tool-args.d.ts +1 -13
  131. package/dist/shared/session-idle-settle.d.ts +2 -1
  132. package/dist/shared/shell-env.d.ts +7 -5
  133. package/dist/shared/snake-case.d.ts +1 -5
  134. package/dist/shared/tool-name.d.ts +1 -1
  135. package/dist/testing/create-plugin-module.d.ts +2 -0
  136. package/dist/tools/delegate-task/constants.d.ts +19 -0
  137. package/dist/tools/delegate-task/skill-resolver.d.ts +9 -2
  138. package/dist/tools/delegate-task/types.d.ts +32 -0
  139. package/dist/tools/glob/constants.d.ts +1 -1
  140. package/dist/tools/grep/constants.d.ts +1 -1
  141. package/dist/tools/hashline-edit/autocorrect-replacement-lines.d.ts +1 -6
  142. package/dist/tools/hashline-edit/constants.d.ts +1 -4
  143. package/dist/tools/hashline-edit/diff-utils.d.ts +1 -6
  144. package/dist/tools/hashline-edit/edit-deduplication.d.ts +1 -5
  145. package/dist/tools/hashline-edit/edit-operation-primitives.d.ts +1 -10
  146. package/dist/tools/hashline-edit/edit-operations.d.ts +2 -8
  147. package/dist/tools/hashline-edit/edit-ordering.d.ts +1 -4
  148. package/dist/tools/hashline-edit/edit-text-normalization.d.ts +1 -7
  149. package/dist/tools/hashline-edit/file-text-canonicalization.d.ts +2 -7
  150. package/dist/tools/hashline-edit/hash-computation.d.ts +2 -11
  151. package/dist/tools/hashline-edit/hashline-chunk-formatter.d.ts +2 -10
  152. package/dist/tools/hashline-edit/hashline-edit-diff.d.ts +1 -1
  153. package/dist/tools/hashline-edit/normalize-edits.d.ts +2 -10
  154. package/dist/tools/hashline-edit/types.d.ts +1 -17
  155. package/dist/tools/hashline-edit/validation.d.ts +2 -20
  156. package/dist/tools/look-at/assistant-message-extractor.d.ts +7 -0
  157. package/dist/tools/look-at/session-poller.d.ts +9 -1
  158. package/dist/tools/skill/tools.d.ts +1 -1
  159. package/dist/tools/skill/types.d.ts +2 -0
  160. package/package.json +31 -16
  161. package/packages/ast-grep-mcp/dist/cli.js +272 -248
  162. package/dist/hooks/comment-checker/apply-patch-edits.d.ts +0 -2
  163. package/dist/shared/known-variants.d.ts +0 -6
  164. package/dist/shared/model-capabilities/bundled-snapshot.d.ts +0 -2
  165. package/dist/shared/model-capabilities/get-model-capabilities.d.ts +0 -2
  166. package/dist/shared/model-capabilities/runtime-model-readers.d.ts +0 -11
  167. package/dist/shared/model-capabilities/supplemental-entries.d.ts +0 -2
  168. package/dist/shared/model-capabilities/types.d.ts +0 -94
  169. package/dist/shared/model-capability-aliases.d.ts +0 -21
  170. package/dist/shared/model-capability-guardrails.d.ts +0 -38
  171. package/dist/shared/model-capability-heuristics.d.ts +0 -11
@@ -34,6 +34,7 @@ type ParentWakeNotifierOptions = {
34
34
  * inside OpenCode's `@parcel/watcher` TSFN callback path. See issue #4120.
35
35
  */
36
36
  userMessageInProgressWindowMs: number;
37
+ parentSessionActivityInProgressWindowMs?: number;
37
38
  };
38
39
  export declare class ParentWakeNotifier {
39
40
  private readonly deps;
@@ -42,11 +43,13 @@ export declare class ParentWakeNotifier {
42
43
  private pendingParentWakeTimers;
43
44
  private dispatchedParentWakes;
44
45
  private dispatchedParentWakeTimers;
46
+ private recentParentSessionActivity;
45
47
  constructor(deps: ParentWakeNotifierDeps, options: ParentWakeNotifierOptions);
46
48
  getPendingParentWakes(): Map<string, PendingParentWake>;
47
49
  getPendingParentWakeTimers(): Map<string, ReturnType<typeof setTimeout>>;
48
50
  getDispatchedParentWakes(): Map<string, PendingParentWake>;
49
51
  getDispatchedParentWakeTimers(): Map<string, ReturnType<typeof setTimeout>>;
52
+ recordParentSessionActivity(sessionID: string): void;
50
53
  queuePendingParentWake(sessionID: string, notification: string, promptContext: ParentWakePromptContext, shouldReply: boolean, delayMs?: number): void;
51
54
  flushPendingParentWake(sessionID: string): Promise<void>;
52
55
  clearDispatchedParentWake(sessionID: string): void;
@@ -55,6 +58,7 @@ export declare class ParentWakeNotifier {
55
58
  clearPendingParentWakeTimer(sessionID: string): void;
56
59
  shutdown(): void;
57
60
  private isSessionActive;
61
+ private hasRecentParentSessionActivity;
58
62
  private resolveParentWakePromptContext;
59
63
  private cloneParentWake;
60
64
  private trackDispatchedParentWake;
@@ -0,0 +1,12 @@
1
+ import type { OpencodeClient } from "./opencode-client";
2
+ export type SessionActivityLookup = {
3
+ readonly type: "activity";
4
+ readonly activity: Date;
5
+ } | {
6
+ readonly type: "missing";
7
+ } | {
8
+ readonly type: "unavailable";
9
+ };
10
+ export type SessionActivityResolver = (sessionID: string) => Promise<SessionActivityLookup>;
11
+ export declare function extractSessionActivityDate(sessionInfo: unknown): Date | undefined;
12
+ export declare function getSessionActivityFromClient(client: OpencodeClient, sessionID: string, directory?: string): Promise<SessionActivityLookup>;
@@ -1,3 +1,5 @@
1
1
  import type { OpencodeClient } from "./opencode-client";
2
2
  export declare const MIN_SESSION_GONE_POLLS = 3;
3
+ export type SessionExistenceStatus = "exists" | "missing" | "unknown";
4
+ export declare function checkSessionExistence(client: OpencodeClient, sessionID: string, directory?: string): Promise<SessionExistenceStatus>;
3
5
  export declare function verifySessionExists(client: OpencodeClient, sessionID: string, directory?: string): Promise<boolean>;
@@ -0,0 +1,18 @@
1
+ export declare const SESSION_NEXT_EVENT_PREFIX = "session.next.";
2
+ export interface MessagePartInfo {
3
+ readonly id: string | undefined;
4
+ readonly sessionID: string | undefined;
5
+ readonly type: string | undefined;
6
+ readonly tool: string | undefined;
7
+ readonly input: Record<string, unknown> | undefined;
8
+ readonly state: {
9
+ readonly status: string | undefined;
10
+ readonly input: Record<string, unknown> | undefined;
11
+ } | undefined;
12
+ readonly field: string | undefined;
13
+ readonly activityTime: Date | undefined;
14
+ }
15
+ export declare function resolveMessagePartInfo(properties: unknown): MessagePartInfo | undefined;
16
+ export declare function resolveSessionNextPartInfo(eventType: string, properties: unknown): MessagePartInfo | undefined;
17
+ export declare function isMessagePartForSession(partInfo: MessagePartInfo | undefined, sessionID: string): boolean;
18
+ export declare function hasOutputSignalFromPart(partInfo: MessagePartInfo | undefined, sessionID?: string): boolean;
@@ -0,0 +1,11 @@
1
+ import type { SessionActivityResolver } from "./session-activity";
2
+ import type { BackgroundTask } from "./types";
3
+ export type TaskActivityRefreshResult = {
4
+ readonly type: "activity";
5
+ readonly activityTime: number;
6
+ } | {
7
+ readonly type: "missing";
8
+ } | {
9
+ readonly type: "unavailable";
10
+ };
11
+ export declare function refreshTaskActivityFromSession(task: BackgroundTask, getSessionActivity: SessionActivityResolver): Promise<TaskActivityRefreshResult>;
@@ -2,6 +2,7 @@ import type { BackgroundTaskConfig } from "../../config/schema";
2
2
  import type { BackgroundTask } from "./types";
3
3
  import type { ConcurrencyManager } from "./concurrency";
4
4
  import type { OpencodeClient } from "./opencode-client";
5
+ import { type SessionActivityResolver } from "./session-activity";
5
6
  export declare function pruneStaleTasksAndNotifications(args: {
6
7
  tasks: Map<string, BackgroundTask>;
7
8
  notifications: Map<string, BackgroundTask[]>;
@@ -21,4 +22,5 @@ export declare function checkAndInterruptStaleTasks(args: {
21
22
  notifyParentSession: (task: BackgroundTask) => Promise<void>;
22
23
  sessionStatuses?: SessionStatusMap;
23
24
  onTaskInterrupted?: (task: BackgroundTask) => void;
25
+ getSessionActivity?: SessionActivityResolver;
24
26
  }): Promise<void>;
@@ -1,10 +1 @@
1
- /**
2
- * Boulder State Constants
3
- */
4
- export declare const BOULDER_DIR = ".omo";
5
- export declare const BOULDER_FILE = "boulder.json";
6
- export declare const BOULDER_STATE_PATH = ".omo/boulder.json";
7
- export declare const NOTEPAD_DIR = "notepads";
8
- export declare const NOTEPAD_BASE_PATH = ".omo/notepads";
9
- /** Prometheus plan directory pattern */
10
- export declare const PROMETHEUS_PLANS_DIR = ".omo/plans";
1
+ export { BOULDER_DIR, BOULDER_FILE, BOULDER_STATE_PATH, NOTEPAD_BASE_PATH, NOTEPAD_DIR, PROMETHEUS_PLANS_DIR, } from "@oh-my-opencode/boulder-state";
@@ -1 +1 @@
1
- export declare function formatDurationHuman(milliseconds: number): string;
1
+ export { formatDurationHuman } from "@oh-my-opencode/utils";
@@ -1,83 +1 @@
1
- /**
2
- * Boulder State Storage
3
- *
4
- * Handles reading/writing boulder.json for active plan tracking.
5
- */
6
- import type { BoulderSessionOrigin, BoulderState, BoulderWorkResumeOption, BoulderWorkState, PlanProgress, TaskSessionState } from "./types";
7
- export declare function getBoulderFilePath(directory: string): string;
8
- export declare function resolveBoulderPlanPath(directory: string, state: Pick<BoulderState, "active_plan" | "worktree_path">): string;
9
- export declare function readBoulderState(directory: string): BoulderState | null;
10
- export declare function writeBoulderState(directory: string, state: BoulderState): boolean;
11
- export declare function appendSessionId(directory: string, sessionId: string, origin?: "direct" | "appended"): BoulderState | null;
12
- export declare function clearBoulderState(directory: string): boolean;
13
- export declare function getTaskSessionState(directory: string, taskKey: string): TaskSessionState | null;
14
- export declare function upsertTaskSessionState(directory: string, input: {
15
- taskKey: string;
16
- taskLabel: string;
17
- taskTitle: string;
18
- sessionId: string;
19
- agent?: string;
20
- category?: string;
21
- }): BoulderState | null;
22
- /**
23
- * Find Prometheus plan files for this project.
24
- * Prometheus stores plans at: {project}/.omo/plans/{name}.md
25
- */
26
- export declare function findPrometheusPlans(directory: string): string[];
27
- /**
28
- * Parse a plan file and count checkbox progress.
29
- *
30
- * Only top-level (zero-indent) checkboxes under `## TODOs` and
31
- * `## Final Verification Wave` sections are counted. The checkbox
32
- * body must carry a valid task label (`N.` for TODOs, `FN.` for
33
- * Final Verification Wave). Nested acceptance-criteria checkboxes
34
- * and checkboxes in other sections are intentionally ignored so
35
- * that progress tracking stays aligned with `readCurrentTopLevelTask`.
36
- */
37
- export declare function getPlanProgress(planPath: string): PlanProgress;
38
- /**
39
- * Extract plan name from file path.
40
- */
41
- export declare function getPlanName(planPath: string): string;
42
- /**
43
- * Create a new boulder state for a plan.
44
- */
45
- export declare function createBoulderState(planPath: string, sessionId: string, agent?: string, worktreePath?: string): BoulderState;
46
- export declare function generateWorkId(planName: string): string;
47
- export declare function getBoulderWorks(state: BoulderState): BoulderWorkState[];
48
- export declare function getActiveWorks(directory: string): BoulderWorkState[];
49
- export declare function getWorkById(directory: string, workId: string): BoulderWorkState | null;
50
- export declare function getWorkByPlanName(directory: string, planName: string, options?: {
51
- worktreePath?: string;
52
- }): BoulderWorkState | null;
53
- export declare function getWorkForSession(directory: string, sessionId: string): BoulderWorkState | null;
54
- export declare function resolveBoulderPlanPathForWork(directory: string, work: Pick<BoulderWorkState, "active_plan" | "worktree_path">): string;
55
- export declare function getWorkResumeOptions(directory: string): BoulderWorkResumeOption[];
56
- export declare function selectActiveWork(directory: string, workId: string): BoulderState | null;
57
- export declare function addBoulderWork(directory: string, input: {
58
- planPath: string;
59
- sessionId: string;
60
- agent?: string;
61
- worktreePath?: string;
62
- startedAt?: string;
63
- }): BoulderState | null;
64
- export declare function appendSessionIdForWork(directory: string, workId: string, sessionId: string, origin?: BoulderSessionOrigin): BoulderState | null;
65
- export declare function upsertTaskSessionStateForWork(directory: string, workId: string, input: {
66
- taskKey: string;
67
- taskLabel: string;
68
- taskTitle: string;
69
- sessionId: string;
70
- agent?: string;
71
- category?: string;
72
- }): BoulderState | null;
73
- export declare function startTaskTimer(directory: string, workId: string, input: {
74
- taskKey: string;
75
- taskLabel: string;
76
- taskTitle: string;
77
- sessionId: string;
78
- agent?: string;
79
- category?: string;
80
- startedAt?: string;
81
- }): BoulderState | null;
82
- export declare function endTaskTimer(directory: string, workId: string, taskKey: string, endedAt?: string): BoulderState | null;
83
- export declare function completeBoulder(directory: string, workId?: string, endedAt?: string): BoulderState | null;
1
+ export { addBoulderWork, appendSessionId, appendSessionIdForWork, clearBoulderState, completeBoulder, createBoulderState, endTaskTimer, findPrometheusPlans, generateWorkId, getActiveWorks, getBoulderFilePath, getBoulderWorks, getPlanName, getPlanProgress, getTaskSessionState, getWorkById, getWorkByPlanName, getWorkForSession, getWorkResumeOptions, readBoulderState, resolveBoulderPlanPath, resolveBoulderPlanPathForWork, selectActiveWork, startTaskTimer, upsertTaskSessionState, upsertTaskSessionStateForWork, writeBoulderState, } from "@oh-my-opencode/boulder-state";
@@ -1,2 +1 @@
1
- import type { TopLevelTaskRef } from "./types";
2
- export declare function readCurrentTopLevelTask(planPath: string): TopLevelTaskRef | null;
1
+ export { readCurrentTopLevelTask } from "@oh-my-opencode/boulder-state";
@@ -1,100 +1 @@
1
- /**
2
- * Boulder State Types
3
- *
4
- * Manages the active work plan state for Sisyphus orchestrator.
5
- * Named after Sisyphus's boulder - the eternal task that must be rolled.
6
- */
7
- export interface BoulderState {
8
- schema_version?: 2;
9
- active_work_id?: string;
10
- works?: Record<string, BoulderWorkState>;
11
- /** Absolute path to the active plan file */
12
- active_plan: string;
13
- /** ISO timestamp when work started */
14
- started_at: string;
15
- ended_at?: string;
16
- elapsed_ms?: number;
17
- status?: BoulderWorkStatus;
18
- updated_at?: string;
19
- /** Session IDs that have worked on this plan */
20
- session_ids: string[];
21
- session_origins?: Record<string, "direct" | "appended">;
22
- /** Plan name derived from filename */
23
- plan_name: string;
24
- /** Agent type to use when resuming (e.g., 'atlas') */
25
- agent?: string;
26
- /** Absolute path to the git worktree root where work happens */
27
- worktree_path?: string;
28
- /** Preferred reusable subagent sessions keyed by current top-level plan task */
29
- task_sessions?: Record<string, TaskSessionState>;
30
- }
31
- export type BoulderSessionOrigin = "direct" | "appended";
32
- export type BoulderWorkStatus = "active" | "completed" | "paused" | "abandoned";
33
- export type BoulderTaskStatus = "running" | "completed" | "cancelled";
34
- export interface BoulderWorkState {
35
- work_id: string;
36
- active_plan: string;
37
- plan_name: string;
38
- status?: BoulderWorkStatus;
39
- started_at: string;
40
- ended_at?: string;
41
- elapsed_ms?: number;
42
- updated_at?: string;
43
- session_ids: string[];
44
- session_origins?: Record<string, BoulderSessionOrigin>;
45
- agent?: string;
46
- worktree_path?: string;
47
- task_sessions?: Record<string, TaskSessionState>;
48
- }
49
- export interface PlanProgress {
50
- /** Total number of checkboxes */
51
- total: number;
52
- /** Number of completed checkboxes */
53
- completed: number;
54
- /** Whether all tasks are done */
55
- isComplete: boolean;
56
- }
57
- export interface TaskSessionState {
58
- /** Stable identifier for the current top-level plan task (e.g. todo:1 / final-wave:F1) */
59
- task_key: string;
60
- /** Original task label from the plan file */
61
- task_label: string;
62
- /** Full task title from the plan file */
63
- task_title: string;
64
- /** Preferred reusable subagent session */
65
- session_id: string;
66
- /** Agent associated with the task session, when known */
67
- agent?: string;
68
- /** Category associated with the task session, when known */
69
- category?: string;
70
- started_at?: string;
71
- ended_at?: string;
72
- elapsed_ms?: number;
73
- status?: BoulderTaskStatus;
74
- /** Last update timestamp */
75
- updated_at: string;
76
- }
77
- export interface BoulderWorkResumeOption {
78
- work_id: string;
79
- plan_name: string;
80
- active_plan: string;
81
- worktree_path?: string;
82
- status: BoulderWorkStatus;
83
- started_at: string;
84
- updated_at: string;
85
- ended_at?: string;
86
- elapsed_ms?: number;
87
- session_count: number;
88
- progress: PlanProgress;
89
- is_current_mirror: boolean;
90
- }
91
- export interface TopLevelTaskRef {
92
- /** Stable identifier for the current top-level plan task */
93
- key: string;
94
- /** Task section in the Prometheus plan */
95
- section: "todo" | "final-wave";
96
- /** Original label token (e.g. 1 / F1) */
97
- label: string;
98
- /** Full task title extracted from the checkbox line */
99
- title: string;
100
- }
1
+ export type { BoulderSessionOrigin, BoulderState, BoulderTaskStatus, BoulderWorkResumeOption, BoulderWorkState, BoulderWorkStatus, PlanProgress, TaskSessionState, TopLevelTaskRef, } from "@oh-my-opencode/boulder-state";
@@ -1,6 +1,6 @@
1
1
  import type { PluginInput } from "@opencode-ai/plugin";
2
- import type { TrackedTask, TaskStatus, ModelFallbackInfo } from "./types";
3
2
  import type { ConcurrencyManager } from "../background-agent/concurrency";
3
+ import type { ModelFallbackInfo, TaskStatus, TrackedTask } from "./types";
4
4
  type OpencodeClient = PluginInput["client"];
5
5
  export declare class TaskToastManager {
6
6
  private tasks;
@@ -1,12 +1,15 @@
1
- import { rename } from "node:fs/promises";
1
+ import { open, rename, rm } from "node:fs/promises";
2
2
  type LockOptions = {
3
3
  staleAfterMs?: number;
4
4
  ownerTag?: string;
5
5
  };
6
+ type AtomicWriteDeps = {
7
+ open?: typeof open;
8
+ rename?: typeof rename;
9
+ rm?: typeof rm;
10
+ };
6
11
  export declare function withLock<T>(lockPath: string, fn: () => Promise<T>, opts?: LockOptions): Promise<T>;
7
12
  export declare function detectStaleLock(lockPath: string, staleAfterMs: number): Promise<boolean>;
8
13
  export declare function reapStaleLock(lockPath: string): Promise<void>;
9
- export declare function atomicWrite(filePath: string, content: string | Buffer, deps?: {
10
- rename: typeof rename;
11
- }): Promise<void>;
14
+ export declare function atomicWrite(filePath: string, content: string | Buffer, deps?: AtomicWriteDeps): Promise<void>;
12
15
  export {};
@@ -31,6 +31,7 @@ export declare class TmuxSessionManager {
31
31
  private tmuxConfig;
32
32
  private projectDirectory;
33
33
  private serverUrl;
34
+ private ctxServerUrl;
34
35
  private sourcePaneId;
35
36
  private sessions;
36
37
  private pendingSessions;
@@ -60,6 +61,7 @@ export declare class TmuxSessionManager {
60
61
  private getSessionMappings;
61
62
  getTrackedPaneId(sessionId: string): string | undefined;
62
63
  getServerUrl(): string;
64
+ getCtxServerUrl(): string | undefined;
63
65
  private removeTrackedSession;
64
66
  private reassignIsolatedContainerAnchor;
65
67
  private cleanupIsolatedContainerAfterSessionDeletion;
@@ -1,7 +1,7 @@
1
1
  export declare const DIRECT_WORK_REMINDER: string;
2
2
  export declare const BOULDER_CONTINUATION_PROMPT: string;
3
3
  export declare const BOULDER_COMPLETE_PROMPT = "<system-reminder>\nBOULDER COMPLETE: plan \"{PLAN_NAME}\" is fully checked.\n\nTotal elapsed: {ELAPSED_HUMAN}\n\nPer-task breakdown:\n{TASK_BREAKDOWN}\n\nPer your <boulder_completion_response> instructions, print the final ORCHESTRATION COMPLETE summary in your next turn. This nudge fires at most once.\n</system-reminder>";
4
- export declare const VERIFICATION_REMINDER = "**THE SUBAGENT JUST CLAIMED THIS TASK IS DONE. THEY ARE PROBABLY LYING.**\n\nSubagents say \"done\" when code has errors, tests pass trivially, logic is wrong,\nor they quietly added features nobody asked for. This happens EVERY TIME.\nAssume the work is broken until YOU prove otherwise.\n\n---\n\n**PHASE 1: READ THE CODE FIRST (before running anything)**\n\nDo NOT run tests yet. Read the code FIRST so you know what you're testing.\n\n1. `Bash(\"git diff --stat -- ':!node_modules'\")` - see exactly which files changed. Any file outside expected scope = scope creep.\n2. `Read` EVERY changed file - no exceptions, no skimming.\n3. For EACH file, critically ask:\n - Does this code ACTUALLY do what the task required? (Re-read the task, compare line by line)\n - Any stubs, TODOs, placeholders, hardcoded values? (`Grep` for TODO, FIXME, HACK, xxx)\n - Logic errors? Trace the happy path AND the error path in your head.\n - Anti-patterns? (`Grep` for `as any`, `@ts-ignore`, empty catch, console.log in changed files)\n - Scope creep? Did the subagent touch things or add features NOT in the task spec?\n4. Cross-check every claim:\n - Said \"Updated X\" - READ X. Actually updated, or just superficially touched?\n - Said \"Added tests\" - READ the tests. Do they test REAL behavior or just `expect(true).toBe(true)`?\n - Said \"Follows patterns\" - OPEN a reference file. Does it ACTUALLY match?\n\n**If you cannot explain what every changed line does, you have NOT reviewed it.**\n\n**PHASE 2: RUN AUTOMATED CHECKS (targeted, then broad)**\n\nNow that you understand the code, verify mechanically:\n1. `lsp_diagnostics` on EACH changed file - ZERO new errors\n2. Run tests for changed modules FIRST, then full suite\n3. Build/typecheck - exit 0\n\nIf Phase 1 found issues but Phase 2 passes: Phase 2 is WRONG. The code has bugs that tests don't cover. Fix the code.\n\n**PHASE 3: HANDS-ON QA - ACTUALLY RUN IT (MANDATORY for user-facing changes)**\n\nTests and linters CANNOT catch: visual bugs, wrong CLI output, broken user flows, API response shape issues.\n\n**If this task produced anything a user would SEE or INTERACT with, you MUST launch it and verify yourself.**\n\n- **Frontend/UI**: `/playwright` skill - load the page, click through the flow, check console. Verify: page loads, interactions work, console clean, responsive.\n- **TUI/CLI**: `interactive_bash` - run the command, try good input, try bad input, try --help. Verify: command runs, output correct, error messages helpful, edge inputs handled.\n- **API/Backend**: `Bash` with curl - hit the endpoint, check response body, send malformed input. Verify: returns 200, body correct, error cases return proper errors.\n- **Config/Build**: Actually start the service or import the config. Verify: loads without error, backward compatible.\n\nThis is NOT optional \"if applicable\". If the deliverable is user-facing and you did not run it, you are shipping untested work.\n\n**PHASE 4: GATE DECISION - Should you proceed to the next task?**\n\nAnswer honestly:\n1. Can I explain what EVERY changed line does? (If no - back to Phase 1)\n2. Did I SEE it work with my own eyes? (If user-facing and no - back to Phase 3)\n3. Am I confident nothing existing is broken? (If no - run broader tests)\n\nALL three must be YES. \"Probably\" = NO. \"I think so\" = NO. Investigate until CERTAIN.\n\n- **All 3 YES** - Proceed: mark task complete, move to next.\n- **Any NO** - Reject: resume session with `session_id`, fix the specific issue.\n- **Unsure** - Reject: \"unsure\" = \"no\". Investigate until you have a definitive answer.\n\n**DO NOT proceed to the next task until all 4 phases are complete and the gate passes.**";
4
+ export declare const VERIFICATION_REMINDER = "**THE SUBAGENT JUST CLAIMED THIS TASK IS DONE. THEY ARE PROBABLY LYING.**\n\nSubagents say \"done\" when code has errors, tests pass trivially, logic is wrong,\nor they quietly added features nobody asked for. This happens EVERY TIME.\nAssume the work is broken until YOU prove otherwise.\n\n---\n\n**PHASE 1: READ THE CODE FIRST (before running anything)**\n\nDo NOT run tests yet. Read the code FIRST so you know what you're testing.\n\n1. `Bash(\"git diff --stat -- ':!node_modules'\")` - see exactly which files changed. Any file outside expected scope = scope creep.\n2. `Read` EVERY changed file - no exceptions, no skimming.\n3. For EACH file, critically ask:\n - Does this code ACTUALLY do what the task required? (Re-read the task, compare line by line)\n - Any stubs, TODOs, placeholders, hardcoded values? (`Grep` for TODO, FIXME, HACK, xxx)\n - Logic errors? Trace the happy path AND the error path in your head.\n - Anti-patterns? (`Grep` for `as any`, `@ts-ignore`, empty catch, console.log in changed files)\n - Scope creep? Did the subagent touch things or add features NOT in the task spec?\n4. Cross-check every claim:\n - Said \"Updated X\" - READ X. Actually updated, or just superficially touched?\n - Said \"Added tests\" - READ the tests. Do they test REAL behavior or just `expect(true).toBe(true)`?\n - Said \"Follows patterns\" - OPEN a reference file. Does it ACTUALLY match?\n\n**If you cannot explain what every changed line does, you have NOT reviewed it.**\n\n**PHASE 2: RUN AUTOMATED CHECKS (targeted, then broad)**\n\nNow that you understand the code, verify mechanically:\n1. `lsp_diagnostics` on EACH changed file - ZERO new errors\n2. Run tests for changed modules FIRST, then full suite\n3. Build/typecheck - exit 0\n\nIf Phase 1 found issues but Phase 2 passes: Phase 2 is WRONG. The code has bugs that tests don't cover. Fix the code.\n\n**PHASE 3: HANDS-ON QA - ACTUALLY RUN IT (MANDATORY for user-facing changes)**\n\nTests and linters CANNOT catch: visual bugs, wrong CLI output, broken user flows, API response shape issues.\n\n**If this task produced anything a user would SEE or INTERACT with, you MUST launch it and verify yourself.**\n\n- **Frontend/UI**: `/playwright` skill - load the page, click through the flow, check console. Verify: page loads, interactions work, console clean, responsive.\n- **TUI/CLI**: `interactive_bash` - run the command, try good input, try bad input, try --help. Verify: command runs, output correct, error messages helpful, edge inputs handled.\n- **API/Backend**: `Bash` with curl - hit the endpoint, check response body, send malformed input. Verify: returns 200, body correct, error cases return proper errors.\n- **Config/Build**: Actually start the service or import the config. Verify: loads without error, backward compatible.\n\nThis is NOT optional \"if applicable\". If the deliverable is user-facing and you did not run it, you are shipping untested work.\n\n**PHASE 4: GATE DECISION - Should you proceed to the next task?**\n\nAnswer honestly:\n1. Can I explain what EVERY changed line does? (If no - back to Phase 1)\n2. Did I SEE it work with my own eyes? (If user-facing and no - back to Phase 3)\n3. Am I confident nothing existing is broken? (If no - run broader tests)\n\nALL three must be YES. \"Probably\" = NO. \"I think so\" = NO. Investigate until CERTAIN.\n\n- **All 3 YES** - Proceed: mark task complete, move to next.\n- **Any NO** - Reject: resume with `task_id`, fix the specific issue.\n- **Unsure** - Reject: \"unsure\" = \"no\". Investigate until you have a definitive answer.\n\n**DO NOT proceed to the next task until all 4 phases are complete and the gate passes.**";
5
5
  export declare const VERIFICATION_REMINDER_GEMINI = "**THE SUBAGENT HAS FINISHED. THEIR WORK IS EXTREMELY SUSPICIOUS.**\n\nThe subagent CLAIMS this task is done. Based on thousands of executions, subagent claims are FALSE more often than true.\nThey ROUTINELY:\n- Ship code with syntax errors they didn't bother to check\n- Create stub implementations with TODOs and call it \"done\"\n- Write tests that pass trivially (testing nothing meaningful)\n- Implement logic that does NOT match what was requested\n- Add features nobody asked for and call it \"improvement\"\n- Report \"all tests pass\" when they didn't run any tests\n\n**This is NOT a theoretical warning. This WILL happen on this task. Assume the work is BROKEN.**\n\n**YOU MUST VERIFY WITH ACTUAL TOOL CALLS. NOT REASONING. TOOL CALLS.**\nThinking \"it looks correct\" is NOT verification. Running `lsp_diagnostics` IS.\n\n---\n\n**PHASE 1: READ THE CODE FIRST (DO NOT SKIP - DO NOT RUN TESTS YET)**\n\nRead the code FIRST so you know what you're testing.\n\n1. `Bash(\"git diff --stat -- ':!node_modules'\")` - see exactly which files changed.\n2. `Read` EVERY changed file - no exceptions, no skimming.\n3. For EACH file:\n - Does this code ACTUALLY do what the task required? RE-READ the task spec.\n - Any stubs, TODOs, placeholders? `Grep` for TODO, FIXME, HACK, xxx\n - Anti-patterns? `Grep` for `as any`, `@ts-ignore`, empty catch\n - Scope creep? Did the subagent add things NOT in the task spec?\n4. Cross-check EVERY claim against actual code.\n\n**If you cannot explain what every changed line does, GO BACK AND READ AGAIN.**\n\n**PHASE 2: RUN AUTOMATED CHECKS**\n\n1. `lsp_diagnostics` on EACH changed file - ZERO new errors. ACTUALLY RUN THIS.\n2. Run tests for changed modules, then full suite. ACTUALLY RUN THESE.\n3. Build/typecheck - exit 0.\n\nIf Phase 1 found issues but Phase 2 passes: Phase 2 is WRONG. Fix the code.\n\n**PHASE 3: HANDS-ON QA (MANDATORY for user-facing changes)**\n\n- **Frontend/UI**: `/playwright`\n- **TUI/CLI**: `interactive_bash`\n- **API/Backend**: `Bash` with curl\n\n**If user-facing and you did not run it, you are shipping UNTESTED BROKEN work.**\n\n**PHASE 4: GATE DECISION**\n\n1. Can I explain what EVERY changed line does? (If no \u2192 Phase 1)\n2. Did I SEE it work via tool calls? (If user-facing and no \u2192 Phase 3)\n3. Am I confident nothing is broken? (If no \u2192 broader tests)\n\nALL three must be YES. \"Probably\" = NO. \"I think so\" = NO.\n\n**DO NOT proceed to the next task until all 4 phases are complete.**";
6
6
  export declare const ORCHESTRATOR_DELEGATION_REQUIRED: string;
7
7
  export declare const SINGLE_TASK_DIRECTIVE: string;
@@ -3,7 +3,14 @@ export interface DisabledHooksConfig {
3
3
  Stop?: string[];
4
4
  PreToolUse?: string[];
5
5
  PostToolUse?: string[];
6
+ PostToolUseFailure?: string[];
7
+ PermissionRequest?: string[];
6
8
  UserPromptSubmit?: string[];
9
+ Notification?: string[];
10
+ SubagentStart?: string[];
11
+ SubagentStop?: string[];
12
+ SessionStart?: string[];
13
+ SessionEnd?: string[];
7
14
  PreCompact?: string[];
8
15
  }
9
16
  export interface PluginExtendedConfig {
@@ -1,4 +1,7 @@
1
- import type { ClaudeHooksConfig } from "./types";
1
+ import type { ClaudeHooksConfig, PluginHooksConfig } from "./types";
2
2
  export declare function getClaudeSettingsPaths(customPath?: string): string[];
3
3
  export declare function clearClaudeHooksConfigCache(): void;
4
+ export declare function resetPluginHooksState(): void;
5
+ export declare function setPluginHooksConfigs(directory: string, configs: PluginHooksConfig[]): void;
6
+ export declare function mergePluginHooksConfigs(base: ClaudeHooksConfig, pluginHooksConfigs: PluginHooksConfig[]): ClaudeHooksConfig;
4
7
  export declare function loadClaudeHooksConfig(customSettingsPath?: string): Promise<ClaudeHooksConfig | null>;
@@ -2,7 +2,7 @@
2
2
  * Claude Code Hooks Type Definitions
3
3
  * Maps Claude Code hook concepts to OpenCode plugin events
4
4
  */
5
- export type ClaudeHookEvent = "PreToolUse" | "PostToolUse" | "UserPromptSubmit" | "Stop" | "PreCompact";
5
+ export type ClaudeHookEvent = "PreToolUse" | "PostToolUse" | "PostToolUseFailure" | "PermissionRequest" | "UserPromptSubmit" | "Notification" | "Stop" | "SubagentStart" | "SubagentStop" | "SessionStart" | "SessionEnd" | "PreCompact";
6
6
  export interface HookMatcher {
7
7
  matcher: string;
8
8
  hooks: HookAction[];
@@ -10,6 +10,8 @@ export interface HookMatcher {
10
10
  export interface HookCommand {
11
11
  type: "command";
12
12
  command: string;
13
+ /** Env vars allowed to pass through to the spawned process (plugin-sourced hooks are intersected with mcp_env_allowlist) */
14
+ allowedEnvVars?: string[];
13
15
  }
14
16
  export interface HookHttp {
15
17
  type: "http";
@@ -22,8 +24,15 @@ export type HookAction = HookCommand | HookHttp;
22
24
  export interface ClaudeHooksConfig {
23
25
  PreToolUse?: HookMatcher[];
24
26
  PostToolUse?: HookMatcher[];
27
+ PostToolUseFailure?: HookMatcher[];
28
+ PermissionRequest?: HookMatcher[];
25
29
  UserPromptSubmit?: HookMatcher[];
30
+ Notification?: HookMatcher[];
26
31
  Stop?: HookMatcher[];
32
+ SubagentStart?: HookMatcher[];
33
+ SubagentStop?: HookMatcher[];
34
+ SessionStart?: HookMatcher[];
35
+ SessionEnd?: HookMatcher[];
27
36
  PreCompact?: HookMatcher[];
28
37
  }
29
38
  export interface PreToolUseInput {
@@ -189,3 +198,10 @@ export interface PluginConfig {
189
198
  disabledHooks?: boolean | ClaudeHookEvent[];
190
199
  keywordDetectorDisabled?: boolean;
191
200
  }
201
+ /**
202
+ * Plugin hooks configuration shape.
203
+ * Replaces the loose `Array<{ hooks?: Record<string, unknown> }>` with a proper typed interface.
204
+ */
205
+ export interface PluginHooksConfig {
206
+ hooks?: Partial<Record<ClaudeHookEvent, unknown[]>>;
207
+ }
@@ -1,3 +1,4 @@
1
+ import { type CheckResult, type HookInput } from "@oh-my-opencode/comment-checker-core";
1
2
  /**
2
3
  * Asynchronously get comment-checker binary path.
3
4
  * Will trigger lazy download if binary not found.
@@ -13,28 +14,7 @@ export declare function getCommentCheckerPathSync(): string | null;
13
14
  * Call this early to trigger download while other init happens.
14
15
  */
15
16
  export declare function startBackgroundInit(): void;
16
- export interface HookInput {
17
- session_id: string;
18
- tool_name: string;
19
- transcript_path: string;
20
- cwd: string;
21
- hook_event_name: string;
22
- tool_input: {
23
- file_path?: string;
24
- content?: string;
25
- old_string?: string;
26
- new_string?: string;
27
- edits?: Array<{
28
- old_string: string;
29
- new_string: string;
30
- }>;
31
- };
32
- tool_response?: unknown;
33
- }
34
- export interface CheckResult {
35
- hasComments: boolean;
36
- message: string;
37
- }
17
+ export type { HookInput, CheckResult };
38
18
  /**
39
19
  * Run comment-checker CLI with given input.
40
20
  * @param input Hook input to check
@@ -1,31 +1 @@
1
- export type CommentType = "line" | "block" | "docstring";
2
- export interface CommentInfo {
3
- text: string;
4
- lineNumber: number;
5
- filePath: string;
6
- commentType: CommentType;
7
- isDocstring: boolean;
8
- metadata?: Record<string, string>;
9
- }
10
- export interface PendingCall {
11
- filePath: string;
12
- content?: string;
13
- oldString?: string;
14
- newString?: string;
15
- edits?: Array<{
16
- old_string: string;
17
- new_string: string;
18
- }>;
19
- tool: "write" | "edit" | "multiedit";
20
- sessionID: string;
21
- timestamp: number;
22
- }
23
- export interface FileComments {
24
- filePath: string;
25
- comments: CommentInfo[];
26
- }
27
- export interface FilterResult {
28
- shouldSkip: boolean;
29
- reason?: string;
30
- }
31
- export type CommentFilter = (comment: CommentInfo) => FilterResult;
1
+ export type { ApplyPatchAccumulator, ApplyPatchFileMetadata, CheckResult, CheckerEdit, CommentFilter, CommentInfo, CommentType, FileComments, FilterResult, HookInput, PendingCall, ResolveCommentCheckerBinaryInput, RunCommentCheckerInput, RunCommentCheckerOptions, SpawnFn, SpawnProcess, SpawnSignal, } from "@oh-my-opencode/comment-checker-core";
@@ -1,7 +1,2 @@
1
- import type { AgentsMdCache } from "@oh-my-opencode/rules-core";
2
- export declare function resolveFilePath(rootDirectory: string, path: string): string | null;
3
- export declare function findAgentsMdUp(input: {
4
- readonly startDir: string;
5
- readonly rootDir: string;
6
- readonly cache?: AgentsMdCache;
7
- }): Promise<string[]>;
1
+ export { resolveFilePath } from "@oh-my-opencode/agents-md-core";
2
+ export { findAgentsMdUp } from "@oh-my-opencode/rules-engine";
@@ -1,18 +1 @@
1
- import type { PluginInput } from "@opencode-ai/plugin";
2
- import type { AgentsMdCache } from "@oh-my-opencode/rules-core";
3
- import type { createDynamicTruncator } from "../../shared/dynamic-truncator";
4
- type DynamicTruncator = ReturnType<typeof createDynamicTruncator>;
5
- export declare function processFilePathForAgentsInjection(input: {
6
- ctx: PluginInput;
7
- truncator: DynamicTruncator;
8
- sessionCaches: Map<string, Set<string>>;
9
- agentsMdCache?: AgentsMdCache;
10
- filePath: string;
11
- sessionID: string;
12
- output: {
13
- title: string;
14
- output: string;
15
- metadata: unknown;
16
- };
17
- }): Promise<void>;
18
- export {};
1
+ export { processFilePathForAgentsInjection } from "@oh-my-opencode/agents-md-core";
@@ -56,3 +56,5 @@ export { createTodoDescriptionOverrideHook } from "./todo-description-override";
56
56
  export { createWebFetchRedirectGuardHook } from "./webfetch-redirect-guard";
57
57
  export { createLegacyPluginToastHook } from "./legacy-plugin-toast";
58
58
  export { createFsyncSkipWarningHook } from "./fsync-skip-warning";
59
+ export { createNotepadWriteGuardHook } from "./notepad-write-guard";
60
+ export { createPlanFormatValidatorHook } from "./plan-format-validator";
@@ -9,4 +9,4 @@
9
9
  * - Vietnamese: phân tích, điều tra, nghiên cứu, kiểm tra, xem xét, chẩn đoán, giải thích, tìm hiểu, gỡ lỗi, tại sao
10
10
  */
11
11
  export declare const ANALYZE_PATTERN: RegExp;
12
- export declare const ANALYZE_MESSAGE = "[analyze-mode]\nANALYSIS MODE. Gather context before diving deep:\n\nCONTEXT GATHERING (parallel):\n- 1-2 explore agents (codebase patterns, implementations)\n- 1-2 librarian agents (if external library involved)\n- Direct tools: Grep, AST-grep, LSP for targeted searches\n\nIF COMPLEX - DO NOT STRUGGLE ALONE. Consult specialists:\n- **Oracle**: Conventional problems (architecture, debugging, complex logic)\n- **Artistry**: Non-conventional problems (different approach needed)\n\nSYNTHESIZE findings before proceeding.";
12
+ export declare const ANALYZE_MESSAGE = "[analyze-mode]\nANALYSIS MODE. Gather context before diving deep:\n\nCONTEXT GATHERING (parallel):\n- 1-2 explore agents (codebase patterns, implementations)\n- 1-2 librarian agents (if external library involved)\n- Direct tools: Grep, AST-grep, LSP for targeted searches\n\nIF COMPLEX - DO NOT STRUGGLE ALONE. Consult specialists:\n- **Oracle**: Conventional problems (architecture, debugging, complex logic)\n- **Artistry**: Non-conventional problems (different approach needed)\n\nSYNTHESIZE findings before proceeding.\n---\nMANDATORY delegate_task params: ALWAYS include load_skills and run_in_background when calling delegate_task. Evaluate available skills before dispatch - pass task-appropriate skills when relevant, pass [] ONLY when no skill matches the task domain.\nExample: delegate_task(subagent_type=\"explore\", prompt=\"...\", run_in_background=true, load_skills=[])";
@@ -1,11 +1,16 @@
1
1
  export declare const CODE_BLOCK_PATTERN: RegExp;
2
2
  export declare const INLINE_CODE_PATTERN: RegExp;
3
- export { isPlannerAgent, isNonOmoAgent, getUltraworkMessage } from "./ultrawork";
4
- export { SEARCH_PATTERN, SEARCH_MESSAGE } from "./search";
5
- export { ANALYZE_PATTERN, ANALYZE_MESSAGE } from "./analyze";
6
- export { TEAM_PATTERN, TEAM_MESSAGE } from "./team";
7
- export { HYPERPLAN_PATTERN, HYPERPLAN_MESSAGE } from "./hyperplan";
8
3
  import type { KeywordType } from "../../config/schema/keyword-detector";
4
+ import { getUltraworkMessage, isPlannerAgent, isNonOmoAgent } from "./ultrawork";
5
+ import { SEARCH_PATTERN, SEARCH_MESSAGE } from "./search";
6
+ import { ANALYZE_PATTERN, ANALYZE_MESSAGE } from "./analyze";
7
+ import { TEAM_PATTERN, TEAM_MESSAGE } from "./team";
8
+ import { HYPERPLAN_PATTERN, HYPERPLAN_MESSAGE } from "./hyperplan";
9
+ export { isPlannerAgent, isNonOmoAgent, getUltraworkMessage };
10
+ export { SEARCH_PATTERN, SEARCH_MESSAGE };
11
+ export { ANALYZE_PATTERN, ANALYZE_MESSAGE };
12
+ export { TEAM_PATTERN, TEAM_MESSAGE };
13
+ export { HYPERPLAN_PATTERN, HYPERPLAN_MESSAGE };
9
14
  export declare const HYPERPLAN_ULTRAWORK_PATTERN: RegExp;
10
15
  export declare function getHyperplanUltraworkMessage(agentName?: string, modelID?: string): string;
11
16
  export type KeywordDetector = {
@@ -5,8 +5,8 @@ export interface DetectedKeyword {
5
5
  }
6
6
  export declare function removeCodeBlocks(text: string): string;
7
7
  export declare function looksLikeSlashCommand(text: string): boolean;
8
- export declare function detectKeywords(text: string, agentName?: string, modelID?: string, disabledKeywords?: ReadonlyArray<KeywordType>): string[];
9
- export declare function detectKeywordsWithType(text: string, agentName?: string, modelID?: string, disabledKeywords?: ReadonlyArray<KeywordType>): DetectedKeyword[];
8
+ export declare function detectKeywords(text: string, agentName?: string, modelID?: string, disabledKeywords?: ReadonlyArray<KeywordType>, enabledExpansions?: ReadonlyArray<KeywordType>): string[];
9
+ export declare function detectKeywordsWithType(text: string, agentName?: string, modelID?: string, disabledKeywords?: ReadonlyArray<KeywordType>, enabledExpansions?: ReadonlyArray<KeywordType>): DetectedKeyword[];
10
10
  export declare function extractPromptText(parts: Array<{
11
11
  type: string;
12
12
  text?: string;
@@ -1,8 +1,9 @@
1
1
  import type { PluginInput } from "@opencode-ai/plugin";
2
+ import type { DefaultModeConfig } from "../../config/schema/default-mode";
2
3
  import type { KeywordDetectorConfig } from "../../config/schema/keyword-detector";
3
4
  import type { ContextCollector } from "../../features/context-injector";
4
5
  import type { RalphLoopHook } from "../ralph-loop";
5
- export declare function createKeywordDetectorHook(ctx: PluginInput, _collector?: ContextCollector, _ralphLoop?: Pick<RalphLoopHook, "startLoop">, config?: KeywordDetectorConfig): {
6
+ export declare function createKeywordDetectorHook(ctx: PluginInput, _collector?: ContextCollector, _ralphLoop?: Pick<RalphLoopHook, "startLoop">, config?: KeywordDetectorConfig, defaultMode?: DefaultModeConfig): {
6
7
  "chat.message": (input: {
7
8
  sessionID: string;
8
9
  agent?: string;
@@ -8,6 +8,11 @@
8
8
  *
9
9
  * The detector injects a thin wrapper that loads the `hyperplan` skill, which
10
10
  * carries the full orchestration instructions for the 5-member adversarial team.
11
+ *
12
+ * The `hpp` shorthand uses an extra negative-lookbehind so that the very common
13
+ * C++ header-file extension `.hpp` (e.g. `interface.hpp`, `src/buffer.hpp`)
14
+ * does NOT falsely trigger hyperplan mode. A leading `.` would otherwise
15
+ * satisfy `\b` because the dot is a non-word character. See issue #4215.
11
16
  */
12
17
  export declare const HYPERPLAN_PATTERN: RegExp;
13
18
  export declare const HYPERPLAN_MESSAGE = "<hyperplan-mode>\n**MANDATORY**: Say \"HYPERPLAN MODE ENABLED!\" as your first response, exactly once.\n\nThe user invoked **hyperplan mode** \u2014 adversarial multi-agent planning via team-mode.\n\nLOAD THE HYPERPLAN SKILL IMMEDIATELY:\n\n```\nskill(name=\"hyperplan\")\n```\n\nAfter loading, follow the skill's full workflow EXACTLY:\n1. Acknowledge and capture the planning request\n2. Spawn the adversarial team via `team_create` with category members `unspecified-low`, `unspecified-high`, `ultrabrain`, and `artistry`; include `deep` only if the category is enabled\n3. Round 1 \u2014 Independent analysis (each member produces findings)\n4. Round 2 \u2014 Cross-attack (each member ruthlessly attacks the other 4's findings)\n5. Round 3 \u2014 Defend, refine, or concede\n6. Distill defensible insights into a structured bundle (Lead does NOT write the plan)\n7. MANDATORY: hand the bundle to the `plan` agent via `task(subagent_type=\"plan\", ...)` \u2014 the plan agent owns sequencing, parallelization, and verification gates\n8. Present the plan agent's output verbatim with provenance line, then clean up the team\n\nDo NOT improvise. Do NOT skip rounds. Do NOT write the plan yourself in step 6 \u2014 the handoff to the plan agent in step 7 is non-negotiable. Be the lead orchestrator and let the adversarial members do the cross-critique.\n\nIf team-mode is unavailable (`team_*` tools missing), instruct the user to set `team_mode.enabled: true` in `~/.config/opencode/oh-my-opencode.jsonc` and restart opencode.\n</hyperplan-mode>";
@@ -0,0 +1,2 @@
1
+ import type { Hooks } from "@opencode-ai/plugin";
2
+ export declare function createNotepadWriteGuardHook(): Hooks;