jackwener/OpenCLI · error · CommandExecutionError

${label} returned an unexpected response

Error message

${label} returned an unexpected response

What it means

postJikeApi validates the shape of the outcome returned by its internal fetch wrapper. If the outcome is not of kind 'response' or its status is not an integer, the contract between the wrapper and the parser is broken, so it throws CommandExecutionError('... returned an unexpected response'). This is a defensive invariant check for malformed or unclassified outcomes.

Source

Thrown at clis/jike/utils.js:85

      } catch (error) {
        return { kind: 'json', status: response.status, detail: String(error?.message || error) };
      }
      return { kind: 'response', status: response.status, body };
    } catch (error) {
      return { kind: 'transport', detail: String(error?.message || error) };
    }
  })()`);
  if (outcome?.kind === 'auth' || outcome?.status === 401 || outcome?.status === 403) {
    throw new AuthRequiredError('web.okjike.com', outcome?.detail || `${label} returned HTTP ${outcome?.status}`);
  }
  if (outcome?.kind === 'transport') {
    throw new CommandExecutionError(`${label} request failed: ${outcome.detail}`);
  }
  if (outcome?.kind === 'json') {
    throw new CommandExecutionError(`${label} returned invalid JSON: ${outcome.detail}`);
  }
  if (outcome?.kind !== 'response' || !Number.isInteger(outcome.status)) {
    throw new CommandExecutionError(`${label} returned an unexpected response`);
  }
  if (outcome.status < 200 || outcome.status >= 300) {
    throw new CommandExecutionError(`${label} returned HTTP ${outcome.status}`);
  }
  return outcome.body;
}

/**
 * 注入浏览器 evaluate 的 JS 函数字符串。
 * 从 React fiber 树中向上最多走 10 层,找到含 id 字段的 props.data。
 */
export const getPostDataJs = `
function getPostData(element) {
  for (const key of Object.keys(element)) {
    if (key.startsWith('__reactFiber$') || key.startsWith('__reactInternalInstance$')) {
      let fiber = element[key];
      for (let i = 0; i < 10 && fiber; i++) {
        const props = fiber.memoizedProps || fiber.pendingProps;

View on GitHub (pinned to 49907e53dc)

Solutions

  1. Inspect the raw outcome shape in the fetch wrapper (clis/jike/utils.js) to see which kind it produced
  2. Add a handler for the unhandled kind in postJikeApi, or fix the wrapper to always classify outcomes
  3. Update to the latest CLI version in case this is a known wrapper bug
  4. Log the full outcome object (JSON.stringify) before this branch to diagnose
  5. If triggered by a patched/hooked fetch environment, test in a clean environment

Example fix

// before (wrapper returns an unclassified kind)
return { kind: 'redirect', location: res.headers.get('location') };
// after
classify: follow the redirect inside the wrapper and return { kind: 'response', status, body };
Defensive patterns

Strategy: type-guard

Type guard

function isWellFormedOutcome(outcome) {
  return outcome != null && typeof outcome === 'object' &&
    (outcome.kind === 'response' || outcome.kind === 'transport' || outcome.kind === 'json' || outcome.kind === 'auth') &&
    (outcome.kind !== 'response' || Number.isInteger(outcome.status));
}

Try / catch

try {
  const body = await body('postJikeApi', path, payload);
} catch (err) {
  if (err instanceof CommandExecutionError && /unexpected response/.test(err.message)) {
    console.error('postJikeApi contract violated — inspect outcome from fetch wrapper', err);
  }
  throw err;
}

Prevention

When it happens

Trigger: The internal outcome object from the fetch wrapper is undefined, has an unknown kind value, or carries a non-integer/missing status — e.g. a wrapper bug, an unhandled response type, or the outcome object being corrupted/constructed incorrectly.

Common situations: A code change in the fetch wrapper introduced a new outcome kind not handled by postJikeApi; an unexpected runtime result (e.g. evaluate returning undefined); version drift between the wrapper and API helper.

Related errors


AI-assisted analysis of jackwener/OpenCLI@49907e53dc (2026-08-29). Data as JSON: /api/errors/121372991b3bd171. Report an issue: GitHub.