python使用jsonpath-ng库操作json数据
jsonpath-ng
库的详细使用如下:
一、安装与导入
-
安装
通过pip
安装库:pip install jsonpath-ng
支持 Python 3.6 及以上版本。
-
导入核心模块
主要使用parse
函数和JSONPath
对象:from jsonpath_ng import parse
二、基础查询操作
1. 简单路径查询
• 场景:从 JSON 中提取指定路径的值。
data = {"person": {"name": "Alice","age": 30,"address": {"city": "New York"}}
}
# 解析表达式
expression = parse("person.name")
# 查找匹配结果
matches = expression.find(data)
print(matches[0].value) # 输出:Alice
支持点号 .
或中括号 []
访问路径,如 parse("person['address']['city']")
,
expression.find() 函数 返回的是一个DatumInContext对象
。
2. 数组遍历查询
• 场景:提取列表中的所有元素。
使用 [*]
通配符匹配数组元素:
data = {"products": [{"name": "A", "price": 10}, {"name": "B", "price": 20}]}
expression = parse("products[*].price")
matches = [match.value for match in expression.find(data)]
print(matches) # 输出:[10, 20]
适用于嵌套数组的递归查询(如 $..price
)。
三、高级查询语法
1. 过滤条件
• 场景:筛选符合条件的数据。
使用 [?()]
表达式实现动态过滤:
data = {"store": {"books": [{"title": "Book1", "price": 15},{"title": "Book2", "price": 25}]}
}
# 筛选价格低于20的书籍
expression = parse("store.books[?(@.price < 20)].title")
matches = [match.value for match in expression.find(data)]
print(matches) # 输出:["Book1"]
支持逻辑运算符(&&
、||
)和算术运算。
[?(@.price < 20)]
:过滤条件
-
(1)
[]
:数组索引或过滤器操作符
作用:表示对数组的操作,内部可以包含索引(如[0]
)或过滤条件(如[?()]
)。示例:
books[0]:选择第一本书。books[?()]:根据条件筛选书籍。
-
(2)
?()
:条件过滤语法
作用:定义过滤逻辑,?()
内需编写布尔表达式。
示例:books[?(@.price < 20)] // 筛选价格低于20的书籍
-
(3)
@
:当前节点引用
作用:在过滤器中表示当前遍历到的数组元素(即每本书的对象)。
示例:{"title": "Book A", "price": 15} // 当前@指向此对象
@.price
表示当前书籍的price
属性值。 -
(4)
@.price < 20
:过滤逻辑
作用:比较当前书籍的价格是否小于 20。
扩展语法:• 逻辑运算符:
&&
(与)、||
(或)、!
(非),如@.price < 20 && @.category == "fiction"
。• 正则匹配:
=~
(如@.title =~ /^The/
)。
2. 函数操作
• 场景:对数据进行聚合计算。
使用内置函数如 length()
、sum()
:
expression = parse("sum(store.books[*].price)")
total_price = expression.find(data)[0].value
print(total_price) # 输出:40
其他函数包括 min()
、max()
等。
四、数据修改操作
1. 键值修改
• 场景:动态更新 JSON 数据中的值。
通过 update()
方法修改匹配项:
expression = parse("person.name")
matches = expression.find(data)
if matches:matches[0].update("Bob") # 将 Alice 改为 Bob
print(data["person"]["name"]) # 输出:Bob
适用于批量修改场景。
五、实际应用案例
1. 接口测试验证
• 场景:验证接口返回数据的关键字段。
import requests
response = requests.get("https://api.example.com/user/1")
data = response.json()
# 验证用户ID是否为1
expression = parse("user.id")
user_id = expression.find(data)[0].value
assert user_id == 1, "用户ID验证失败"
2. 数据提取与转换
• 场景:从复杂 JSON 中提取结构化数据。
data = {"orders": [{"id": 1, "items": [{"name": "item1", "qty": 2}]},{"id": 2, "items": [{"name": "item2", "qty": 3}]}]
}
# 提取所有订单的商品名称和数量
expression = parse("orders[*].items[*].[name, qty]")
matches = [match.value for match in expression.find(data)]
print(matches) # 输出:[["item1", 2], ["item2", 3]]
六、注意事项
- 路径大小写敏感:JSON 键名需严格匹配大小写。
- 错误处理:捕获
IndexError
或KeyError
避免程序崩溃:try:matches = expression.find(data)if not matches:print("未找到匹配项") except Exception as e:print(f"查询失败:{e}")
- 性能优化:对大型 JSON 数据避免频繁解析表达式,可预编译重用
parse
对象。