#java #hibernate #jpa #orm #hibernate-mapping
#java #гибернация #jpa #orm #гибернация-отображение
Вопрос:
Рассмотрим следующую модель:
Абстрактный класс AbstractLog
@MappedSuperclass
public abstract class AbstractLog{
private Long id;
private Set<Comment> comments;
@Id
@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "quasar_log_id_seq")
public Long getId() {
return id;
}
@OrderBy(clause = "created")
@OneToMany(mappedBy = "abstractLog", fetch = FetchType.LAZY, cascade = { CascadeType.ALL }, orphanRemoval = true)
public Set<Comment> getComments() {
return comments;
}
// setters
}
Журнал аудита
@Entity
@SequenceGenerator(name = "quasar_log_id_seq", sequenceName = "quasar_log_id_seq")
public class AuditLog extends AbstractLog {
private Set<AuditLogItem> items;
@OrderBy(clause = "date")
@OneToMany(mappedBy = "auditLog")
public Set<AuditLogItem> getItems() {
return items;
}
}
Журнал документации
@Entity
@SequenceGenerator(name = "quasar_log_id_seq", sequenceName = "quasar_log_id_seq")
public class DocumentationLog extends AbstractLog {
private Set<DocumentationLogItem> items;
@OrderBy(clause = "date")
@OneToMany(mappedBy = "documentationLog")
public Set<DocumentationLogItem> getItems() {
return items;
}
}
Комментарий
@Entity
@SequenceGenerator(name = "quasar_comment_id_seq", sequenceName = "quasar_comment_id_seq", initialValue = 1, allocationSize =1)
@Table(name = "quasar_comment")
public class Comment extends IdentifiableEntity {
private User user;
private String comment;
private AbstractLog abstractLog;
@Id
@Override
@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "quasar_comment_id_seq")
public Long getId() {
return super.getId();
}
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "id_user")
public User getUser() {
return user;
}
@Column(name = "comment", length = 300)
public String getComment() {
return comment;
}
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "audit_log_id", nullable = false)
public AbstractLog getAbstractLog() {
return abstractLog;
}
}
Вы заметите, что генератор последовательности идентификаторов одинаков для всех расширенных объектов AbstractLog
.
Цель состоит в том, чтобы объект Comment
был общим для всех расширенных объектов AbstractLog
. Возможно ли это с помощью аннотации @MappedSuperclass
? Если бы я использовал @Inheritance
аннотацию, класс AbstractLog тоже был бы создан, но я этого не хочу. В настоящее время выдается ссылка на ошибку неизвестного объекта.
Ответ №1:
@MappedSuperclass используется для наследования свойств, но поскольку он не представляет сущность, вы можете использовать отношения сущностей, поэтому вам остаются только базовые типы, генерация идентификаторов и оптимистичная версия блокировки.
Если вы не хотите, чтобы базовый класс был отдельной таблицей (например, таблица для каждого подкласса), вы можете использовать стратегию таблица для конкретного класса. У каждого объекта будет своя таблица, а унаследованные свойства будут удобны только для Java, поскольку они будут дублироваться в каждой таблице SQL.
Таким образом, вы можете заменить @MappedSuperclass на:
@Inheritance(InheritanceType.TABLE_PER_CLASS)
Но согласно Java Persistence wiki:
По умолчанию используется наследование одной таблицы, а таблица для каждого класса является необязательной функцией спецификации JPA, поэтому не все поставщики могут ее поддерживать.
Hibernate поддерживает его, но если вы планируете использовать другого поставщика JPA, у вас может не быть его поддержки.