假设你有一个类需要保存一些映射项,使用任何枚举作为键。使用此映射可以生成例如具有十六进制值的varbinary
(SQL Server)。
@Entity
public abstract class X {
@ElementCollection
private Map<Enum, Boolean> values;
}
这有效,但主要问题是可读性。数据库中的数据不是人类可读的。尝试使用@MapKeyEnumerated(EnumType.STRING)
或使用EnumType.Ordinal不起作用,因为Enum可以是任何类型,并将MyEnum.SOME_VALUE
保存为“SOME_VALUE”。
是否可以拦截保存/检索并保存一个完全限定的名称(com.x.myenum.value)或可用于恢复枚举而不是十六进制值的清晰内容?
答案 0 :(得分:3)
要存储一个其中key是枚举的Map,并在db中获取人类可读的内容,您可以尝试:
@Entity
public class QuestionnaireDefinition{
...
@OneToMany(mappedBy = "questionnaireDefinition", fetch = FetchType.LAZY, cascade = CascadeType.ALL)
@MapKeyEnumerated(EnumType.STRING)
@MapKeyColumn(name = "language", insertable = false, updatable = false)
private final Map<Language, QuestionnaireDefinitionTranslation> translations = new HashMap<Language, QuestionnaireDefinitionTranslation>();
... }
其中QuestionnaireDefinitionTranslation是在给定语言枚举的情况下将被fecthed的实体或值。 在此示例中,映射值为type:QuestionnaireDefinitionTranslation
@Entity
public class QuestionnaireDefinitionTranslation {
@Enumerated(EnumType.STRING)
@Column(nullable = false, insertable = true, updatable = true)
private Language language;
@ManyToOne(fetch = FetchType.LAZY, optional = false)
private QuestionnaireDefinition questionnaireDefinition;
private String text;
...
}
类语言是普通的枚举:
public enum Language {
EN, ES, FI, FR;
}
使这项工作的想法是: 1.首先坚持所有者类:
QuestionnaireDefinition questionnaireDef = new QuestionnaireDefinition();
em.persist(questionnaireDef );
然后使用您的枚举作为键的聚合类。
QuestionnaireDefinitionTranslation translation = new QuestionnaireDefinitionTranslation();
translation.set(questionnaireDef);
translation.setLanguage(Language.En);
translation.setText("hello");
em.persist(translation);
总而言之,你可以通过你的枚举来获取
QuestionnaireDefinition qd = em.find(1,QuestionnaireDefinition.class);
qd.getTranslations().get(Language.EN);
请注意事务,LazyException和那些东西。