JsonPath实战

概述

JsonPath,GitHub是一种简单的方法来提取给定JSON文档的部分内容,提供类似正则表达式的语法来解析JSON文档。

特性

入门

引入如下Maven依赖:

<dependency><groupId>com.jayway.jsonpath</groupId><artifactId>json-path</artifactId>
</dependency>

基本使用:

JsonPath.read("", "");

需要传入两个String类型的参数,第一个参数为一个JSON String,第二个参数为JsonPath表达式。对应的源码为:

public static <T> T read(String json, String jsonPath, Predicate... filters) {return (new ParseContextImpl()).parse(json).read(jsonPath, filters);
}

第三个参数Predicate,表示谓词,在进阶部分会详细讲解。

查看com.jayway.jsonpath.JsonPath源码,不难发现,第一个参数可以替换成Object、File、URL、InputStream类型的JSON,即可以直接读取一个JSON文件或网络资源等。

返回类型可以是用泛型定义的任意对象(<T> T),也可以是一个DocumentContext(用得不多,可以直接忽略)。

JsonPath表达式

从上面的简介,不难得知,使用好JsonPath的基础条件是熟悉JsonPath表达式:

  • JsonPath中的根成员对象始终称为$,无论是对象JSON Object还是数组JSON Array
  • JsonPath表达式支持点表示法
  • 也支持括号表示法,繁琐,不建议使用
  • 解析JSON Array时,支持数组表示法,索引从0开始
  • 数组表示法,和Python 数组语法几乎没有差别
  • *表示所有节点
  • ..表示选择所有符合条件的节点
  • ?()表示过滤操作
  • @表示当前节点

如何校验JsonPath表达式的合法性呢?

JsonPath.compile("$..");

在这里插入图片描述
使用IDEA的话,编译器会给出warning,执行mvn compile可以成功。运行这一行代码,JsonPath给出报错:InvalidPathException: Path must not end with a '.' or '..'

函数支持

函数可以在路径的尾部调用,函数的输出是路径表达式的输出,该函数的输出是由函数本身所决定的。

函数描述输出
min()返回数值类型数组的最小值Double
max()返回数值类型数组的最大值Double
avg()返回数值类型数组的平均值Double
stddev()返回数值类型数组的标准偏差值Double
length()返回数值类型数组的长度Integer

过滤器运算符

?(),表示过滤器,用于筛选数组的逻辑表达式。一个典型的过滤器将是[?(@.age > 18)]@表示正在处理的当前项目。可使用逻辑运算符&&||来创建更复杂的过滤器。字符串文字必须用单引号或双引号括起来:[?(@.color == 'blue')][?(@.color == "blue")]

操作符描述
==left等于right(注意1不等于’1’)
!=不等于
<小于
<=小于等于
>大于
>=大于等于
=~匹配正则表达式[?(@.name =~ /foo.*?/i)]
in左边存在于右边 [?(@.size in [‘S’, ‘M’])]
nin左边不存在于右边
size数组或字符串长度
empty数组或字符串为空

实战

示例JSON文档:

{"store": {"book": [{"category": "reference","author": "Nigel Rees","title": "Sayings of the Century","price": 8.95},{"category": "fiction","author": "J. R. R. Tolkien","title": "The Lord of the Rings","isbn": "0-395-19395-8","price": 22.99}],"bicycle": {"color": "red","price": 19.95}},"expensive": 10
}

很简单的一个JSON文档,有两个键值对,其中store表示商场,卖book和bicycle;expensive=10。

$.store.book[0].title表示获取第一本书的标题,测试代码:

log.info(JsonPath.read(jsonStr, "$.store.book[0].title"));

输出:Sayings of the Century

使用括号表示法,$['store']['book'][0]['title'],输出同样是Sayings of the Century

$..book.length()表示获取book这个Array的个数,输出2,测试代码略。

$..book[0,1]表示获取第一、二两本书。
$..book[-2:]表示获取最后两本书。
$..book[:1]表示获取从索引0开始的书籍,索引1不算在内。
$..book[1:2]表示获取从索引1开始的书籍,索引2不算在内。
$..book[1:]表示获取第二本(索引1开始)到最后一本书。

$.store.book[*].author表示获取所有book的作者,输出是一个列表。使用..的话,$..author也表示获取所有作者,输出列表。

$..book[?(@.isbn)]表示获取JSON中book Array里包含isbn编号的书。

$.store.book[?(@.isbn)].author表示获取JSON中book Array里包含isbn编号的书的作者。

$.store.book[?(@.price < 10)]表示获取JSON中book Array里售价低于10的书。

$..book[?(@.price < $['expensive'])]表示获取JSON中book Array里售价低于expensive的书。

支持的常用表达式

JsonPath描述
$根节点
@当前节点
.or[]子节点
..选择所有符合条件的节点
*所有节点
[]迭代器标示,如数组下标
[,]支持迭代器中做多选
[start:end:step]数组切片运算符
?()支持过滤操作
()支持表达式计算

进阶

Exception

以json-path-2.9.0版本为例,共定义8个Exception:

  • InvalidCriteriaException
  • InvalidJsonException
  • InvalidModificationException
  • InvalidPathException
  • JsonPathException
  • PathNotFoundException
  • ValueCompareException
  • EvaluationAbortException
  • MappingException
    在这里插入图片描述

谓词

谓词,谓语,也有翻译成断言的,即Predicate,JsonPath中的过滤器谓词有三种:

  • 内联谓词
  • 过滤器谓词
  • 自定义谓词

内联谓词

List<Map<String, Object>> books =  JsonPath.parse(json).read("$.store.book[?(@.price < 10)]");

可使用&&||结合多个谓词[?(@.price < 10 && @.category == 'fiction')]。使用!否定一个谓词[?(!(@.price < 10 && @.category == 'fiction'))]

过滤谓词

使用Filter API构建:

import static com.jayway.jsonpath.JsonPath.parse;
import static com.jayway.jsonpath.Criteria.where;
import static com.jayway.jsonpath.Filter.filter;
Filter filter = filter(where("category").is("fiction").and("price").lte(10D)
);
List<Map<String, Object>> books = parse(json).read("$.store.book[?]", filter);

占位符?为路径中的过滤器。当提供多个过滤器时,它们按照占位符数量与提供的过滤器数量相匹配的顺序应用。可以在一个过滤器操作[?, ?]中指定多个谓词占位符,这两个谓词都必须匹配。

过滤器也可以与ORAND一起使用

Filter fooOrBar = filter(where("foo").exists(true)).or(where("bar").exists(true));
Filter fooAndBar = filter(where("foo").exists(true)).and(where("bar").exists(true));

自定义谓词

Predicate booksWithIsbn = new Predicate() {@Overridepublic boolean apply(PredicateContext ctx) {return ctx.item(Map.class).containsKey("isbn");}
};
List<Map<String, Object>> books = reader.read("$.store.book[?].isbn", List.class, booksWithIsbn);

Configuration

Option

源码为com.jayway.jsonpath.Option,枚举类:

  • DEFAULT_PATH_LEAF_TO_NULL:当检索不到时返回null对象,否则如果不配置这个,会直接抛出异常PathNotFoundException
  • ALWAYS_RETURN_LIST:总是返回list,即便是一个确定的非list类型,也会被包装成list
  • AS_PATH_LIST:返回path
  • SUPPRESS_EXCEPTIONS:不抛出异常,需要判断如下:
    • ALWAYS_RETURN_LIST开启,则返回空list
    • ALWAYS_RETURN_LIST关闭,则返回null
  • REQUIRE_PROPERTIES:如果设置,则不允许使用通配符,比如$[*].b会抛出PathNotFoundException异常。

SPI

SPI是
在这里插入图片描述

cache

对应于源码

json

mapper

参考

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/640793.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

美国RAKSmart服务器性能科普

当我们谈论服务器性能时&#xff0c;无疑会涉及多个维度&#xff0c;包括存储能力、网络连接、稳定性、管理界面以及安全性等。在这篇科普文章中&#xff0c;我们将深入探讨美国RAKSmart服务器的性能特点。 首先&#xff0c;RAKSmart服务器在存储和扩展性方面表现出色。它们配备…

Vs Code npm install 报错解决方法

用的人家的前端框架发现是封装过的&#xff0c;要修改人家前端的话还得把前端源码放在Vs Code 上运行&#xff0c;后端放在IDEA上运行&#xff0c;然后前后端并行开发&#xff0c;在配置前端环境时遇到&#xff1a; npm install 这个的原因是我把node下载到D盘了权限不够框框爆…

Mysql 、Redis 数据双写一致性 更新策略与应用

零、important point 1. 缓存双写一致性问题 2. java实现逻辑&#xff08;对于 QPS < 1000 可以使用&#xff09; public class UserService {public static final String CACHE_KEY_USER "user:";Resourceprivate UserMapper userMapper;Resourceprivate Re…

C++中的queue(容器适配器)

目录 一、成员函数 一、构造函数 二、入栈 push 三、出栈 pop 四、判空 empty 五、队列大小 size 六、取队头元素 front 七、取队尾元素 back 八、入栈 emplace 九、交换函数 swap 二、非成员函数重载 一、关系运算符重载 二、交换函数 swap C中的queue不再是容…

AWD线下攻防万字最完整战术(记第一届“长城杯”半决赛战术)

目录 准备阶段 1.登录比赛平台&#xff08;获取资产&#xff09; 查看账号账号修改 服务器SSH口令mysqlWEB服务口令(后台密码)数据库后台管理员密码 账号用户检查 2.dump源码&#xff08;方便应急响应恢复靶机&#xff09; 网站源码备份 压缩文件解压文件备份到服务器本地上传…

Google Ads广告为Demand Gen推出生成式AI工具,可自动生成广告图片

谷歌今天宣布在Google Ads广告中为Demand Gen活动推出新的生成人工智能功能。 这些工具由谷歌人工智能提供支持&#xff0c;广告商只需几个步骤即可使用文本提示创建高质量的图片。 这些由人工智能驱动的创意功能旨在增强视觉叙事能力&#xff0c;帮助品牌在YouTube、YouTube…

Webpack-

定义 静态模块&#xff1a;指的是编写代码过程中的html&#xff0c;css&#xff0c;js&#xff0c;图片等固定内容的文件 打包&#xff1a;把静态模块内容压缩、整合、翻译等&#xff08;前端工程化&#xff09; 1&#xff09;把less/sass转成css代码 2&#xff09;把ES6降级…

1.基于Springboot对SpringEvent初步封装

一&#xff1a;前置知识 Spring Event是Spring框架提供的一种事件机制&#xff0c;用于处理组件之间的通信。在复杂的系统中&#xff0c;模块或组件之间的通信是必不可少的。Spring Event可以用于以下场景&#xff1a; 1.系统间解耦&#xff1a;模块或组件之间通过事件进行通…

.gitignore语法及配置问题

语法及配置 前言.gitignore语法Git 忽略规则优先级gitignore规则不生效Java项目中常用的.gitignore文件c项目中常用的.gitignore注意事项 前言 在工程中&#xff0c;并不是所有文件都需要保存到版本库中&#xff0c;例如“target”目录及目录下的文件就可以忽略。在Git工作区的…

NLP大模型的训练

NLP模型的训练主要分成两步&#xff1a; 1.先进行通用任务的训练&#xff1b;无监督的样本是无穷无尽的&#xff1b; 这里列举两种&#xff1a;MLM和NSP,NSP由于在某些论文中被证明是无效的&#xff0c;所以用的少&#xff1b; MLM: 接下来会在特定任务上进行finetune>su…

夜神、雷电、android studio手机模拟器资源占用情况

夜神、雷电、android studio手机模拟器内存资源占用情况 由于开发电脑只有16G内存&#xff0c;出于开发需要和本身硬件资源的限制&#xff0c;对多个手机模拟器进行了机器资源占用&#xff08;主要是内存&#xff09;的简单比较。 比较的模拟器包括&#xff1a; 1. Android S…

[Kotlin]引导页

使用Kotlin Jetpack Compose创建一个左右滑动的引导页, 效果如图. 1.添加依赖项 androidx.compose.ui最新版本查询:https://maven.google.com/web/index.html com.google.accompanist:accompanist-pager最新版本查询:https://central.sonatype.com/ 确保在 build.gradle (M…