Kann ich eine eingebettete Hibernate Einheit nicht-nullable machen?
-
19-09-2019 - |
Frage
Was ich will:
@Embedded(nullable = false)
private Direito direito;
Doch wie Sie wissen, gibt es kein solches Attribut zu @Embeddable.
Gibt es einen richtigen Weg, dies zu tun? Ich will nicht Abhilfen.
Lösung
Fähiges Komponenten (oder Verbundelemente, was auch immer Sie sie nennen wollen) in der Regel mehr enthalten als eine Eigenschaft und damit abgebildet werden, um mehr als eine Spalte. Die gesamte Komponente ist null kann daher auf unterschiedliche Weise behandelt werden; J2EE-Spezifikation schreibt nicht vor, eine oder andere Weise.
hält Hibernate Komponente NULL sein, wenn alle seine Eigenschaften NULL sind (und umgekehrt). Sie können also eine deklarieren (jede) der Eigenschaften (innerhalb @Embeddable
oder als Teil @AttributeOverride
auf @Embedded
entweder) nicht null zu sein, zu erreichen, was Sie wollen.
Alternativ, wenn Sie Hibernate Validator verwenden Sie Ihre Immobilie mit @NotNull
mit Anmerkungen versehen können, obwohl dies nur in App-Level-Kontrolle führen wird, nicht db-Ebene.
Andere Tipps
Es ist möglich, "hibernate.create_empty_composites.enabled", da Hibernate 5.1 zu verwenden, um dieses Verhalten zu ändern (siehe https://hibernate.atlassian.net/browse/HHH-7610 )
Fügen Sie Dummy-Feld in der Klasse, die @Embeddable markiert ist.
@Formula("0")
private int dummy;
Auch ich war nicht mit einem der Vorschläge bisherigen begeistert, so dass ich einen Aspekt geschaffen, das für mich behandeln würde.
Dies ist nicht vollständig getestet, und auf jeden Fall nicht getestet gegen Sammlungen von eingebetteten Objekten, so käufer passen. Doch für mich scheint bisher geleistete Arbeit.
Grundsätzlich fängt die Getter zum @Embedded
Feld und stellt sicher, dass das Feld aufgefüllt wird.
public aspect NonNullEmbedded {
// define a pointcut for any getter method of a field with @Embedded of type Validity with any name in com.ia.domain package
pointcut embeddedGetter() : get( @javax.persistence.Embedded * com.company.model..* );
/**
* Advice to run before any Embedded getter.
* Checks if the field is null. If it is, then it automatically instantiates the Embedded object.
*/
Object around() : embeddedGetter(){
Object value = proceed();
// check if null. If so, then instantiate the object and assign it to the model.
// Otherwise just return the value retrieved.
if( value == null ){
String fieldName = thisJoinPoint.getSignature().getName();
Object obj = thisJoinPoint.getThis();
// check to see if the obj has the field already defined or is null
try{
Field field = obj.getClass().getDeclaredField(fieldName);
Class clazz = field.getType();
value = clazz.newInstance();
field.setAccessible(true);
field.set(obj, value );
}
catch( NoSuchFieldException | IllegalAccessException | InstantiationException e){
e.printStackTrace();
}
}
return value;
}
}
Sie können einen Nullsafe Getter verwenden.
public Direito getDireito() {
if (direito == null) {
direito = new Direito();
}
return direito;
}