无法将对象列表存储为Oracle单列JSON,请求技术排查
问题分析与解决方案
错误根源
你遇到的Can not set java.lang.String field xxx.demo.Models.Sensors.amplitudos to xxx.demo.Models.Sensors错误,本质是JPA无法直接将@Embeddable类的数组映射到数据库单个字段:
@Embeddable注解的作用是将类的字段嵌入到主实体的数据库表中(比如Sensors的amplitudos、displacement会成为SENSOR表的独立列),而非把整个对象数组序列化为单个字段存储。- 直接用
Sensors[]作为实体字段时,JPA无法识别该如何处理数组与数据库列的映射,导致类型转换逻辑混乱。
要实现将对象数组存入Oracle单个字段,需要把数组序列化为JSON字符串存储,读取时再反序列化为对象数组。
具体解决方案
步骤1:创建JSON序列化转换器
自定义JPA属性转换器,负责将Sensors数组与JSON字符串互相转换:
import com.fasterxml.jackson.core.JsonProcessingException; import com.fasterxml.jackson.databind.ObjectMapper; import jakarta.persistence.AttributeConverter; import jakarta.persistence.Converter; import java.io.IOException; @Converter(autoApply = true) public class SensorsArrayConverter implements AttributeConverter<Sensors[], String> { private final ObjectMapper objectMapper = new ObjectMapper(); // 将对象数组转为JSON字符串,存入数据库 @Override public String convertToDatabaseColumn(Sensors[] sensorsArray) { try { return objectMapper.writeValueAsString(sensorsArray); } catch (JsonProcessingException e) { throw new RuntimeException("序列化Sensors数组失败", e); } } // 将数据库中的JSON字符串转为对象数组 @Override public Sensors[] convertToEntityAttribute(String dbData) { try { return objectMapper.readValue(dbData, Sensors[].class); } catch (IOException e) { throw new RuntimeException("反序列化JSON为Sensors数组失败", e); } } }
步骤2:修改Sensor实体类
更新sensors字段的注解,关联转换器,并指定数据库列类型为Oracle的CLOB(存储长文本):
@Entity @Table(name = "SENSOR") public class Sensor implements Serializable { // 其他字段保持不变 @Column(name = "SENSORS", columnDefinition = "CLOB") @Convert(converter = SensorsArrayConverter.class) private Sensors[] sensors; // 构造方法、getter/setter保持不变 }
步骤3:修正JSON字段映射
JSON请求中的sensorid是小写蛇形命名,而实体类中是驼峰命名sensorId,需要在Sensors类的字段上添加注解确保映射正确:
@Embeddable public class Sensors { // 其他字段保持不变 @JsonProperty("sensorid") private Integer sensorId; // getter/setter保持不变 }
步骤4:确认数据库列类型
确保SENSOR表的SENSORS列类型为CLOB(如果JSON内容较短,也可以用VARCHAR2(4000),但CLOB更适合存储长JSON)。
验证
发送原JSON请求后,sensors数组会被自动序列化为JSON字符串存入SENSORS列,查询时会反序列化为Sensors[]对象返回,完全符合你的需求。
内容的提问来源于stack exchange,提问作者Luthfi Fitra Musyaffa
相关产品推荐
相关产品推荐

