介绍


JsonPath是一种能够提取部分JSON文档属性、对象、数组的语法,支持条件过滤、数学运算、字符串处理等功能。JsonPath与JSON文档就像 XPath 表达式与 XML 文档结合使用一样。

由于 JSON 结构通常是匿名的,并不一定和XML一样具有“根成员对象”,因此 JsonPath假定分配$给外层对象的抽象名称。JsonPath由用点分隔的表达式段(操作符)组成。 操作符可以是一个简单的词,如 JSON 值名称、*,也可以是括在方括号 [ ] 中的更复杂的构造。 括号段前的分隔点是可选的,也可以省略。下面是几种JsonPath的提取JSON文档内容语法:

JsonPath 描述
$.object.name 返回object.name的内容。
$.object['name'] 返回object.name的内容。
$.object.['name'] 返回object.name的内容。
$.object.history.length() 返回object.history数组元素的个数。
$[?(@.name == 'Object')].price.first() 返回第一个名为'Object'的对象的价格字段。
$[?(@.price > 10)].length() 返回price大于10的对象个数。

Jayway JsonPathStefan Goessner JsonPath的Java实现,是用于读取JSON文档的Java DSL。本文主要通过Jayway JsonPath来简单介绍JsonPath的使用语法,通过真实报文案例来进行操作。

支持的操作符


操作符 描述
` 操作符
--- ---
查询的根节点对象,表示一个json的数据,可以是对象或数组
@ 当前节点对象
* 通配符,获取所有节点
.. 递归查找,查找所有层次的属性值
<name> 按名称匹配对象属性。
.<name> 按照名称查找子节点
['<name>','<name>',...] 可用查找多个节点
[<number>,<number>,...] 按索引匹配数组元素,可同时查找多个数组元素
[start:end] 按定义的范围匹配数组元素:

<start>- 要匹配的第一个索引(包括)。 如果未指定,则匹配从头开始的所有数组元素。 如果为负数,则指定从数组末尾开始的偏移量。

<end>- 要匹配的最后一个索引(不包括)。 如果未指定,则匹配所有数组元素到最后。 如果为负数,则指定从数组末尾开始的偏移量。 | | [?(<expression>)] | 过滤表达式可匹配对象/数组元素,表达式的结果必须为布尔值 |

可以通过在 JSONPath 中添加 ~ 后缀来提取匹配的元素名称。 它返回匹配对象的名称或匹配数组项的字符串格式的索引。

过滤操作符


操作符 描述
== 等于
!= 不等于
< 小于
<= 小于或等于
> 大于
>= 大于或等于
=~ 匹配正则表达式 [?(@.name =~ /foo.*?/i)]
in 包含 [?(@.size in ['S', 'M'])]
nin 不包含
subsetof 子集 [?(@.sizes subsetof ['S', 'M', 'L'])]
anyof 交集 [?(@.sizes anyof ['M', 'L'])]
noneof 不是交集 [?(@.sizes noneof ['M', 'L'])]
size 左侧(数组或字符串)的大小应与右侧匹配
empty 左侧(数组或字符串)应该为空

支持的函数


可以在JsonPath表达式执行后进行调用,其输入值为表达式的结果。函数的输出看具体某个函数的含义。

函数 描述 返回值类型
min() 数值类型数组最小值 Double
max() 数值类型数组最大值 Double
avg() 数值类型数组平均值 Double
stddev() 数值类型数组标准差 Double
length() 数组长度 Integer
sum() 数值类型数组求和 Double
keys() 提取匹配的元素名称与~操作符功能一致 Set<E>
concat(X) 拼接 与入参相同
append(X) 把元素添加到JsonPath输出的数组中 与入参相同
first() 数组中的第一个元素 数组中元素类型
last() 数组中的最后一个元素 数组中元素类型
index(X) 提供索引为X的数组的元素,如果X为负数,则从后往前取 数组中元素类型

用一个复杂的接单报文来演示


https://jsonpath.com,这个在线网站可以用来验证JsonPath表达式,但是不支持函数,函数可以通过java代码来验证。

String json ="{.....}";
Object read = JsonPath.read(json, "$..price.min()");
System.out.println(read);

示例报文

{
"address":"大良街道同兴路****",
"createTime":"2023-09-20 17:48:44",
"customerName":"培^_^",
"id":0,
"memberId":"ECP002000*****",
"mobile":"184^_^8547",
"extendMessage":{
"clientNo":"testEBU516154",
"clientName":"广州网络科技有限公司",
"spSoNo":"test1976065878296",
"road":"011"
},
"odOrderDetailList":[
{
"id":1,
"productName":"白医生中频针灸理疗仪家用医院医用多功能颈椎肩周炎腰肌劳损电疗经络激光低频按摩器同款中频激光综合治疗仪 2023新款",
"quantity":1,
"productSku":"38fjjjj",
"price":189.6
},
{
"id":2,
"productName":"测试SKU",
"quantity":3,
"productSku":"ESG03JJ1",
"price":200
}
],
"totalPrice":0,
"volume":17318.4,
"extendInfo":{
"templateInfo":[
{
"code":"TP123",
"isPrint":1,
"type":2,
"printType":0
},
{
"code":"TPABC",
"isPrint":1,
"type":4,
"printType":0
}
],
"attrs":{
"plateFormCode":"274"
},
"senderName":"流苏",
"senderAddress":"广东省中山市南头镇永辉北路*****",
"paymentTime":"2023-09-20 17:22:31"
},
"carrierName":"京东配送",
"provinceName":"广东",
"isConsumable":0,
"merchantType":"0",
"tags":[
"a",
"b",
"c",
"d",
"e"
]
}

操作结果

JsonPath 结果
$.extendMessage.clientName "广州网络科技有限公司"
$.extendMessage['clientNo'] "testEBU516154"
$.extendMessage {"clientNo":"testEBU516154","clientName":"广州网络科技有限公司","spSoNo":"test1976065878296","road":"011"}
$.odOrderDetailList[0].productName "白医生中频针灸理疗仪家用医院医用多功能颈椎肩周炎腰肌劳损电疗经络激光低频按摩器同款中频激光综合治疗仪 2023新款"
$.odOrderDetailList[-1].productName "测试SKU"
$.odOrderDetailList.length() 2
$.tags[:] ["a", "b", "c", "d", "e" ]
$.tags[2:] ["c", "d", "e" ]
$.tags[:3] ["a", "b", "c"]
$.tags[1:4] ["b", "c", "d"]
$.tags[-2:] ["d", "e"]
$.tags[:-3] ["a", "b"]
$.tags[:-3].length() 2
$.odOrderDetailList[0,1].productName "白医生中频针灸理疗仪家用医院医用多功能颈椎肩周炎腰肌劳损电疗经络激光低频按摩器同款中频激光综合治疗仪 2023新款", "测试SKU"
$.odOrderDetailList[1].[productName,price] "测试SKU", 200
$..id 0,1,2
$.odOrderDetailList[?(@.id == 4 - 0.4 * 5)].productSku "ESG03JJ1"
$.odOrderDetailList[?(@.id == 1
$.extendInfo.templateInfo[?(!(@.type == 2))].code "TPABC"
$.extendInfo.templateInfo[?((@.type != 2))].code "TPABC"
$.odOrderDetailList[?(@.price > 190)].productName "测试SKU"
$.odOrderDetailList[?(@.id> $.id)].productSku ["38fjjjj","ESG03JJ1"]
$..[?(@.productSku)] [{"id":1,"productName":"白医生中频针灸理疗仪家用医院医用多功能颈椎肩周炎腰肌劳损电疗经络激光低频按摩器同款中频激光综合治疗仪 2023新款","quantity":1,"productSku":"38fjjjj","price":189.6},{"id":2,"productName":"测试SKU","quantity":3,"productSku":"ESG03JJ1","price":200}]
$..tags.length() 5
$.odOrderDetailList[*].price.min() 189.6
$..price.max() 200

作者:京东物流 马红岩

来源:京东云开发者社区 自猿其说 Tech 转载请注明来源

Jayway JsonPath-提取JSON文档内容的Java DSL的更多相关文章

  1. 不规范的json文档 转化成 java 对象的处理

    最近练习爬取数据,遇到了json文档中属性名称没有用双引号的情况,内容如下: 标准的json文档,属性名称都是带双引号的 最后写了个方法,替换属性名字 为 两头追加双引号的属性名字, 特别要注意,防止 ...

  2. 一个SQLServer中JSON文档型数据的查询问题

    近日在项目中遇到一个问题: 如何在报表中统计JSON格式存储的数据? 例如有个调查问卷记录表,记录每个问题的答案. 其结构示意如下(横表设计) Id user date Q1_Answer Q2_An ...

  3. java操作office和pdf文件java读取word,excel和pdf文档内容

    在平常应用程序中,对office和pdf文档进行读取数据是比较常见的功能,尤其在很多web应用程序中.所以今天我们就简单来看一下Java对word.excel.pdf文件的读取.本篇博客只是讲解简单应 ...

  4. C#提取TXT文档指定内容

    早上有分享一篇<VB.NET提取TXT文档指定内容> http://www.cnblogs.com/insus/p/3267347.html 那是原网友的需求用VB.NET写的.刚才有只懂 ...

  5. python、java、ruby、node等如何提取office文档中的内容?

    我相信大家都有过这样的需求,把doc.ppt.excel.pdf.txt中的文本内容提取出来.提取出来的文本内容可用于文档内容的全文索引,文档的基本内容摘要等.在度娘上搜索“如何提取文档内容”,确实有 ...

  6. Collection+JSON 文档

    Collection+JSON 文档 对于这个设计,我们不再以可能的状态和转移为起点,相反,我们将从一个集合状态响应中可能元素的顶层布局开始.从这一点入手,其他细节可以随着设计向超媒体类型最底层属性的 ...

  7. 使用DOM4J解析XML文档,以及使用XPath提取XML文档

    使用DOM4J解析XML文档 需要首先下载DOM4J工具包.这是个第三方工具包 在使用DOM4J解析的时候需要导入 DOM4J的JAR包 下载DOM4J工具包->在MyEclipse中新建lib ...

  8. 使用Java POI来选择提取Word文档中的表格信息

    通过使用Java POI来提取Word(1992)文档中的表格信息,其中POI支持不同的ms文档类型,在具体操作中需要注意.本文主要是通过POI来提取微软2003文档中的表格信息,具体code如下(事 ...

  9. QJsonDocument实现Qt下JSON文档读写

    版权声明:若无来源注明,Techie亮博客文章均为原创. 转载请以链接形式标明本文标题和地址: 本文标题:QJsonDocument实现Qt下JSON文档读写     本文地址:http://tech ...

  10. package.json文档

    之前在博客中写过一篇关于 " node.js的安装配置 " 的文章,里面有提到利用 gulp watch 来监听文档的变化.其中需要 package.json 文件才能实现效果,所 ...

随机推荐

  1. MQ消息队列篇:三大MQ产品的必备面试种子题

    MQ有什么用? MQ(消息队列)是一种FIFO(先进先出)的数据结构,主要用于实现异步通信.削峰平谷和解耦等功能.它通过将生产者生成的消息发送到队列中,然后由消费者进行消费.这样,生产者和消费者之间就 ...

  2. 这些年写过的花式sql - 第3句 今日流失用户

    第3句 今日流失用户 需求: 当日流失用户的定义:昨天登录的,今天没登录的用户数 有一张用户登录日志表,有字段 date_stamp(日期时间戳),用户id(uid).如果用户在某天登录了,该表会有一 ...

  3. [golang]字符串拼接

    前言 在go语言中,因为字符串只能被访问,不能被修改,所以进行字符串拼接的时候,golang都需要进行内存拷贝,造成一定的性能消耗. 方式1:操作符 + 特点:简单,可读性良好.每次拼接都会产生内存拷 ...

  4. MyBatis-Plus批量插入方法saveBatch

    1. saveBatch能否提高插入的效率? 先说结论,saveBatch()方法也是一条一条的插入,也就是说它会产生多条insert语句,而不是一条insert语句,所以它不是真正的批量插入,更不能 ...

  5. virtualbox克隆虚拟机

    1.选择要克隆的虚拟机 2.设置克隆机的名称和存放位置 3.选择克隆类型 4.克隆结果

  6. 用ChatGPT三分钟免费做出数字人视频- 提升自媒体魅力

    本教程收集于:AIGC从入门到精通教程汇总 操作指引 ChatGPT产生文案=>腾讯智影数字人播报=>粘贴文案=>导出视频. 说明:部分资源只有会员才能用~,非会员可生成5分钟视频. ...

  7. python如何提取浏览器中保存的网站登录用户名密码

    python如何提取Chrome中的保存的网站登录用户名密码? 很多浏览器都贴心地提供了保存用户密码功能,用户一旦开启,就不需要每次都输入用户名.密码,非常方便.作为python脚本,能否拿到用户提前 ...

  8. Pytest 框架执行用例流程浅谈

    背景: 根据以下简单的代码示例,我们将从源码的角度分析其中的关键加载执行步骤,对pytest整体流程架构有个初步学习. 代码示例: import pytest def test_add(): asse ...

  9. Deep Transfer Learning综述阅读笔记

    这是一篇linkedin发表的深度迁移学习综述, 里面讲了一些对于search/recommend system中的迁移学习应用. 有不少指导性的方法, 看完后摘录出来 对于ranking方向的TL, ...

  10. 在线PNG, JPG, BMP 转ICO图标,适用WINDOWS XP, VISTA, 7, 8, 10

    在线PNG, JPG, BMP 转ICO图标网址: http://static.krpano.tech/image2ico 该网站可以把PNG, JPG和BMP图片转换成包含多个层级的ICO图标, 可 ...