Uint8数组转HTML后解析script内嵌套JSON报错,求解决方法
问题描述
我正在解析一个HTML文档的Uint8数组,文档内的script标签嵌套了需要解析的JSON数据,操作步骤如下:
- 将数组转为文本:
data = Buffer.from(str).toString('utf8')
- 提取script标签内的JSON字符串,得到类似内容:
... {"phrase":"Go to \"California\"","color":"red","html":"<div class=\"myclass\">Ok</div>"} ...
- 用replace方法清理字符串:
data = data.replace(/\\"/g, "\"").replace(/\\/g, "")
处理后得到:
{"phrase":"Go to "California"","color":"red","html":"<div class="myclass">Ok</div>"}
尝试用JSON.parse()解析时,因属性值包含未转义的引号报错。想了解是否能用正则进一步处理,或者有合适的库推荐?目前正在使用Cheerio,也可借助该工具解决问题。
解决方案
方法一:修正正则替换逻辑
你之前的替换错误删除了所有转义符,导致内部引号失去必要的转义。正确逻辑应该是先处理HTML实体转义,再保留JSON本身的转义规则:
// 先把HTML实体"转为普通引号 let cleanedData = data.replace(/"/g, '"'); // 尝试直接解析 try { const parsed = JSON.parse(cleanedData); console.log(parsed); } catch (e) { // 针对多余的转义反斜杠做处理,只清除引号前的无效反斜杠 cleanedData = cleanedData.replace(/\\(?=")/g, ''); const parsed = JSON.parse(cleanedData); console.log(parsed); }
方法二:Cheerio配合转义工具处理
利用Cheerio定位script标签,结合unescape-html处理HTML转义,再提取并修复JSON:
- 安装依赖:
npm install unescape-html
- 代码示例:
const cheerio = require('cheerio'); const unescape = require('unescape-html'); // 假设已将Uint8数组转为htmlText文本 const $ = cheerio.load(htmlText); // 定位目标script标签(可根据id/内容特征筛选) const scriptContent = $('script').text(); // 反转义HTML实体 const unescapedContent = unescape(scriptContent); // 提取script内的JSON片段(匹配跨行内容) const jsonMatch = unescapedContent.match(/\{.*\}/s); if (jsonMatch) { try { const parsedJson = JSON.parse(jsonMatch[0]); console.log(parsedJson); } catch (e) { // 修复内部未转义的引号 const fixedJson = jsonMatch[0].replace(/"([^"]*)"/g, (match, content) => { return `"${content.replace(/"/g, '\\"')}"`; }); const parsedJson = JSON.parse(fixedJson); console.log(parsedJson); } }
方法三:使用JSON修复库
如果正则处理复杂度高,可借助jsonrepair自动修复格式错误的JSON:
- 安装依赖:
npm install jsonrepair
- 代码示例:
const jsonrepair = require('jsonrepair'); // 传入有格式问题的JSON字符串 const brokenJson = '{"phrase":"Go to "California"","color":"red","html":"<div class="myclass">Ok</div>"}'; const fixedJson = jsonrepair(brokenJson); const parsed = JSON.parse(fixedJson); console.log(parsed);
内容的提问来源于stack exchange,提问作者good1492
相关产品推荐
相关产品推荐

