{"record":{"id":"4738d4e9482e1833","repo":"jackwener/OpenCLI","slug":"notebooklm-rpc","errorCode":"NOTEBOOKLM_RPC","errorMessage":"NotebookLM RPC failed${errorCode ? ` (code=${errorCode})` : ''}","messagePattern":"NotebookLM RPC failed(.+?)\\)` : ''\\}","errorType":"error_code","errorClass":"CliError","httpStatus":null,"severity":"error","filePath":"clis/notebooklm/rpc.js","lineNumber":160,"sourceCode":"export function extractNotebooklmRpcResult(rawBody, rpcId) {\n    const chunks = parseNotebooklmChunkedResponse(rawBody);\n    for (const chunk of chunks) {\n        if (!Array.isArray(chunk))\n            continue;\n        const items = Array.isArray(chunk[0]) ? chunk : [chunk];\n        for (const item of items) {\n            if (!Array.isArray(item) || item.length < 1)\n                continue;\n            if (item[0] === 'er') {\n                const errorCode = typeof item[2] === 'number'\n                    ? item[2]\n                    : typeof item[5] === 'number'\n                        ? item[5]\n                        : null;\n                if (errorCode === 401 || errorCode === 403) {\n                    throw new AuthRequiredError(NOTEBOOKLM_DOMAIN, `NotebookLM RPC returned auth error (${errorCode})`);\n                }\n                throw new CliError('NOTEBOOKLM_RPC', `NotebookLM RPC failed${errorCode ? ` (code=${errorCode})` : ''}`, 'Retry from an already logged-in NotebookLM session, or inspect the raw response with debug logging.');\n            }\n            if (item[0] === 'wrb.fr' && item[1] === rpcId) {\n                const payload = item[2];\n                if (typeof payload === 'string') {\n                    try {\n                        return JSON.parse(payload);\n                    }\n                    catch {\n                        throw new CliError('NOTEBOOKLM_RPC_SCHEMA', `NotebookLM RPC ${rpcId} returned malformed JSON`, 'Retry from the NotebookLM page; the internal RPC response shape may have changed.');\n                    }\n                }\n                return payload;\n            }\n        }\n    }\n    throw new CliError('NOTEBOOKLM_RPC_SCHEMA', `NotebookLM RPC ${rpcId} returned no matching response frame`, 'Retry from the NotebookLM page; the internal RPC response shape may have changed.');\n}\nexport async function fetchNotebooklmInPage(page, url, options = {}) {","sourceCodeStart":142,"sourceCodeEnd":178,"githubUrl":"https://github.com/jackwener/OpenCLI/blob/49907e53dc3ade5c223ff0c4c2c2785687cec4e6/clis/notebooklm/rpc.js#L142-L178","documentation":"When a batchexecute error frame's numeric code is anything other than 401/403 (or absent), extractNotebooklmRpcResult throws CliError code NOTEBOOKLM_RPC with the code interpolated when known. This covers server-side rejections of the RPC that are not auth problems — malformed request, unknown rpc id, server error, quota. The message advises retrying from a logged-in session and enabling debug logging to inspect the raw response.","triggerScenarios":"callNotebooklmRpc receives an error frame with errorCode like 400/404/429/500, or a non-numeric code, so the 401/403 branch is skipped and the generic NOTEBOOKLM_RPC CliError is thrown.","commonSituations":"NotebookLM changed or retired an internal RPC id (protocol drift); request payload shape invalid after a CLI/page version mismatch; server-side quota (429); transient 5xx during Google incidents.","solutions":["Retry the command — transient 5xx/429 errors often clear","Run with debug logging to capture the raw batchexecute response and the error code","Update the CLI: a changed internal RPC protocol usually means a client update is needed","Confirm the notebook id/URL passed to the command is valid and accessible"],"exampleFix":"// before (blind retry loop on any failure)\ntry { await rpc(); } catch { await rpc(); }\n// after (inspect code before deciding)\ntry { await rpc(); }\ncatch (e) {\n  if (e.code === 'NOTEBOOKLM_RPC' && /code=429/.test(e.message)) await sleep(backoff);\n  else throw e;\n}","handlingStrategy":"retry","validationCode":"// validate inputs that commonly cause non-auth RPC failures\nif (!notebookUrl.match(/https:\\/\\/notebooklm\\.google\\.com\\/notebook\\/[\\w-]+/)) {\n  throw new Error('Invalid notebook URL/id before issuing RPC');\n}","typeGuard":"function isNonAuthRpcError(e) {\n  return e instanceof Error && e.code === 'NOTEBOOKLM_RPC' && !/\\(40[13]\\)/.test(e.message);\n}","tryCatchPattern":"try {\n  result = await callNotebooklmRpc(page, rpcId, payload);\n} catch (e) {\n  if (isNonAuthRpcError(e) && /code=(429|5\\d\\d)/.test(e.message)) {\n    await sleep(backoff); // transient server-side; retry with backoff\n  } else throw e;\n}","preventionTips":["Retry transient codes (429/5xx) with exponential backoff","Update the CLI when errors persist — internal RPC ids change with frontend updates","Enable debug logging to capture raw responses and exact error codes"],"tags":["rpc","server-error","protocol","notebooklm"],"backgroundTag":"rpc-request-failed","analyzedSha":"49907e53dc3ade5c223ff0c4c2c2785687cec4e6","analyzedAt":"2026-08-29T08:14:47.543Z","schemaVersion":2},"datasetVersion":"2026-08-29T12:17:43.993Z"}