gpt4 book ai didi

java - 将实体字段更改为不同类型的字段

转载 作者:太空宇宙 更新时间:2023-11-04 09:32:18 25 4
gpt4 key购买 nike

基本上,假设我有一个类 - 汽车。此类车有一个字段“用户”。现在有不同类型的用户 - 比如说“推销员”、“出租车司机”、“检查员”。所有这些都是独立的类,从长远来看将具有不同的领域。现在假设汽车被卖掉了,那么车主就必须更换。现在问题来了 - 为了更改所有者,用户类上的“所有者”字段必须是通用的 - 它不能是“推销员”,因为我如何将所有者更改为“出租车司机”。我听说过术语多态数据库和围绕这个主题的变形,但老实说我不知道​​如何解决这个问题。

我查阅了一份指南,其中的建议在某种程度上起到了作用。它所做的就是创建一个抽象类“所有者”,并创建扩展该抽象类的“检查员”、“推销员”、“出租车司机”类。抽象类使用 single_table 的继承,在这种情况下,将创建一个表,其中存储扩展所有者的所有类,并且可以通过列“type”来区分它们。通过 jpa 保存实体在这个解决方案中工作得很好,但是当我想通过 ID 查找所有者时,它不起作用,可能是因为我的 JpaRepository 试图将数据库行映射到类 Owner,但由于 Owner 是一个抽象类,它无法创建它的实例。

@Entity
@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
@DiscriminatorColumn(name = "type", discriminatorType =
DiscriminatorType.STRING)
public abstract class Owner {
@Id
@GeneratedValue
private Long id;
}


@Entity
@Data
@DiscriminatorValue("salesman")
public class Salesman extends Owner {
@Id
@GeneratedValue
private Long id;

private Long balance;
}


@Repository
public interface OwnerRepository extends JpaRepository<Owner, Long> {
}


@Service
public class OwnerService {

@Autowired
private OwnerRepository repo;

public Owner getById(Long id) {
return repo.getOne(id);
}
}

我希望能够更改汽车的用户并与他们进行简单的 CRUD 操作。

目前,我在尝试使用 JpaRepository 方法 getOne() 时收到以下错误:路径 [] 上下文中 servlet [dispatcherServlet] 的 Servlet.service() 抛出异常 [请求处理失败;嵌套异常是 org.springframework.http.converter.HttpMessageConversionException: 类型定义错误: [简单类型, 类 org.hibernate.proxy.pojo.bytebuddy.ByteBuddyInterceptor];嵌套异常是 com.fasterxml.jackson.databind.exc.InvalidDefinitionException:找不到类 org.hibernate.proxy.pojo.bytebuddy.ByteBuddyInterceptor 的序列化器,并且没有发现创建 BeanSerializer 的属性(为避免异常,禁用 SerializationFeature.FAIL_ON_EMPTY_BEANS)(通过引用链:ee.priit.polymorphism.model.Owner$HibernateProxy$GnSn po6f["hibernateLazyInitializer"])] 的根本原因

com.fasterxml.jackson.databind.exc.InvalidDefinitionException:没有找到类 org.hibernate.proxy.pojo.bytebuddy.ByteBuddyInterceptor 的序列化器,并且没有发现创建 BeanSerializer 的属性(为避免异常,禁用 SerializationFeature.FAIL_ON_EMPTY_BEANS)(通过引用链:ee.priit.polymorphism.model.Owner$HibernateProxy$GnSnpo6 f["hibernateLazyInitializer"])

最佳答案

您可以使用参数化创建 jpa 存储库

public interface OwnerRepository extends JpaRepository<Owner, Long>

find() 将返回 Salseman 类型,并删除为 Owner 类型。如果您要再创建一个扩展 Owner 的类,那么当您调用 findAll 时,jpa 将返回 OwnerExaminer 混合在一起并删除为父 Owner 类型的列表。至少是最新的jpa+hibernate版本。

在数据提取期间,jpa(hibernate)根据鉴别器列值确定目标实体类型,并相应地创建目标实体类型。

如果您想获取所有 Owner 但仅获取 OwnerSalesman 参数化,例如

public interface OwnerRepository extends JpaRepository<Salesman, Long>

就可以了。

如果您尝试启用

spring:
jpa:
properties:
hibernate:
show_sql: true
format_sql: true

...hibernate sql 输出,你会发现精确的 select 查询结构。 (既然你要求 jpa,我假设你使用 spring 或 spring boot)。

关于java - 将实体字段更改为不同类型的字段,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56947383/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com