2016-05-05 8 views
1

Ich erstellte benutzerdefinierte Ergebnis Transformator, der BasicTransformerAdapter erweitert. In transformTuple-Methode erstelle ich neues Objekt der Entität:Hibernate ResultTransformer und gwt requestfactory

@Override 
    public Object transformTuple(Object[] tuple, String[] aliases) { 
    RegistryRow row = new RegistryRow(); 
    DataRow dataRow = new DataRow(); 
    Registry registry = new Registry(); 

    for (int i = 0; i < aliases.length; i++) { 
     if ("id".equals(aliases[i])) { 
     row.setId((Long) tuple[i]); 
     } else if ("entityVersion".equals(aliases[i])) { 
     row.setEntityVersion((Long) tuple[i]); 
     } else if ("gridRowId".equals(aliases[i])) { 
     dataRow.setId((Long) tuple[i]); 
     } else if ("rowEntityVersion".equals(aliases[i])) { 
     dataRow.setEntityVersion((Long) tuple[i]); 
     } else if (tuple[i] != null && aliases[i] != null && aliases[i].startsWith("set")) { 
     try { 
      DataType type = DataRow.getDataType(tuple[i].getClass()); 
      Method m = DataRow.class.getMethod(aliases[i], type.getDataClass()); 
      m.invoke(dataRow, DataRow.castValue(tuple[i], type)); 
     } catch (Exception e) { 
      LOG.error("--Error while setting dataRow data: ", e); 
     } 
     } else if ("registryCode".equals(aliases[i])) { 
     registry.setCode((String) tuple[i]); 
     } else if ("registryEntityVersion".equals(aliases[i])) { 
     registry.setEntityVersion((Long) tuple[i]); 
     } 
    } 

    row.setRegistry(registry); 
    row.setGridRow(dataRow); 

    return row; 
    } 

Alles funktioniert gut. Es wird eine Liste von RegistryRow-Objekten erstellt. Auf Client-Seite ist es RegistryRowProxy die wie folgt aussieht:

@ProxyFor(value = RegistryRow.class, locator = LongEntityLocator.class) 
public interface RegistryRowProxy extends EntityProxy, BeanModelTag { 

    Long getId(); 

    DataRowProxy getGridRow(); 

    Date getCreateDate(); 

    RegistryProxy getRegistry(); 

    Long getDataId(); 
} 

Es in gwt RequestFactory verwendet wird, die Liste Dienst aufruft.

getRequestFactory().registryRow().list(registry.getCode(), paramsId).with("gridRow").fire(receiver); 

Es gibt Daten zurück, alles ist in Ordnung, aber wenn ich show_sql einschalte, macht es zusätzliche Selects zur Datenbank. Fragen wie diese:

select "all_columns" from RegistryRow where id = ?; 
select "all_columns" from DataRow where id = ?; 

Diese Abfragen werden so oft ausgeführt, wie Zeilen in der Liste vorhanden sind. Ich weiß nicht, wie ich diese zusätzlichen Abfragen, die Einfluss auf die Leistung haben, loswerden kann. Weißt du, warum es zusätzliche Abfragen für die Datenbank gibt? (ich hinzufügen, dass es in Entity-Variablen sind, die wie folgt aussieht:

@JoinColumn(name = "T_DATA_ROWS_ID") 
    @NotNull 
    private DataRow gridRow; 

aber nicht alle von ihnen)

Update 1: Annotation wie folgt aussehen genau:

@OneToOne(fetch = FetchType.EAGER, cascade = CascadeType.ALL) 
@JoinColumn(name = "T_DATA_ROWS_ID") 
@NotNull 
private DataRow gridRow; 

Und Trotzdem werden für jede Zeile Abfragen ausgeführt.

Antwort

0

Sie teilen RequestFactory mit, dass sie eine RegistryRowProxy abrufen und ihre gridRow Untereigenschaft erneut abrufen möchten (mithilfe von with("gridRow")).
Also auf Ihrem Backend RequestFactory wird intern rufen Sie Ihre getGridRow Getter und dies wird dazu führen, dass Hibernate die gridRow Beziehung laden (faul).
Um die Unterabfragen zu vermeiden, müssen Sie Hibernate mitteilen, dass die Beziehung schnell geladen werden soll.
JPA sollte dies standardmäßig für @OneToOne und @ManyToOne Beziehungen tun.

Ich gehe davon aus, Ihr Problem ist, dass Sie die @OneToOne Anmerkung auf Ihre DataRow dataGrid Eigenschaft fehlen:

@JoinColumn(name = "T_DATA_ROWS_ID",nullable=false) 
@NotNull 
@OneToOne 
private DataRow gridRow; 
+0

Im Code sieht es so aus: '@OneToOne (Fetch = FetchType.EAGER, Kaskade = CascadeType.ALL) @JoinColumn (name = "T_DATA_ROWS_ID") @NotNull private DataRow gridRow; ' – Caroline