基于元素名称过滤深度嵌套JSON数组项及修改属性值的JavaScript实现问询
解决深层嵌套JSON的过滤与属性修改问题
嘿,作为JS新手能想到用splice已经很棒了!不过针对这种深层嵌套的结构,我们可以用更直观安全的方法来处理,同时确保不会误改其他类似结构的内容。下面一步步帮你实现需求:
核心思路
我们需要精准定位到目标数组,然后分两步处理:过滤不需要的项,再修改剩余项的visible属性。全程只操作你指定的levelOneB下的contents数组,不会影响其他结构。
步骤1:编写JSON处理函数
先写一个专门处理目标JSON的函数,这样可以复用,也避免误改其他数据:
function processTargetJson(jsonData) { // 1. 精准定位到目标contents数组(加存在性检查,避免层级不存在报错) const targetContents = jsonData?.levelOneB?.levelOneBDeepBro?.levelOneBDeepBroTabs?.[0]?.levelOneBDeepBroTabsShaper?.daContent?.daContentShaper?.contents; if (!targetContents || !Array.isArray(targetContents)) { console.log("目标数组不存在,直接返回原数据"); return jsonData; } // 2. 过滤数组:移除包含contentTypeA或ahThisIsTheBContent的项 const filteredContents = targetContents.filter(item => { const content = item?.contentItem?.content; if (!content) return true; // 无content的项默认保留(可根据需求调整) // 检查是否包含要移除的属性 const hasContentTypeA = 'contentTypeA' in content; const hasBContent = 'ahThisIsTheBContent' in content; return !hasContentTypeA && !hasBContent; // 只保留不满足移除条件的项 }); // 3. 修改剩余项的visible属性:把false改成true filteredContents.forEach(item => { const content = item?.contentItem?.content; if (!content) return; // 遍历content下的所有子对象(兼容contentTypeB/C等动态键名) Object.values(content).forEach(contentObj => { if (contentObj.hasOwnProperty('visible') && contentObj.visible === false) { contentObj.visible = true; } }); }); // 将处理后的数组替换回原JSON结构 jsonData.levelOneB.levelOneBDeepBro.levelOneBDeepBroTabs[0].levelOneBDeepBroTabsShaper.daContent.daContentShaper.contents = filteredContents; return jsonData; }
代码细节解释:
- 可选链保护:用
?.避免因某个层级不存在导致的报错,新手写代码一定要加这个保险! - 过滤逻辑:用
filter替代splice,因为filter返回新数组,不会直接修改原数组,更安全易调试;用in操作符判断属性存在性,比直接访问更可靠。 - 动态修改属性:用
Object.values(content)遍历content下的所有子对象,不管键名是contentTypeB还是C,都能找到并修改visible属性。
步骤2:在浏览器扩展中介入流程
因为你要通过浏览器扩展修改原页面的JSON数据,常见的两种介入方式:
方式1:拦截Fetch请求
如果原页面用fetch获取JSON,可在扩展的content script中重写fetch方法,拦截请求并修改返回结果:
// content script中注入 const originalFetch = window.fetch; window.fetch = async (...args) => { const response = await originalFetch(...args); // 只处理目标接口(根据实际URL关键词调整) if (response.url.includes('目标接口的URL关键词')) { const json = await response.json(); // 调用处理函数修改数据 const processedJson = processTargetJson(json); // 构造新响应返回给原页面 return new Response(JSON.stringify(processedJson), { headers: response.headers, status: response.status, statusText: response.statusText }); } return response; };
方式2:修改原页面全局数据
如果原页面把JSON存在全局变量(比如window.pageData),可监听变量变化或定时检查修改:
// content script中注入 setInterval(() => { if (window.pageData) { window.pageData = processTargetJson(window.pageData); // 若原页面有渲染函数,可触发重新渲染 if (window.renderPage) window.renderPage(); } }, 500);
关键注意事项
- 路径精准匹配:确保目标路径和原页面JSON结构完全一致;如果
levelOneBDeepBroTabs有多个元素,要把[0]改成遍历整个数组! - 隔离其他结构:我们的函数只修改指定路径下的数组,其他类似结构(比如
levelOneA里的数组)完全不会被影响。 - 调试技巧:先在浏览器控制台打印
targetContents,确认找到的是正确数组后再执行后续操作,出错时能快速定位问题。
内容的提问来源于stack exchange,提问作者Eliot
相关产品推荐
相关产品推荐

