我正在尝试用jpa建模一个收件箱实体...
我的想法是,收件箱是一组消息的Map,Map应从对话的“主题”索引,主题是消息实体的一列,其中包括发送者+接收者名称的连接,始终按字母顺序......这样,对话中的双方将始终指向同一主题
@Table(name = "chat_box")
@Entity(name = "ChatBox")
public class ChatBox {
@NotNull
@ManyToMany(fetch = FetchType.LAZY, cascade = CascadeType.REMOVE, targetEntity = ChatMessage.class)
@MapKeyColumn(name = "address_type")
@MapKey(name = "sender")
private final Map<@NonNull String, @NonNull Set<@NonNull ChatMessage>> messageList = new HashMap<>();
}
@Table(name = "chat_message",
uniqueConstraints = {@UniqueConstraint(name = "unique_conversation", columnNames = {"conversation"})},
indexes = {@Index(name = "index_conversation", unique = true, columnList = "conversation")}
)
@Entity(name = "ChatMessage")
public class ChatMessage extends BasicEntity {
@NotBlank(message = "O campo 'remetente' não pode estar em branco")
@Size(min = 1, max = 63, message = "O campo 'remetente' deve ter entre ${min} e ${max} carácteres, valor informado; '${validatedValue}'")
@Column(name = "sender", unique = false, nullable = false, insertable = true, updatable = false, length = 63)
private String sender;
@NotBlank(message = "O campo 'destinatario' não pode estar em branco")
@Size(min = 1, max = 63, message = "O campo 'destinatario' deve ter entre ${min} e ${max} carácteres, valor informado; '${validatedValue}'")
@Column(name = "receiver", unique = false, nullable = false, insertable = true, updatable = false, length = 63)
private String receiver;
@NotBlank(message = "O campo 'mensagem' não pode estar em branco")
@Size(min = 1, max = 511, message = "O campo 'mensagem' deve ter entre ${min} e ${max} carácteres, valor informado; '${validatedValue}'")
@Column(name = "message", unique = false, nullable = false, insertable = true, updatable = false, length = 511)
private String message;
@Column(name = "_read", unique = true, nullable = false, insertable = true, updatable = true)
private boolean read;
@Column(name = "conversation", unique = true, nullable = false, insertable = true, updatable = false, length = 127)
public String getConversation() {
return receiver.toLowerCase().compareTo(sender.toLowerCase()) < 1 ? String.format("%s_%s", receiver, sender) : String.format("%s_%s", sender, receiver);
}
}
我应该如何注解Map属性使其按预期工作??这是一个好方法吗?我应该创建另一个实体,这是一组聊天消息,然后只创建这个实体的Map吗?
感谢所有帮助
1条答案
按热度按时间njthzxwz1#
如果你想用两个表来建模,你需要引入一个中间层,比如域模型层,因为JPA不能对
Map<?, Collection<?>>
建模。我认为这是一个完美的Blaze-Persistence实体视图用例。
我创建这个库是为了允许在JPA模型和自定义接口或抽象类定义的模型之间进行简单的Map,就像Spring Data Projections一样。其思想是您可以按照自己喜欢的方式定义目标结构(域模型),并通过JPQL表达式将属性(getter)Map到实体模型。
使用Blaze-Persistence Entity-Views时,您的用例的DTO模型可能如下所示:
查询是将实体视图应用于查询的问题,最简单的是按id查询。
ChatBoxDto a = entityViewManager.find(entityManager, ChatBoxDto.class, id);
Spring Data 集成允许您像Spring Data 投影一样使用它:https://persistence.blazebit.com/documentation/entity-view/manual/en_US/index.html#spring-data-features
最好的部分是,它只会获取实际需要的状态!