使用多个 JSON path 删除嵌套对象成员并保持剩余文档结构
如果只想从 MySQL 的 JSON 列里删除多个嵌套对象成员,直接把多个 JSON path 依次传给 JSON_REMOVE() 即可。关键是每个 path 都定位到要删除的叶子成员,并注意参数按从左到右处理:前一个 path 修改后的文档,会成为后一个 path 的输入。这样既能清理指定字段,也能保留父对象和其它同级字段。
官方文档地址:https://dev.mysql.com/doc/refman/8.4/en/json-modification-functions.html
推荐采用“先 SELECT 预览结果,再用主键限定 UPDATE”的生产写法。不要传根路径 $,也不要把父对象当成叶子成员删除;不存在的成员不会报错,但会让这条 path 对文档没有影响。
一、先把生产目标收窄到叶子成员
假设表中有一个 profile_json JSON 列,文档结构如下:
-- 这份样例同时保留联系信息、偏好设置和不应被删除的字段
SET @profile = '{
"profile": {"display_name": "Lin", "phone": "13800000000", "region": "华东"},
"preferences": {"debug": true, "theme": "dark"},
"member_level": "pro"
}';
本次需求是删除 profile.phone 和 preferences.debug,而 profile.display_name、profile.region、preferences.theme 以及根部的 member_level 都要保留。因此目标 path 是 $.profile.phone 与 $.preferences.debug,而不是 $.profile 或 $。

二、准备路径清单并先预览结果
JSON_REMOVE(json_doc, path[, path] ...) 返回修改后的 JSON 文档。传入的文档必须是有效 JSON;任意参数为 SQL NULL 时结果为 NULL;path 不能是根路径 $,也不能含 * 或 ** 通配符。对象成员不存在时不是错误,这个 path 会被忽略。
-- 先只计算新文档,不改变表数据,便于人工确认删除边界 SELECT JSON_REMOVE( @profile, '$.profile.phone', '$.preferences.debug' ) AS preview_json;
预览结果应当只移除两个成员,父对象仍然存在:
{"profile": {"display_name": "Lin", "region": "华东"}, "preferences": {"theme": "dark"}, "member_level": "pro"}
这一步还可以发现路径拼写问题。例如把 $.preferences.debug 写成不存在的 $.preference.debug,函数不会把它当成语法错误,也不会删除其它字段,所以生产脚本应把路径清单作为变更记录的一部分。
三、多个 path 为什么必须考虑从左到右
MySQL 会按参数出现的顺序处理 path。每次修改生成的新文档,会继续作为下一个 path 的输入。删除两个互不相干的叶子成员时,顺序通常不会改变结果;但如果先删除父对象,后面的嵌套 path 就失去匹配对象。
-- 正确:两个 path 都指向独立的叶子成员,剩余结构仍然完整 SELECT JSON_REMOVE( @profile, '$.profile.phone', '$.preferences.debug' ) AS cleaned_json; -- 有风险:先删掉 profile,后面的 profile.phone 已经没有匹配对象 SELECT JSON_REMOVE( @profile, '$.profile', '$.profile.phone' ) AS parent_first_json;
第二种写法不会报错,但它表达的是“删除整个 profile”,不是“删除 profile 里的一个成员”。如果业务要求保留父对象,路径清单应只允许叶子成员;如果确实要删除整个对象,也应在发布单中明确写出这个更大的影响范围。

四、生产 UPDATE 的权限、审计与发布检查
确认预览结果后,再把同一个表达式放进限定主键的 UPDATE。对于批量清理,不要省略 WHERE,也不要把“路径不存在不会报错”误当成“所有行都已经完成清理”。
-- 只更新指定记录,并跳过 SQL NULL,避免把文档结果写成 NULL START TRANSACTION; UPDATE customer_profile SET profile_json = JSON_REMOVE( profile_json, '$.profile.phone', '$.preferences.debug' ) WHERE id = 1001 AND profile_json IS NOT NULL; -- 发布前读取同一条记录,确认目标字段已移除、其它字段仍在 SELECT id, profile_json FROM customer_profile WHERE id = 1001; -- 应用层审计完成后再提交;发现范围不对就回滚 COMMIT;
权限上只给执行该表更新所需的最小权限,并把主键范围、path 清单、预览结果和影响行数写入变更记录。若需要清理多行,可以先按主键分批生成预览,再在同一事务策略下执行;不要用一个没有过滤条件的更新语句测试路径。
这里的 profile_json IS NOT NULL 只是在 SQL 层排除空列。JSON 文档里的 JSON null 与 SQL NULL 不是同一概念,处理前应按业务字段约定区分。
相关问题
删除路径不存在时会失败吗?
不会。只要 JSON 文档和 path 本身合法,目标成员不存在时该 path 对文档没有影响;因此仍应通过预览和审计记录确认实际清理范围。
为什么不直接删除整个嵌套对象?
删除父对象会连同其中所有成员一起消失。需要保持剩余文档结构时,应使用指向具体对象成员的 path,并把父对象先删除的写法视为不同的变更。
小结:多成员清理的核心不是把 path 写得越多越好,而是让每个 path 都有明确边界;先预览、再按从左到右规则检查,最后用主键和事务策略发布。
解释 interleaved 模式下并发语句预分配自增值和编号间隔的关系
- 上一篇
- 解释 interleaved 模式下并发语句预分配自增值和编号间隔的关系
- 下一篇
- 用 JSON_TYPE 在触发器或查询中区分对象、数组和基础标量
-
- 数据库 · MySQL | 31分钟前 | MySQL · 执行计划 · 索引优化 · mysql Update explain Index Condition Pushdown
- 区分 UPDATE 必须读取并修改完整记录与 SELECT 的索引条件下推显示
- 205浏览 收藏
-
- 数据库 · MySQL | 34分钟前 |
- 用左前缀分组索引配合 MIN 直接取得每组最小值
- 203浏览 收藏
-
- 数据库 · MySQL | 1天前 | MySQL · mysql Performance Schema SET RESOURCE GROUP
- MySQL SET RESOURCE GROUP怎样把指定线程切换到目标资源组
- 291浏览 收藏
-
- 数据库 · MySQL | 1天前 |
- MySQL clone plugin怎样复制实例用于测试环境
- 260浏览 收藏
-
- 数据库 · MySQL | 1天前 | MySQL · 权限管理 ·
- MySQL roles怎样为只读账号组合最小权限
- 368浏览 收藏
-
- 数据库 · MySQL | 1天前 | MySQL · 空间计算 MySQL GIS ST_Distance_Sphere 经纬度距离
- MySQL GIS ST_Distance_Sphere怎样计算经纬度近似距离
- 148浏览 收藏
-
- 数据库 · MySQL | 1天前 | mysql JSON_TABLE JSON查询 ON EMPTY ON ERROR JSON null EXISTS PATH
- MySQL JSON_TABLE怎样把缺失字段和 JSON null 区分开
- 102浏览 收藏
-
- 数据库 · MySQL | 1天前 |
- MySQL recursive CTE怎样限制递归查询深度
- 137浏览 收藏
-
- 数据库 · MySQL | 1天前 |
- MySQL window function怎样在分组内取第二条记录
- 488浏览 收藏
-
- 数据库 · MySQL | 1天前 |
- MySQL optimizer_trace怎样读取一次查询的优化决策
- 152浏览 收藏
-
- 前端进阶之JavaScript设计模式
- 设计模式是开发人员在软件开发过程中面临一般问题时的解决方案,代表了最佳的实践。本课程的主打内容包括JS常见设计模式以及具体应用场景,打造一站式知识长龙服务,适合有JS基础的同学学习。
- 543次学习
-
- GO语言核心编程课程
- 本课程采用真实案例,全面具体可落地,从理论到实践,一步一步将GO核心编程技术、编程思想、底层实现融会贯通,使学习者贴近时代脉搏,做IT互联网时代的弄潮儿。
- 516次学习
-
- 简单聊聊mysql8与网络通信
- 如有问题加微信:Le-studyg;在课程中,我们将首先介绍MySQL8的新特性,包括性能优化、安全增强、新数据类型等,帮助学生快速熟悉MySQL8的最新功能。接着,我们将深入解析MySQL的网络通信机制,包括协议、连接管理、数据传输等,让
- 500次学习
-
- JavaScript正则表达式基础与实战
- 在任何一门编程语言中,正则表达式,都是一项重要的知识,它提供了高效的字符串匹配与捕获机制,可以极大的简化程序设计。
- 487次学习
-
- 从零制作响应式网站—Grid布局
- 本系列教程将展示从零制作一个假想的网络科技公司官网,分为导航,轮播,关于我们,成功案例,服务流程,团队介绍,数据部分,公司动态,底部信息等内容区块。网站整体采用CSSGrid布局,支持响应式,有流畅过渡和展现动画。
- 485次学习
-
- PubMedQA
- 深入了解PubMedQA生物医学问答数据集,涵盖其核心功能、使用方法及在临床决策、药物研发等场景的应用,助力提升NLP模型性能。
- 893次使用
-
- H2O EvalGPT
- H2O EvalGPT是H2O.ai推出的开源LLM评估平台,提供详细的大模型性能排行榜、行业特定基准测试及A/B测试功能,助您快速选择最适合项目的高性能大语言模型。
- 894次使用
-
- LMArena
- LMArena是加州大学伯克利分校推出的AI模型匿名评测平台。通过盲测投票机制,用户可对比不同大模型回答并生成实时排行榜,助力开发者优化模型及用户选择最佳AI工具。
- 978次使用
-
- HELM
- 深入了解斯坦福推出的HELM(Holistic Evaluation of Language Models)大模型评测体系。本文解析其核心功能、安装配置步骤及应用场景,涵盖准确性、公平性、鲁棒性等多维度指标,助力开发者全面优化语言模型性能。
- 965次使用
-
- MMBench
- MMBench是由上海人工智能实验室等机构联合推出的多模态基准测试平台,提供细粒度能力评估、大规模数据集及VLMEvalKit工具。本文详细介绍其核心功能、安装使用方法及应用场景,助力开发者全面评估多模态模型性能。
- 791次使用
-
- MySQL数据清理的需求分析和改进
- 2023-01-24 479浏览
-
- MySQL 8.4 写入一抖就怪磁盘?先把 redo log 容量和检查点看明白
- 2026-06-02 382浏览
-
- MySQL 不可见索引实战:想删索引又怕翻车,先做一次生产级预演
- 2026-06-02 388浏览
-
- MySQL 8.4 直方图实战:同一条 SQL 有时快有时慢,先查列分布统计
- 2026-06-02 419浏览
-
- MySQL 8.4 连接池雪崩实战:Too many connections 不是把 max_connections 调大就完事
- 2026-06-05 491浏览

