@skj1724/oh-my-opencode 3.19.12 → 3.19.14

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.
package/dist/cli/index.js CHANGED
@@ -8467,7 +8467,7 @@ var import_picocolors2 = __toESM(require_picocolors(), 1);
8467
8467
  // package.json
8468
8468
  var package_default = {
8469
8469
  name: "@skj1724/oh-my-opencode",
8470
- version: "3.19.12",
8470
+ version: "3.19.14",
8471
8471
  description: "The Best AI Agent Harness - Batteries-Included OpenCode Plugin with Multi-Model Orchestration, Parallel Background Agents, and Crafted LSP/AST Tools",
8472
8472
  main: "dist/index.js",
8473
8473
  types: "dist/index.d.ts",
package/dist/index.js CHANGED
@@ -24998,6 +24998,7 @@ init_runtime_fallback();
24998
24998
  function createRuntimeFallbackHook(ctx, options) {
24999
24999
  const retryStates = new Map;
25000
25000
  const fallbackAttempts = new Map;
25001
+ const interruptingSessions = new Map;
25001
25002
  const config = options?.config ?? {
25002
25003
  enabled: true,
25003
25004
  max_attempts: 3,
@@ -25020,21 +25021,31 @@ function createRuntimeFallbackHook(ctx, options) {
25020
25021
  if (sessionID2) {
25021
25022
  retryStates.delete(sessionID2);
25022
25023
  fallbackAttempts.delete(sessionID2);
25024
+ interruptingSessions.delete(sessionID2);
25023
25025
  }
25024
25026
  return false;
25025
25027
  }
25026
- if (event.type !== "session.error" && event.type !== "message.updated")
25028
+ if (event.type !== "session.error" && event.type !== "message.updated" && event.type !== "message.part.updated")
25027
25029
  return false;
25028
25030
  const props = event.properties;
25029
25031
  let sessionID;
25030
25032
  let error;
25033
+ let retryAttempt;
25031
25034
  if (event.type === "session.error") {
25032
25035
  sessionID = props?.sessionID;
25033
25036
  error = props?.error;
25034
- } else {
25037
+ } else if (event.type === "message.updated") {
25035
25038
  const info = props?.info;
25036
25039
  sessionID = info?.sessionID;
25037
25040
  error = info?.error;
25041
+ } else {
25042
+ const part = props?.part;
25043
+ if (part?.type !== "retry")
25044
+ return false;
25045
+ const retryPart = part;
25046
+ sessionID = retryPart.sessionID ?? props?.sessionID;
25047
+ error = retryPart.error;
25048
+ retryAttempt = retryPart.attempt;
25038
25049
  }
25039
25050
  if (!sessionID || error === undefined || error === null)
25040
25051
  return false;
@@ -25049,7 +25060,8 @@ function createRuntimeFallbackHook(ctx, options) {
25049
25060
  errorKeys: error && typeof error === "object" ? Object.keys(error) : [],
25050
25061
  messageSnippet: classification.reason?.substring(0, 100),
25051
25062
  sessionID,
25052
- eventType: event.type
25063
+ eventType: event.type,
25064
+ retryAttempt
25053
25065
  });
25054
25066
  if (classification.category === "context_overflow") {
25055
25067
  return false;
@@ -25058,17 +25070,26 @@ function createRuntimeFallbackHook(ctx, options) {
25058
25070
  return false;
25059
25071
  }
25060
25072
  if (classification.category === "rate_limit") {
25061
- const state2 = retryStates.get(sessionID) ?? { attempt: 0, lastAttemptTime: Date.now() };
25062
- const decision = calculateRetryDelay(state2.attempt, config, classification.retryAfterMs);
25063
- if (decision.retryable && state2.attempt < config.max_retries_before_fallback) {
25064
- retryStates.set(sessionID, {
25065
- attempt: state2.attempt + 1,
25066
- lastAttemptTime: Date.now()
25067
- });
25068
- await new Promise((resolve8) => setTimeout(resolve8, decision.delay_ms));
25069
- return false;
25073
+ const effectiveAttempt = retryAttempt ?? retryStates.get(sessionID)?.attempt ?? 0;
25074
+ if (retryAttempt !== undefined) {
25075
+ if (effectiveAttempt >= config.max_retries_before_fallback) {
25076
+ retryStates.delete(sessionID);
25077
+ } else {
25078
+ return false;
25079
+ }
25080
+ } else {
25081
+ const state2 = retryStates.get(sessionID) ?? { attempt: 0, lastAttemptTime: Date.now() };
25082
+ const decision = calculateRetryDelay(state2.attempt, config, classification.retryAfterMs);
25083
+ if (decision.retryable && state2.attempt < config.max_retries_before_fallback) {
25084
+ retryStates.set(sessionID, {
25085
+ attempt: state2.attempt + 1,
25086
+ lastAttemptTime: Date.now()
25087
+ });
25088
+ await new Promise((resolve8) => setTimeout(resolve8, decision.delay_ms));
25089
+ return false;
25090
+ }
25091
+ retryStates.delete(sessionID);
25070
25092
  }
25071
- retryStates.delete(sessionID);
25072
25093
  }
25073
25094
  if (classification.category !== "quota" && classification.category !== "rate_limit") {
25074
25095
  return false;
@@ -25110,6 +25131,22 @@ function createRuntimeFallbackHook(ctx, options) {
25110
25131
  if (fallbackResult.kind !== "next") {
25111
25132
  return false;
25112
25133
  }
25134
+ const isRetryPartEvent = event.type === "message.part.updated" && retryAttempt !== undefined;
25135
+ if (isRetryPartEvent) {
25136
+ if (interruptingSessions.get(sessionID)) {
25137
+ return false;
25138
+ }
25139
+ interruptingSessions.set(sessionID, true);
25140
+ try {
25141
+ await ctx.client.session.abort({ path: { id: sessionID } });
25142
+ log("[runtime-fallback] aborted retry loop", { sessionID, retryAttempt });
25143
+ } catch (abortErr) {
25144
+ log("[runtime-fallback] abort failed, falling through to direct prompt", {
25145
+ sessionID,
25146
+ error: String(abortErr)
25147
+ });
25148
+ }
25149
+ }
25113
25150
  try {
25114
25151
  await ctx.client.session.prompt({
25115
25152
  path: { id: sessionID },
@@ -25127,6 +25164,10 @@ function createRuntimeFallbackHook(ctx, options) {
25127
25164
  { model: fallbackResult.model, error: classifyProviderError(fallbackError) }
25128
25165
  ]);
25129
25166
  return false;
25167
+ } finally {
25168
+ if (isRetryPartEvent) {
25169
+ interruptingSessions.delete(sessionID);
25170
+ }
25130
25171
  }
25131
25172
  };
25132
25173
  return { handler };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@skj1724/oh-my-opencode",
3
- "version": "3.19.12",
3
+ "version": "3.19.14",
4
4
  "description": "The Best AI Agent Harness - Batteries-Included OpenCode Plugin with Multi-Model Orchestration, Parallel Background Agents, and Crafted LSP/AST Tools",
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",