@skj1724/oh-my-opencode 3.19.4 → 3.19.5

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.
@@ -4,9 +4,13 @@
4
4
 
5
5
  import { spawnSync } from "node:child_process";
6
6
  import { createRequire } from "node:module";
7
+ import { dirname, join } from "node:path";
8
+ import { fileURLToPath } from "node:url";
7
9
  import { getPlatformPackage, getBinaryPath } from "./platform.js";
8
10
 
9
11
  const require = createRequire(import.meta.url);
12
+ const __dirname = dirname(fileURLToPath(import.meta.url));
13
+ const distCliPath = join(__dirname, "..", "dist", "cli", "index.js");
10
14
 
11
15
  /**
12
16
  * Detect libc family on Linux
@@ -29,52 +33,55 @@ function getLibcFamily() {
29
33
  function main() {
30
34
  const { platform, arch } = process;
31
35
  const libcFamily = getLibcFamily();
36
+ const args = process.argv.slice(2);
32
37
 
33
- // Get platform package name
34
- let pkg;
35
- try {
36
- pkg = getPlatformPackage({ platform, arch, libcFamily });
37
- } catch (error) {
38
- console.error(`\noh-my-opencode: ${error.message}\n`);
39
- process.exit(1);
40
- }
41
-
42
- // Resolve binary path
43
- const binRelPath = getBinaryPath(pkg, platform);
44
-
45
- let binPath;
38
+ let binPath = null;
46
39
  try {
40
+ const pkg = getPlatformPackage({ platform, arch, libcFamily });
41
+ const binRelPath = getBinaryPath(pkg, platform);
47
42
  binPath = require.resolve(binRelPath);
48
43
  } catch {
49
- console.error(`\noh-my-opencode: Platform binary not installed.`);
50
- console.error(`\nYour platform: ${platform}-${arch}${libcFamily === "musl" ? "-musl" : ""}`);
51
- console.error(`Expected package: ${pkg}`);
52
- console.error(`\nTo fix, run:`);
53
- console.error(` npm install ${pkg}\n`);
54
- process.exit(1);
55
44
  }
56
45
 
57
- // Spawn the binary
58
- const result = spawnSync(binPath, process.argv.slice(2), {
46
+ if (binPath) {
47
+ const result = spawnSync(binPath, args, {
48
+ stdio: "inherit",
49
+ });
50
+
51
+ if (!result.error && !result.signal) {
52
+ process.exit(result.status ?? 0);
53
+ }
54
+
55
+ if (result.error) {
56
+ console.warn(`\noh-my-opencode: Platform binary failed: ${result.error.message}`);
57
+ } else if (result.signal) {
58
+ console.warn(`\noh-my-opencode: Platform binary crashed (signal: ${result.signal})`);
59
+ }
60
+ console.warn(" Falling back to Bun...\n");
61
+ }
62
+
63
+ const fallbackResult = spawnSync("bun", ["run", distCliPath, ...args], {
59
64
  stdio: "inherit",
60
65
  });
61
66
 
62
- // Handle spawn errors
63
- if (result.error) {
64
- console.error(`\noh-my-opencode: Failed to execute binary.`);
65
- console.error(`Error: ${result.error.message}\n`);
67
+ if (fallbackResult.error) {
68
+ console.error(`\noh-my-opencode: Failed to execute CLI via Bun.`);
69
+ if (fallbackResult.error.code === "ENOENT") {
70
+ console.error(` Bun is not installed. Install it from https://bun.sh\n`);
71
+ } else {
72
+ console.error(` Error: ${fallbackResult.error.message}\n`);
73
+ }
66
74
  process.exit(2);
67
75
  }
68
76
 
69
- // Handle signals
70
- if (result.signal) {
71
- const signalNum = result.signal === "SIGTERM" ? 15 :
72
- result.signal === "SIGKILL" ? 9 :
73
- result.signal === "SIGINT" ? 2 : 1;
77
+ if (fallbackResult.signal) {
78
+ const signalNum = fallbackResult.signal === "SIGTERM" ? 15 :
79
+ fallbackResult.signal === "SIGKILL" ? 9 :
80
+ fallbackResult.signal === "SIGINT" ? 2 : 1;
74
81
  process.exit(128 + signalNum);
75
82
  }
76
-
77
- process.exit(result.status ?? 1);
83
+
84
+ process.exit(fallbackResult.status ?? 1);
78
85
  }
79
86
 
80
87
  main();
package/dist/cli/index.js CHANGED
@@ -6164,6 +6164,12 @@ class PerfTimer {
6164
6164
  }
6165
6165
  }
6166
6166
 
6167
+ // src/shared/perf-tracer.ts
6168
+ var init_perf_tracer = () => {};
6169
+
6170
+ // src/shared/fileio-monitor.ts
6171
+ var init_fileio_monitor = () => {};
6172
+
6167
6173
  // src/shared/index.ts
6168
6174
  var init_shared = __esm(() => {
6169
6175
  init_frontmatter();
@@ -6191,6 +6197,8 @@ var init_shared = __esm(() => {
6191
6197
  init_model_requirements();
6192
6198
  init_model_resolver();
6193
6199
  init_model_availability();
6200
+ init_perf_tracer();
6201
+ init_fileio_monitor();
6194
6202
  });
6195
6203
 
6196
6204
  // src/cli/model-fallback.ts
@@ -8422,7 +8430,7 @@ var import_picocolors2 = __toESM(require_picocolors(), 1);
8422
8430
  // package.json
8423
8431
  var package_default = {
8424
8432
  name: "@skj1724/oh-my-opencode",
8425
- version: "3.19.4",
8433
+ version: "3.19.5",
8426
8434
  description: "The Best AI Agent Harness - Batteries-Included OpenCode Plugin with Multi-Model Orchestration, Parallel Background Agents, and Crafted LSP/AST Tools",
8427
8435
  main: "dist/index.js",
8428
8436
  types: "dist/index.d.ts",
@@ -24960,6 +24968,7 @@ var HookNameSchema = exports_external.enum([
24960
24968
  "edit-error-recovery",
24961
24969
  "delegate-task-retry",
24962
24970
  "prometheus-md-only",
24971
+ "perf-profiler",
24963
24972
  "start-work",
24964
24973
  "atlas"
24965
24974
  ]);
@@ -25073,11 +25082,21 @@ var DynamicContextPruningConfigSchema = exports_external.object({
25073
25082
  }).optional()
25074
25083
  }).optional()
25075
25084
  });
25085
+ var ProfilingConfigSchema = exports_external.object({
25086
+ enabled: exports_external.boolean().default(false),
25087
+ output_dir: exports_external.string().optional(),
25088
+ slow_threshold_ms: exports_external.number().default(100),
25089
+ memory_snapshot_interval: exports_external.number().default(5),
25090
+ trace_api: exports_external.boolean().default(true),
25091
+ trace_fileio: exports_external.boolean().default(true),
25092
+ trace_polling: exports_external.boolean().default(true)
25093
+ });
25076
25094
  var ExperimentalConfigSchema = exports_external.object({
25077
25095
  aggressive_truncation: exports_external.boolean().optional(),
25078
25096
  auto_resume: exports_external.boolean().optional(),
25079
25097
  truncate_all_tool_outputs: exports_external.boolean().optional(),
25080
- dynamic_context_pruning: DynamicContextPruningConfigSchema.optional()
25098
+ dynamic_context_pruning: DynamicContextPruningConfigSchema.optional(),
25099
+ profiling: ProfilingConfigSchema.optional()
25081
25100
  });
25082
25101
  var SkillSourceSchema = exports_external.union([
25083
25102
  exports_external.string(),
@@ -71,6 +71,7 @@ export declare const HookNameSchema: z.ZodEnum<{
71
71
  "edit-error-recovery": "edit-error-recovery";
72
72
  "delegate-task-retry": "delegate-task-retry";
73
73
  "prometheus-md-only": "prometheus-md-only";
74
+ "perf-profiler": "perf-profiler";
74
75
  "start-work": "start-work";
75
76
  }>;
76
77
  export declare const BuiltinCommandNameSchema: z.ZodEnum<{
@@ -890,6 +891,15 @@ export declare const DynamicContextPruningConfigSchema: z.ZodObject<{
890
891
  }, z.core.$strip>>;
891
892
  }, z.core.$strip>>;
892
893
  }, z.core.$strip>;
894
+ export declare const ProfilingConfigSchema: z.ZodObject<{
895
+ enabled: z.ZodDefault<z.ZodBoolean>;
896
+ output_dir: z.ZodOptional<z.ZodString>;
897
+ slow_threshold_ms: z.ZodDefault<z.ZodNumber>;
898
+ memory_snapshot_interval: z.ZodDefault<z.ZodNumber>;
899
+ trace_api: z.ZodDefault<z.ZodBoolean>;
900
+ trace_fileio: z.ZodDefault<z.ZodBoolean>;
901
+ trace_polling: z.ZodDefault<z.ZodBoolean>;
902
+ }, z.core.$strip>;
893
903
  export declare const ExperimentalConfigSchema: z.ZodObject<{
894
904
  aggressive_truncation: z.ZodOptional<z.ZodBoolean>;
895
905
  auto_resume: z.ZodOptional<z.ZodBoolean>;
@@ -920,6 +930,15 @@ export declare const ExperimentalConfigSchema: z.ZodObject<{
920
930
  }, z.core.$strip>>;
921
931
  }, z.core.$strip>>;
922
932
  }, z.core.$strip>>;
933
+ profiling: z.ZodOptional<z.ZodObject<{
934
+ enabled: z.ZodDefault<z.ZodBoolean>;
935
+ output_dir: z.ZodOptional<z.ZodString>;
936
+ slow_threshold_ms: z.ZodDefault<z.ZodNumber>;
937
+ memory_snapshot_interval: z.ZodDefault<z.ZodNumber>;
938
+ trace_api: z.ZodDefault<z.ZodBoolean>;
939
+ trace_fileio: z.ZodDefault<z.ZodBoolean>;
940
+ trace_polling: z.ZodDefault<z.ZodBoolean>;
941
+ }, z.core.$strip>>;
923
942
  }, z.core.$strip>;
924
943
  export declare const SkillSourceSchema: z.ZodUnion<readonly [z.ZodString, z.ZodObject<{
925
944
  path: z.ZodString;
@@ -1043,6 +1062,7 @@ export declare const OhMyOpenCodeConfigSchema: z.ZodObject<{
1043
1062
  "edit-error-recovery": "edit-error-recovery";
1044
1063
  "delegate-task-retry": "delegate-task-retry";
1045
1064
  "prometheus-md-only": "prometheus-md-only";
1065
+ "perf-profiler": "perf-profiler";
1046
1066
  "start-work": "start-work";
1047
1067
  }>>>;
1048
1068
  disabled_commands: z.ZodOptional<z.ZodArray<z.ZodEnum<{
@@ -1778,6 +1798,15 @@ export declare const OhMyOpenCodeConfigSchema: z.ZodObject<{
1778
1798
  }, z.core.$strip>>;
1779
1799
  }, z.core.$strip>>;
1780
1800
  }, z.core.$strip>>;
1801
+ profiling: z.ZodOptional<z.ZodObject<{
1802
+ enabled: z.ZodDefault<z.ZodBoolean>;
1803
+ output_dir: z.ZodOptional<z.ZodString>;
1804
+ slow_threshold_ms: z.ZodDefault<z.ZodNumber>;
1805
+ memory_snapshot_interval: z.ZodDefault<z.ZodNumber>;
1806
+ trace_api: z.ZodDefault<z.ZodBoolean>;
1807
+ trace_fileio: z.ZodDefault<z.ZodBoolean>;
1808
+ trace_polling: z.ZodDefault<z.ZodBoolean>;
1809
+ }, z.core.$strip>>;
1781
1810
  }, z.core.$strip>>;
1782
1811
  auto_update: z.ZodOptional<z.ZodBoolean>;
1783
1812
  skills: z.ZodOptional<z.ZodUnion<readonly [z.ZodArray<z.ZodString>, z.ZodIntersection<z.ZodRecord<z.ZodString, z.ZodUnion<readonly [z.ZodBoolean, z.ZodObject<{
@@ -1833,6 +1862,7 @@ export type SisyphusAgentConfig = z.infer<typeof SisyphusAgentConfigSchema>;
1833
1862
  export type CommentCheckerConfig = z.infer<typeof CommentCheckerConfigSchema>;
1834
1863
  export type ExperimentalConfig = z.infer<typeof ExperimentalConfigSchema>;
1835
1864
  export type DynamicContextPruningConfig = z.infer<typeof DynamicContextPruningConfigSchema>;
1865
+ export type ProfilingConfig = z.infer<typeof ProfilingConfigSchema>;
1836
1866
  export type SkillsConfig = z.infer<typeof SkillsConfigSchema>;
1837
1867
  export type SkillDefinition = z.infer<typeof SkillDefinitionSchema>;
1838
1868
  export type RalphLoopConfig = z.infer<typeof RalphLoopConfigSchema>;
@@ -1,5 +1,6 @@
1
1
  import type { PluginInput } from "@opencode-ai/plugin";
2
2
  import type { BackgroundTask, LaunchInput, ResumeInput } from "./types";
3
+ import type { PerfTracer } from "../../shared/perf-tracer";
3
4
  import type { BackgroundTaskConfig } from "../../config/schema";
4
5
  interface EventProperties {
5
6
  sessionID?: string;
@@ -26,9 +27,11 @@ export declare class BackgroundManager {
26
27
  private shutdownTriggered;
27
28
  private config?;
28
29
  private perfAggregator;
30
+ private perfTracer?;
29
31
  private queuesByKey;
30
32
  private processingKeys;
31
33
  constructor(ctx: PluginInput, config?: BackgroundTaskConfig);
34
+ setPerfTracer(tracer: PerfTracer): void;
32
35
  launch(input: LaunchInput): Promise<BackgroundTask>;
33
36
  private processKey;
34
37
  private startTask;
@@ -8,11 +8,5 @@ export interface StoredMessage {
8
8
  tools?: Record<string, ToolPermission>;
9
9
  }
10
10
  export declare function findNearestMessageWithFields(messageDir: string): StoredMessage | null;
11
- /**
12
- * Finds the FIRST (oldest) message in the session with agent field.
13
- * This is used to get the original agent that started the session,
14
- * avoiding issues where newer messages may have a different agent
15
- * due to OpenCode's internal agent switching.
16
- */
17
11
  export declare function findFirstMessageWithAgent(messageDir: string): string | null;
18
12
  export declare function injectHookMessage(sessionID: string, hookContent: string, originalMessage: OriginalMessageContext): boolean;
@@ -28,3 +28,4 @@ export { createStartWorkHook } from "./start-work";
28
28
  export { createAtlasHook } from "./atlas";
29
29
  export { createDelegateTaskRetryHook } from "./delegate-task-retry";
30
30
  export { createQuestionLabelTruncatorHook } from "./question-label-truncator";
31
+ export { createPerfProfilerHook } from "./perf-profiler";
@@ -0,0 +1,2 @@
1
+ import type { PerfProfilerOptions, PerfProfilerHook } from "./types";
2
+ export declare function createPerfProfilerHook(options: PerfProfilerOptions): PerfProfilerHook;
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,42 @@
1
+ import type { ProfilingConfig } from "../../config/schema";
2
+ import type { PerfTracer } from "../../shared/perf-tracer";
3
+ export interface PerfProfilerOptions {
4
+ config: ProfilingConfig;
5
+ tracer: PerfTracer;
6
+ /** 注册 Map/Set size 采集回调,key 为探针名称,fn 返回当前 size */
7
+ memoryProbes?: Record<string, () => number>;
8
+ }
9
+ export interface PerfProfilerHook {
10
+ "event": (input: {
11
+ event: {
12
+ type: string;
13
+ properties?: unknown;
14
+ };
15
+ }) => Promise<void>;
16
+ "tool.execute.before": (input: {
17
+ tool: string;
18
+ sessionID: string;
19
+ callID: string;
20
+ }, output: {
21
+ args: Record<string, unknown>;
22
+ }) => Promise<void>;
23
+ "tool.execute.after": (input: {
24
+ tool: string;
25
+ sessionID: string;
26
+ callID: string;
27
+ }, output: {
28
+ title: string;
29
+ output: string;
30
+ metadata: unknown;
31
+ }) => Promise<void>;
32
+ "chat.message": (input: {
33
+ sessionID: string;
34
+ agent?: string;
35
+ }, output: {
36
+ message: Record<string, unknown>;
37
+ parts: Array<{
38
+ type: string;
39
+ text?: string;
40
+ }>;
41
+ }) => Promise<void>;
42
+ }
@@ -1,10 +1,34 @@
1
- import type { ThinkModeInput } from "./types";
2
1
  export * from "./detector";
3
2
  export * from "./switcher";
4
3
  export * from "./types";
5
4
  export declare function clearThinkModeState(sessionID: string): void;
6
5
  export declare function createThinkModeHook(): {
7
- "chat.params": (output: ThinkModeInput, sessionID: string) => Promise<void>;
6
+ "chat.params": (input: {
7
+ sessionID: string;
8
+ agent: string;
9
+ model: {
10
+ id: string;
11
+ providerID: string;
12
+ };
13
+ provider: {
14
+ source: string;
15
+ info: unknown;
16
+ options: Record<string, unknown>;
17
+ };
18
+ message: {
19
+ role: string;
20
+ parts?: Array<{
21
+ type: string;
22
+ text?: string;
23
+ }>;
24
+ };
25
+ }, output: {
26
+ temperature: number;
27
+ topP: number;
28
+ topK: number;
29
+ maxOutputTokens: number | undefined;
30
+ options: Record<string, unknown>;
31
+ }) => Promise<void>;
8
32
  event: ({ event }: {
9
33
  event: {
10
34
  type: string;
@@ -1,3 +1,5 @@
1
+ import type { Model, UserMessage } from "@opencode-ai/sdk";
2
+ import type { ProviderContext } from "@opencode-ai/plugin";
1
3
  export interface ThinkModeState {
2
4
  requested: boolean;
3
5
  modelSwitched: boolean;
@@ -5,17 +7,17 @@ export interface ThinkModeState {
5
7
  providerID?: string;
6
8
  modelID?: string;
7
9
  }
8
- export interface ModelRef {
9
- providerID: string;
10
- modelID: string;
11
- }
12
- export interface MessageWithModel {
13
- model?: ModelRef;
14
- }
15
10
  export interface ThinkModeInput {
16
- parts: Array<{
17
- type: string;
18
- text?: string;
19
- }>;
20
- message: MessageWithModel;
11
+ sessionID: string;
12
+ agent: string;
13
+ model: Model;
14
+ provider: ProviderContext;
15
+ message: UserMessage;
16
+ }
17
+ export interface ThinkModeOutput {
18
+ temperature: number;
19
+ topP: number;
20
+ topK: number;
21
+ maxOutputTokens: number | undefined;
22
+ options: Record<string, unknown>;
21
23
  }