{"record":{"id":"280ccb5fffdb0cc4","repo":"jackwener/OpenCLI","slug":"error-280ccb","errorCode":null,"errorMessage":"解析到的字幕列表对象不符合数组格式","messagePattern":"解析到的字幕列表对象不符合数组格式","errorType":"exception","errorClass":"CommandExecutionError","httpStatus":null,"severity":"error","filePath":"clis/bilibili/subtitle.js","lineNumber":121,"sourceCode":"         }\n      })()\n    `;\n        let items;\n        try {\n            items = await page.evaluate(fetchJs);\n        }\n        catch (err) {\n            throw new CommandExecutionError(`字幕获取失败: ${err?.message || err}`);\n        }\n        if (items?.error) {\n            throw new CommandExecutionError(`字幕获取失败: ${items.error}${items.text ? ' — ' + items.text : ''}`);\n        }\n        if (!items || typeof items !== 'object' || items.success !== true) {\n            throw new CommandExecutionError('字幕获取结果对象不符合预期格式');\n        }\n        const finalItems = items.data;\n        if (!Array.isArray(finalItems)) {\n            throw new CommandExecutionError('解析到的字幕列表对象不符合数组格式');\n        }\n        if (finalItems.length === 0) {\n            throw new EmptyResultError('bilibili subtitle', '字幕文件中没有字幕片段。');\n        }\n        // 5. 数据映射\n        return finalItems.map((item, idx) => {\n            const from = Number(item?.from);\n            const to = Number(item?.to);\n            if (!item || typeof item !== 'object' || !Number.isFinite(from) || !Number.isFinite(to)) {\n                throw new CommandExecutionError('字幕片段缺少有效 from/to 时间戳');\n            }\n            return {\n                index: idx + 1,\n                from: from.toFixed(2) + 's',\n                to: to.toFixed(2) + 's',\n                content: String(item.content ?? '')\n            };\n        });","sourceCodeStart":103,"sourceCodeEnd":139,"githubUrl":"https://github.com/jackwener/OpenCLI/blob/49907e53dc3ade5c223ff0c4c2c2785687cec4e6/clis/bilibili/subtitle.js#L103-L139","documentation":"A CommandExecutionError thrown when items.data (the parsed subtitle body from the CDN) is not an array. Bilibili subtitle JSON files normally contain a body array of cue objects; a non-array means the CDN returned something else (e.g. an error object or changed schema).","triggerScenarios":"The CDN subtitle JSON's relevant field is not an array — e.g. Bilibili renamed body→data or wrapped it, or the fetched JSON is actually an error payload that still passed earlier checks.","commonSituations":"Bilibili API/CDN format migration; fetching a JSON that is an auth/error response; ai-subtitle (智能字幕) files with a different structure than CC files.","solutions":["Inspect the fetched subtitle JSON to see its actual structure.","Update the CLI/library if Bilibili changed the subtitle file schema.","Try a non-AI CC subtitle (different --lang) to see if only AI subtitle files differ.","Report the raw JSON payload with a bug report if the schema changed upstream."],"exampleFix":null,"handlingStrategy":"type-guard","validationCode":"// If you fetch the subtitle JSON yourself first:\nconst body = json.body ?? json.data;\nif (!Array.isArray(body)) throw new Error('subtitle cues not an array');","typeGuard":"const isCueList = (d) => Array.isArray(d) && d.every(c => c && typeof c === 'object');","tryCatchPattern":"try {\n  await run('bilibili subtitle', { url });\n} catch (e) {\n  if (/不符合数组格式/.test(e.message)) throw new Error('Bilibili subtitle JSON schema changed; inspect raw CDN payload.');\n  throw e;\n}","preventionTips":["Pin/monitor library versions against Bilibili format changes.","Inspect the raw subtitle JSON when this fires.","Try alternative tracks via --lang to isolate schema differences."],"tags":["bilibili","subtitle","schema","json"],"backgroundTag":"schema-validation-failed","analyzedSha":"49907e53dc3ade5c223ff0c4c2c2785687cec4e6","analyzedAt":"2026-08-29T08:14:47.543Z","schemaVersion":2},"datasetVersion":"2026-08-29T12:17:43.993Z"}