You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Java中通过JsonPath用自定义函数设置嵌套JSON对象的值

解决方案:用自定义函数处理JsonPath匹配值并回写JSON

一、使用支持该功能的第三方库:Jayway JsonPath

Jayway JsonPath是Java生态中功能更丰富的JsonPath实现,原生支持通过自定义函数对匹配到的值进行转换并回写。

示例代码

首先引入Maven依赖:

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

然后编写处理逻辑:

import com.jayway.jsonpath.JsonPath;
import com.jayway.jsonpath.MapFunction;
import net.minidev.json.JSONObject;

public class JsonPathProcessor {
    public static void main(String[] args) {
        String json = "{\n" +
                "    \"store\": {\n" +
                "       \"name\": \"ABC Co\",\n" +
                "        \"book\": [\n" +
                "            {\n" +
                "                \"category\": \"reference\",\n" +
                "                \"author\": \"Nigel Rees\",\n" +
                "                \"title\": \"Sayings of the Century\",\n" +
                "                \"price\": 8.95,\n" +
                "                \"edition\": {\n" +
                "                       \"year\": 1990,\n" +
                "                       \"published_by\": \"MacMillan\"\n" +
                "                 }\n" +
                "            },\n" +
                "            {\n" +
                "                \"category\": \"fiction\",\n" +
                "                \"author\": \"Evelyn Waugh\",\n" +
                "                \"title\": \"Sword of Honour\",\n" +
                "                \"price\": 12.99,\n" +
                "                \"edition\": {\n" +
                "                       \"year\": 1980,\n" +
                "                       \"published_by\": \"MacMillan\"\n" +
                "                 }\n" +
                "            }\n" +
                "        ]\n" +
                "     }\n" +
                "}";

        // 批量处理数组中所有书籍价格:自定义逻辑为价格加10
        JSONObject modifiedJson = JsonPath.parse(json)
                .map("$.store.book[*].price", new MapFunction<Double, Double>() {
                    @Override
                    public Double map(Double currentValue, Configuration configuration) {
                        return currentValue + 10; // 替换为你的加密/自定义处理逻辑
                    }
                })
                // 处理单个对象属性:商店名称添加后缀
                .map("$.store.name", new MapFunction<String, String>() {
                    @Override
                    public String map(String currentValue, Configuration configuration) {
                        return currentValue + " - Updated";
                    }
                })
                .json();

        System.out.println(modifiedJson.toJSONString());
    }
}

核心说明

  • map方法会自动遍历所有匹配JsonPath的节点,将每个节点值传入自定义MapFunction,用返回值直接替换原节点内容。
  • 同时支持数组批量元素和单个对象属性的处理,完全覆盖你的需求场景。

二、基于fastjson2自行实现setNestedJson方法

如果不想切换库,可以基于fastjson2的API,先查询所有匹配节点的具体路径,再逐个应用函数并回写。

实现思路

  1. 用JSONPath.eval获取所有匹配的值,同时用JSONPath.getPaths获取每个值对应的完整定位路径。
  2. 对每个值应用自定义函数生成新值。
  3. 用JSONPath.set逐个将新值写回原JSON对象。

示例代码

import com.alibaba.fastjson2.JSON;
import com.alibaba.fastjson2.JSONObject;
import com.alibaba.fastjson2.JSONPath;
import java.util.List;
import java.util.function.Function;

public class FastJson2CustomProcessor {

    public static <T, R> void setNestedJson(JSONObject jsonObject, String jsonPath, Function<T, R> func) {
        // 获取所有匹配节点的值和对应路径
        List<Object> matches = JSONPath.eval(jsonObject, jsonPath);
        List<String> nodePaths = JSONPath.getPaths(jsonObject, jsonPath);

        // 遍历处理每个节点
        for (int i = 0; i < matches.size(); i++) {
            String path = nodePaths.get(i);
            T originalValue = (T) matches.get(i);
            R newValue = func.apply(originalValue);
            JSONPath.set(jsonObject, path, newValue);
        }
    }

    public static void main(String[] args) {
        String jsonStr = "{\n" +
                "    \"store\": {\n" +
                "       \"name\": \"ABC Co\",\n" +
                "        \"book\": [\n" +
                "            {\n" +
                "                \"category\": \"reference\",\n" +
                "                \"author\": \"Nigel Rees\",\n" +
                "                \"title\": \"Sayings of the Century\",\n" +
                "                \"price\": 8.95,\n" +
                "                \"edition\": {\n" +
                "                       \"year\": 1990,\n" +
                "                       \"published_by\": \"MacMillan\"\n" +
                "                 }\n" +
                "            },\n" +
                "            {\n" +
                "                \"category\": \"fiction\",\n" +
                "                \"author\": \"Evelyn Waugh\",\n" +
                "                \"title\": \"Sword of Honour\",\n" +
                "                \"price\": 12.99,\n" +
                "                \"edition\": {\n" +
                "                       \"year\": 1980,\n" +
                "                       \"published_by\": \"MacMillan\"\n" +
                "                 }\n" +
                "            }\n" +
                "        ]\n" +
                "     }\n" +
                "}";

        JSONObject jsonObject = JSON.parseObject(jsonStr);

        // 处理价格:自定义逻辑为乘以2
        setNestedJson(jsonObject, "$.store.book[0:].price", (Double price) -> price * 2);

        // 处理商店名称:自定义逻辑为转为大写
        setNestedJson(jsonObject, "$.store.name", (String name) -> name.toUpperCase());

        System.out.println(jsonObject.toJSONString());
    }
}

核心说明

  • JSONPath.getPaths会返回每个匹配节点的精确路径(比如$.store.book[0].price、$.store.book[1].price),确保能精准定位修改。
  • 自定义函数通过Function<T,R>接口传入,支持任意类型的转换逻辑(加密、运算、字符串处理等)。

内容的提问来源于stack exchange,提问作者Chris Paul

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.20 10:33:14