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

如何以简洁方式提取Java Record嵌套字段?BeanUtils不支持该类型

Java Record 嵌套属性读取的实现方案

commons-beanutils 可以轻松从JavaBean中读取嵌套属性值:

public class Person {
  Address address;
  public Address getAddress() { return address; }
}
public class Address {
  String city;
  public String getCity() { return city; }
}

var p = new Person();
p.address = new Address();
p.address.city = "Malgudi";

BeanUtils.getNestedProperty(p, "address.city"); // ✅ 返回 Malgudi

但当使用Java Record时,BeanUtils并不支持这种嵌套属性读取:

public record Person(Address address) {}
public record Address(String city) {}

var p = new Person(new Address("Malgudi"));

BeanUtils.getNestedProperty(p, "address.city"); // ❌ 报错:Unknown property 'address'

以下是几种简洁的替代实现方案:

方案1:使用Jackson ObjectMapper

Jackson原生支持Java Record,可通过JSON节点路径读取嵌套属性:

import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.JsonNode;

public class RecordNestedDemo {
    public static void main(String[] args) throws Exception {
        var p = new Person(new Address("Malgudi"));
        ObjectMapper mapper = new ObjectMapper();
        
        // 方式1:转换为JsonNode后逐层读取
        JsonNode rootNode = mapper.valueToTree(p);
        String city = rootNode.get("address").get("city").asText(); // ✅ Malgudi
        
        // 方式2:使用JSON路径直接定位
        String cityPathValue = mapper.readValue(mapper.writeValueAsString(p), JsonNode.class)
                                    .at("/address/city").asText();
    }
}

方案2:使用Spring BeanWrapper

Spring的BeanWrapper组件兼容Java Record,支持通过属性路径直接取值:

import org.springframework.beans.BeanWrapper;
import org.springframework.beans.BeanWrapperImpl;

public class RecordNestedDemo {
    public static void main(String[] args) {
        var p = new Person(new Address("Malgudi"));
        BeanWrapper wrapper = new BeanWrapperImpl(p);
        String city = (String) wrapper.getPropertyValue("address.city"); // ✅ Malgudi
    }
}

方案3:自定义轻量反射工具类

如果不想引入第三方依赖,可利用Record自动生成的访问方法(属性名())实现工具类:

import java.lang.reflect.Method;

public class RecordPropertyUtils {
    public static Object getNestedProperty(Object record, String path) throws Exception {
        String[] props = path.split("\\.");
        Object current = record;
        for (String prop : props) {
            Method accessor = current.getClass().getMethod(prop);
            current = accessor.invoke(current);
            if (current == null) return null;
        }
        return current;
    }

    public static void main(String[] args) throws Exception {
        var p = new Person(new Address("Malgudi"));
        String city = (String) getNestedProperty(p, "address.city"); // ✅ Malgudi
    }
}

内容的提问来源于stack exchange,提问作者Knight Industries

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.08 18:21:24