json_table是oracle 12c+解析json数组最可靠的方式,必须在from子句中作为表源使用,不能在select列表中直接调用;路径中数组须显式写[*],嵌套数组推荐用nested path(12.2+)或双层json_table(12.1),pl/sql中则需用json_array_t类处理。

JSON_TABLE 是 Oracle 12c+ 解析 JSON 数组最可靠的方式,但必须写对语法结构——它不是函数调用,而是必须出现在 FROM 子句里的表源。
JSON_TABLE 必须配合 FROM 使用,不能当普通函数调用
常见错误是把 JSON_TABLE 当成 JSON_VALUE 那样直接在 SELECT 列表里用,结果报 ORA-00903:invalid table name。它本质是一个“横向表生成器”,只能在 FROM 中和主表做隐式 lateral join。
- 正确写法:
SELECT jt.name FROM t1, JSON_TABLE(t1.json_col, '$.items[*]' COLUMNS (name VARCHAR2(50) PATH '$.name')) jt - 错误写法:
SELECT JSON_TABLE(json_col, '$.items[*]') FROM t1(语法不合法) - 路径中数组必须显式写
[*],写成$.items只会取第一个元素,且不报错、只静默截断 - 如果 JSON 字段是
CLOB或含空格/特殊字符的键名,路径要用双引号:如$.["order id"]
嵌套数组展开必须用 NESTED PATH 或双层 JSON_TABLE
遇到 {"orders":[{"id":1,"items":[{"sku":"A"},{"sku":"B"}]}]} 这类结构,想展开成每行一个 sku 并带上 order.id,单层 JSON_TABLE 会触发笛卡尔积。
- 推荐写法(12.2+):
JSON_TABLE(json_col, '$.orders[*]' COLUMNS (order_id NUMBER PATH '$.id', NESTED PATH '$.items[*]' COLUMNS (sku VARCHAR2(10) PATH '$.sku'))) - 兼容写法(12.1):外层查
orders,再用第二层JSON_TABLE对jt1.items字段再次解析 -
NESTED PATH必须写在COLUMNS内部,不能放在外层路径上 - 某 order 的
items是空数组或null时,默认该 order 下无记录;需加NULL ON EMPTY才保留 order 行
PL/SQL 中处理 JSON 数组得靠 JSON_ARRAY_T,索引从 0 开始
在存储过程里遍历 JSON 数组,不能用 SQL 的 JSON_TABLE,而要用 JSON_ARRAY_T 类型及其方法——它的索引规则和 PL/SQL 集合不同,容易越界。
- 构造数组:
v_arr := JSON_ARRAY_T('[{"id":1},{"id":2}]'); - 遍历必须写
FOR i IN 0 .. v_arr.get_size() - 1,写成1 .. v_arr.get_size()会漏掉首项、越界取NULL - 取对象:
v_obj := JSON_OBJECT_T(v_arr.get(i));,再用v_obj.get_string('id') - 默认出错返回
NULL,不抛异常;要捕获错误,先调v_obj.on_error(1) - 修改后转回字符串:
v_arr.to_string(),注意结果含换行缩进,如需紧凑格式得手动REPLACE
嵌套层级深、字段名大小写混用、数组路径漏写 [<em>]</em> —— 这三处最容易导致查询返回空结果却不报错,调试时建议先用 SELECT FROM DUAL WHERE '<your_json>' IS JSON;</your_json> 验证合法性,再逐层简化路径测试。










