wes*_*eyy 6 java inheritance spring hibernate jpa
我在我的应用程序中设计了实体以遵循Hibernate 的继承策略Inheritance.JOINED。
基本抽象类是UserTable,具体派生类是ClientTable和OwnerTable。
我想要实现的目标是拥有一个存储库,我可以在其中通过or 进行find任何UserTable(ClientTable和OwnerTable)。重要的要求是,一旦它们被获取,它们就可以被强制转换为正确的类型,并且它们携带它们的特定字段(而不仅仅是从 继承的那些)。IdEmailUserTable
同样重要的是,我应该能够通过同一个存储库保存这些实体,即。repository.save(clientTable).
所以这样的事情应该是可能的:
UserTableRepository repository = // ...
int clientId = 3;
int ownerId = 5;
ClientTable clientTable = (ClientTable) repository.findByUserId(clientId);
OwnerTable clientTable = (OwnerTable) repository.findByUserId(ownerId);
clientTable = (ClientTable) repository.findByEmail(clientEmail);
ownerTable = (OwnerTable) repository.findByEmail(ownerEmail);
Run Code Online (Sandbox Code Playgroud)
我的实体看起来像这样。
用户表.java
@Entity
@Table(name = "USER")
@Inheritance(strategy = InheritanceType.JOINED)
public abstract class UserTable implements Serializable {
@Column(name = "USER_ID", nullable = false)
private Long userId;
@EmbeddedId
private UserTablePK userTablePK;
@Column(name = "PASSWORD", nullable = false, length = 512)
private String password;
@Column(name = "FIRSTNAME", nullable = false, length = 256)
private String firstName;
// get, set
}
Run Code Online (Sandbox Code Playgroud)
.. 和一个主键
用户表PK.java
@Embeddable
public class UserTablePK implements Serializable {
private static final long serialVersionUID = 1L;
@Column(name = "EMAIL", nullable = false, length = 256)
private String email;
public UserTablePK() {
}
public UserTablePK(String email) {
this.email = email;
}
// get, set
}
Run Code Online (Sandbox Code Playgroud)
客户端表
@Entity
@Table(name = "CLIENT")
public class ClientTable extends UserTable implements Serializable {
@Column(name = "SHOPING_POWER")
private Integer shoppingPower;
@Column(name = "SHOPPING_FREQUENCY")
private Integer shoppingFreq;
// get, set
}
Run Code Online (Sandbox Code Playgroud)
所有者表
@Entity
@Table(name = "OWNER")
public class OwnerTable extends UserTable implements Serializable {
@Column(name = "EFFICIENCY")
private String efficiency;
@Column(name = "SALARAY")
private Integer;
// get, set
}
Run Code Online (Sandbox Code Playgroud)
现在,一旦设置了实体,我就需要编写一个与上述类似的存储库,这里是我需要帮助的地方。我想写这样的东西。
UserTableRepository.java
@Repository
public interface UserTableRepository extends CrudRepository<UserTable, UserTablePK> {
@Query("SELECT e FROM UserTable e WHERE e.userTablePK.email = ?1")
public UserTable findByEmail(String email); // if owner email, retrieve OwnerTable; if client email, retrieve ClientTable instance
@Query("SELECT e FROM UserTable e WHERE e.userId = ?1")
public UserTable findByUserId(Long userId); // if owner id, retrieve OwnerTable; if client id, retrieve ClientTable instance
}
Run Code Online (Sandbox Code Playgroud)
我实际上还没有尝试过这个,因为我想检查这是否是正确的路线,但是:我很怀疑这Query是否可行。因为为了检索整个子类对象,应该使用某种 JOIN,问题是我不能明确地说 ie。JOIN ClientTable因为那样我将无法获取任何OwnerTable实体。
我怎样才能实现从同一个存储库中获取两个子类?
此外,要求是能够获取特定的子类。所以像:
List<ClientTable> clients = repository.findAllClients();
Run Code Online (Sandbox Code Playgroud)
是否可以使用相同的存储库,还是应该编写特定于子类的存储库?例如。
@Repository
public interface ClientTableRepository extends CrudRepository<ClientTable, ClientTablePK> {
// empty
}
Run Code Online (Sandbox Code Playgroud)
...然后像这样称呼它们:
ClientTableRepository repository = // ...
List<ClientTable> clients = repository.findAll();
Run Code Online (Sandbox Code Playgroud)
这是否足以让 JPA 确定如何仅查找特定子类的所有实例?
您想要实现的正是 JPA 中继承的工作方式。
因此,您的查询完全没问题,并且结果列表中将包含子类的实例。
在我的一篇博客文章中了解有关 JPA 继承的更多信息:
https://72.services/inheritance-in-jpa/
| 归档时间: |
|
| 查看次数: |
3636 次 |
| 最近记录: |