Ответ 1
Я не думаю, что с аннотациями можно "игнорировать" поле из адреса во встроенных объектах.
Обходным путем является создание базового типа Address без электронной почты и ExtendedAddress (подкласс адреса) с полем электронной почты.
Я переношу некоторые классы в файле hibm.xml Hibernate на аннотации JPA.
У нас есть вложенный класс Address
, который используется в нескольких местах. Каждое место использует другое подмножество свойств в адресе.
(геттеры/сеттеры опущены для краткости)
@Embeddable
public class Address {
String email;
String address;
String city;
String state;
String zip;
String country;
}
@Entity
@Table(name="customer")
public class Customer {
@Embedded
@AttributeOverrides({
@AttributeOverride(name="address", [email protected](name="ship_addr"),
@AttributeOverride(name="city", [email protected](name="ship_city"),
@AttributeOverride(name="state", [email protected](name="ship_state"),
@AttributeOverride(name="zip", [email protected](name="ship_zip"),
@AttributeOverride(name="country", [email protected](name="ship_country")
})
Address shippingAddress;
@Embedded
@AttributeOverrides({
@AttributeOverride(name="address", [email protected](name="bill_addr"),
@AttributeOverride(name="city", [email protected](name="bill_city"),
@AttributeOverride(name="state", [email protected](name="bill_state"),
@AttributeOverride(name="zip", [email protected](name="bill_zip")
})
Address billingAddress;
}
Обратите внимание, что в этом надуманном примере shippingAddress использует Address.country, но billingAddress не работает; и ни один из них не использует Address.email.
Проблема в том, что Hibernate выводит теги @Column
для любого столбца, где я явно не предоставил его.
Я попробовал добавить @Transient
ко всем полям Address
, но кажется, что @AttributeOverride
не trump @Transient
.
Есть ли какое-либо обходное решение для этого?
Я не думаю, что с аннотациями можно "игнорировать" поле из адреса во встроенных объектах.
Обходным путем является создание базового типа Address без электронной почты и ExtendedAddress (подкласс адреса) с полем электронной почты.
Моим советом было бы создать новый объект под названием PartialAddress/NationalAddress/BillingAddress. Это будет использоваться только для отображения JPA и не будет отображаться на интерфейсе Customer:
private PartialAddress billingAddress;
public Address getBillingAddress() {
return billingAddress.toAddress();
}
В противном случае, я придумал несколько уродливое обходное решение этой проблемы, возможно, это сработает и для вас. Вместо того, чтобы сопоставлять поле с реальным столбцом, я возвращаю константу null:
@Embedded
@AttributeOverrides({
@AttributeOverride(name="address", [email protected](name="bill_addr"),
@AttributeOverride(name="city", [email protected](name="bill_city"),
@AttributeOverride(name="state", [email protected](name="bill_state"),
@AttributeOverride(name="zip", [email protected](name="bill_zip"),
@AttributeOverride(name="country", [email protected](name="bill_id + null"),
})
Address billingAddress;
Я использую Oracle и EclipseLink, также работает на Hibernate 3.6. И я тестировал его только на объектах только для чтения. Хотя теоретически установка атрибутов insertable
и updatable
на false должна быть достаточной.