json_table函数需mysql 8.0.4+,核心结构为json_table(json_doc, path columns(...)),必须指定路径(如$[*])、列名、类型及path表达式,嵌套数组需lateral关联子json_table。

JSON_TABLE函数的基本用法和必要参数
MySQL 8.0.4+ 才支持 JSON_TABLE,低于这个版本会直接报错 FUNCTION JSON_TABLE does not exist。它不是简单把 JSON 字符串“展开”,而是需要显式声明列名、类型、路径和提取逻辑,漏掉任意一个都会语法报错。
核心结构必须包含三部分:JSON_TABLE( json_doc, path COLUMNS ( ... ) )。其中 json_doc 是合法 JSON(字符串或字段),path 必须是数组路径(如 $[*]),COLUMNS 里每列需指定 FOR ORDINALITY 或 PATH + 类型转换。
常见错误:把对象数组写成 $(顶层对象)而不是 $[*](遍历数组元素);或者在 COLUMNS 中漏写 INT PATH "$.id" 这类完整声明,只写 id INT 会导致 Unknown column 'id' in 'field list'。
处理含嵌套对象的JSON数组
如果数组每个元素是对象(比如 [{"name":"a","tags":["x","y"]},{"name":"b","tags":["z"]}]),不能直接用 tags VARCHAR(100) PATH "$.tags" 拿到数组内容——那只会转成字符串 ["x","y"]。真要展开 tags 数组,得再套一层 JSON_TABLE,且外层必须用 LATERAL 关联。
实操要点:
- 外层
JSON_TABLE提取主对象字段(如name),并用id FOR ORDINALITY记录原始位置 - 内层
JSON_TABLE的json_doc必须是外层字段,例如t.tags,不能写死原 JSON 字符串 - 内层
path写$[*],否则只取第一个 tag - 必须加
LATERAL,否则 MySQL 报错Reference 't.tags' not supported (<code>LATERALrequired)
示例片段:
SELECT t.name, u.tag
FROM JSON_TABLE('[
{"name":"a","tags":["x","y"]},
{"name":"b","tags":["z"]}
]', '$[*]' COLUMNS (
name VARCHAR(10) PATH '$.name',
tags JSON PATH '$.tags'
)) AS t
LATERAL JSON_TABLE(t.tags, '$[*]' COLUMNS (tag VARCHAR(10) PATH '$')) AS u;
性能和数据类型注意事项
JSON_TABLE 是逐行解析,不走索引,大数据量时比预建关系表慢一个数量级。别指望它替代规范化设计。
类型转换要小心:VARCHAR(N) 超出长度会截断,INT PATH "$.id" 遇到非数字字符串(如 "id": "abc")直接转成 0,不会报错;想捕获异常得配合 JSON_VALID() 预检。
空值处理:路径不存在时默认为 NULL,但若声明了 NOT NULL(如 name VARCHAR(10) NOT NULL PATH '$.name'),整行会被过滤掉——这点容易被忽略,导致结果行数少于预期。
另外,JSON_EXTRACT 和 -> 操作符返回的是 JSON 类型,而 JSON_TABLE 的 PATH 表达式里必须用字符串字面量(如 '$.name'),不能拼接变量,动态路径只能靠预处理生成 SQL。
调试 JSON_TABLE 的常见卡点
最常卡在 JSON 格式非法:MySQL 对 JSON 要求严格,末尾多逗号、单引号代替双引号、键名没引号都会让整个 JSON_TABLE 返回空结果,且无明确错误提示。先用 SELECT JSON_VALID('your_json') 确认返回 1。
路径表达式大小写敏感,$.Name 和 $.name 是不同字段;数组索引从 0 开始,$[0] 只取首项,$[*] 才遍历全部。
如果结果为空但 JSON 和路径都确认无误,检查是否用了保留字当列名(如 order、group),必须用反引号包裹:`order` VARCHAR(10) PATH '$.order'。
最后提醒:MySQL 的 JSON 函数不支持正则匹配路径,也无法按条件过滤数组元素(比如只取 status="active" 的对象),这类需求得先用 JSON_SEARCH 或应用层筛一遍。











