{"record":{"id":"e008fc1d6154cb1e","repo":"siyuan-note/siyuan","slug":"version-request-returned-http-response-status","errorCode":null,"errorMessage":"version request returned HTTP \" + response.status","messagePattern":"version request returned HTTP \" \\+ response\\.status","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"app/electron/main.js","lineNumber":2585,"sourceCode":"const fetchWithTimeout = async (url, options = {}, timeout = 5000) => {\n    const abortController = new AbortController();\n    const timer = setTimeout(() => abortController.abort(), timeout);\n    try {\n        return await session.defaultSession.fetch(url, Object.assign({\n            credentials: \"include\",\n            bypassCustomProtocolHandlers: true,\n            redirect: \"manual\",\n        }, options, {signal: abortController.signal}));\n    } finally {\n        clearTimeout(timer);\n    }\n};\n\nconst requestRemoteKernelVersion = async (target) => {\n    const response = await fetchWithTimeout(target.origin + \"/api/system/version\", {method: \"GET\"});\n    if (!response.ok) {\n        await response.body?.cancel();\n        throw new Error(\"version request returned HTTP \" + response.status);\n    }\n    return response.json();\n};\n\nconst isRemoteKernelAuthenticated = async (target) => {\n    const response = await fetchWithTimeout(target.origin + \"/stage/build/app/\", {\n        method: \"GET\",\n        redirect: \"manual\",\n    });\n    if (response.status === 401 || response.status >= 300 && response.status < 400) {\n        await response.body?.cancel();\n        return false;\n    }\n    if (!response.ok) {\n        await response.body?.cancel();\n        throw new Error(\"authentication probe returned HTTP \" + response.status);\n    }\n    await response.body?.cancel();","sourceCodeStart":2567,"sourceCodeEnd":2603,"githubUrl":"https://github.com/siyuan-note/siyuan/blob/8641553a1f07374001902d3ce773285db1292b2d/app/electron/main.js#L2567-L2603","documentation":"requestRemoteKernelVersion fetches /api/system/version from a remote kernel target and throws when the HTTP response is not ok (non-2xx). This is the connectivity/health probe for connecting to a kernel hosted on another machine.","triggerScenarios":"fetchWithTimeout(target.origin + \"/api/system/version\", {method: \"GET\"}) resolves but response.ok is false — e.g. 404 because the URL is not a SiYuan kernel, 401/403 from auth, 502/503 from a reverse proxy, or 500 from a broken kernel.","commonSituations":"Typing a --remote URL that points at a non-SiYuan web server; remote kernel behind a proxy that rewrites paths; the remote kernel is down or restarting; firewall/WAF returning 403; wrong port in the URL.","solutions":["Verify the remote kernel is running and reachable by opening target.origin in a browser","Confirm the URL points to a SiYuan kernel root (the /api/system/version endpoint must exist)","Check the HTTP status in the message: 401/403 means auth/proxy issues, 5xx means the remote server or proxy is unhealthy","If behind a reverse proxy, ensure /api/* is forwarded unchanged to the kernel port"],"exampleFix":"// before\n//   const url = \"https://myserver:80/siyuan\";\n// after (point at the kernel origin root, correct port)\n//   const url = \"https://myserver:6806\";","handlingStrategy":"try-catch","validationCode":"if _, err := json.Marshal(Conf.NotebookCrypto); err != nil {\n    // config struct not serializable; do not attempt backup save\n}\n","typeGuard":null,"tryCatchPattern":"if err := saveNotebookCryptoBackup(kek); err != nil {\n    if strings.Contains(err.Error(), \"marshal notebook crypto backup failed\") {\n        // inspect wrapped inner error; suspect struct/marshaler changes\n    }\n}\n","preventionTips":["Keep conf.NotebookCrypto limited to JSON-serializable fields","Avoid custom MarshalJSON overrides on crypto config structs"],"tags":["network","http","remote-kernel","health-check"],"backgroundTag":"http-error-response","analyzedSha":"8641553a1f07374001902d3ce773285db1292b2d","analyzedAt":"2026-09-11T16:08:28.414Z","contentChangedAt":"2026-09-11T16:08:28.414Z","schemaVersion":2},"datasetVersion":"2026-09-14T00:17:10.932Z"}