jackwener/OpenCLI · error · CommandExecutionError
Zhihu answer download request failed: ${error instanceof Err
Error message
Zhihu answer download request failed: ${error instanceof Error ? error.message : String(error)} What it means
extractAnswer runs an in-page evaluate that fetches the Zhihu v4 answer API (with credentials) and normalizes the returned content HTML. If that whole evaluate script rejects — the browser context threw, the bridge connection broke, or serialization failed — the .catch rethrows it as a CommandExecutionError with a 'try again later / rerun with -v' hint. Note that in-page fetch/JSON errors are deliberately caught inside the script and returned as status/errorCode/malformed fields instead, so this wrapper indicates an evaluate-level failure, not an HTTP error.
Source
Thrown at clis/zhihu/download-helpers.js:197
const errorCode = payload.error?.code ?? '';
const errorMessage = payload.error?.message || payload.error_msg || payload.message || '';
const needLogin = payload.error?.need_login === true || payload.need_login === true;
if (!response.ok || errorCode || errorMessage || needLogin) {
return { status: response.status, errorCode, errorMessage, needLogin };
}
if (typeof payload.content !== 'string') return { malformed: true };
const normalized = ${normalize}(payload.content, document);
return { value: {
answerUrl: typeof payload.url === 'string' ? payload.url : '',
questionUrl: typeof payload.question?.url === 'string' ? payload.question.url : '',
title: typeof payload.question?.title === 'string' ? payload.question.title : '',
author: typeof payload.author?.name === 'string' ? payload.author.name : '',
createdTime: payload.created_time,
...normalized
} };
})()
`).catch((error) => {
throw new CommandExecutionError(
`Zhihu answer download request failed: ${error instanceof Error ? error.message : String(error)}`,
'Try again later or rerun with -v for more detail.',
);
});
const data = unwrapEvaluateResult(raw);
if (!data || typeof data !== 'object' || Array.isArray(data)) {
throw new CommandExecutionError('Zhihu answer download returned a malformed Browser Bridge payload');
}
const status = data.status;
if (String(data.errorCode) === '40362') {
throw new CommandExecutionError(
`Zhihu risk control blocked answer ${target.answerId} (40362): ${data.errorMessage || 'abnormal request'}`,
'Open the answer in the connected Chrome profile and retry later.',
);
}
if (status === 401 || status === 403 || String(data.errorCode) === '40353' || data.needLogin) {
throw new AuthRequiredError('www.zhihu.com', 'Failed to download Zhihu answer');View on GitHub (pinned to 49907e53dc)
Solutions
- Retry the command after a short wait — transient bridge/page instability is the usual cause.
- Rerun with -v (verbose) to see the underlying evaluate error as the remediation hint suggests.
- Reconnect the Browser Bridge / relaunch Chrome if the tab was lost, then retry.
- Check page stability first: ensure no pending navigation or captcha wall on the answer page before calling.
Example fix
// before
const data = await extractAnswer(page, target);
// after
try {
const data = await extractAnswer(page, target);
} catch (err) {
if (/download request failed/.test(err.message)) {
await sleep(5000); // hint says: try again later
return extractAnswer(page, target);
}
throw err;
} Defensive patterns
Strategy: retry
Validate before calling
// ensure the page is stable and still on the answer before evaluating
const url = await page.getCurrentUrl();
if (!url || !url.includes('/answer/')) {
throw new Error('page not on an answer; re-navigate before extraction');
} Try / catch
try {
const data = await extractAnswer(page, target);
} catch (err) {
if (String(err.message).startsWith('Zhihu answer download request failed')) {
// library hint: try again later; retry with backoff and verbose logging
await sleep(5000);
return extractAnswer(page, target);
}
throw err;
} Prevention
- Retry with backoff — the built-in hint explicitly says 'try again later'
- Run with -v during development to capture the underlying evaluate error
- Avoid concurrent downloads on one bridge tab; serialize extraction calls
- Reconnect the bridge if Chrome has been running for a long session
When it happens
Trigger: Calling extractAnswer when the page.evaluate promise rejects: the tab navigated or closed while fetch ran, the Browser Bridge connection dropped mid-request, a script-level exception escaped the internal try/catch blocks, or the evaluate result could not be marshaled back.
Common situations: Chrome closed or crashed during a long fetch; Zhihu risk control reloaded the page mid-call; network flakiness combined with bridge instability; very large answer content causing serialization issues in older bridge versions.
Related errors
- Failed to open Zhihu answer ${answerId}: ${err instanceof Er
- Zhihu answer detail request failed: ${err instanceof Error ?
- FETCH_ERROR
- archive search request failed: ${error?.message || error}
- archive wayback request failed: ${error?.message || error}
AI-assisted analysis of jackwener/OpenCLI@49907e53dc (2026-08-29).
Data as JSON: /api/errors/c0feaf547f37ec08.
Report an issue: GitHub.