2016-08-18 3 views
1

I eine Feder Datenentität haben (unter Verwendung von JPA w/Ruhezustand und MySQL), definiert als solche:Feder Daten JPA Entität Änderung nicht beibehalten werden

@Entity 
@Table(name = "dataset") 
public class Dataset { 

    @Id 
    @GenericGenerator(name = "generator", strategy = "increment") 
    @GeneratedValue(generator = "generator") 
    private Long id; 
    @Column(name = "name", nullable = false) 
    private String name; 
    @Column(name = "guid", nullable = false) 
    private String guid; 
    @Column(name = "size", nullable = false) 
    private Long size; 
    @Column(name = "create_time", nullable = false) 
    private Date createTime; 
    @OneToOne(optional = false) 
    @JoinColumn(name = "created_by") 
    private User createdBy; 
    @Column(name = "active", nullable = false) 
    private boolean active; 
    @Column(name = "orig_source", nullable = false) 
    private String origSource; 
    @Column(name = "orig_source_type", nullable = false) 
    private String origSourceType; 
    @Column(name = "orig_source_org", nullable = false) 
    private String origSourceOrg; 
    @Column(name = "uri", nullable = false) 
    private String uri; 
    @Column(name = "mimetype", nullable = false) 
    private String mimetype; 
    @Column(name = "registration_state", nullable = false) 
    private int registrationState; 
    @OneToMany(fetch = FetchType.EAGER, cascade = {CascadeType.ALL}) 
    @JoinColumn(name = "dataset_id") 
    @JsonManagedReference 
    private List<DatasetFile> datasetFiles; 

Ich habe folgende Repository für diese Entität:

public interface DatasetRepo extends JpaRepository<Dataset, Long> { 

    @Query("SELECT CASE WHEN COUNT(p) > 0 THEN 'true' ELSE 'false' END FROM Dataset p WHERE p.uri = ?1 and p.registrationState>0") 
    public Boolean existsByURI(String location); 

    @Query("SELECT a FROM Dataset a LEFT JOIN FETCH a.datasetFiles c where a.registrationState>0") 
    public List<Dataset> getAll(Pageable pageable); 

    @Query("SELECT a FROM Dataset a LEFT JOIN FETCH a.datasetFiles c WHERE a.registrationState>0") 
    public List<Dataset> findAll(); 

    @Query("SELECT a FROM Dataset a LEFT JOIN FETCH a.datasetFiles c where a.guid= ?1") 
    public Dataset findByGuid(String guid); 
} 

Jetzt - In einer Steuerung, ich hole ein Dataset, eines seiner Attribute zu aktualisieren, und ich würde erwarten, dass diese Attributänderung an die DB geleert wird, aber es ist nie.

@RequestMapping(value = "/storeDataset", method = RequestMethod.GET) 
    public @ResponseBody 
    WebServiceReturn storeDataset(
      @RequestParam(value = "dsGUID", required = true) String datasetGUID, 
      @RequestParam(value = "stType", required = true) String stType) { 
     WebServiceReturn wsr = null; 
     logger.info("stType: '" + stType + "'"); 
     if (!stType.equals("MongoDB") && !stType.equals("Hive") && !stType.equals("HDFS")) { 
      wsr = getFatalWebServiceReturn("Invalid Storage type '" + stType + "'"); 
     } else if (stType.equals("MongoDB")) { 
      /* Here is where I'm reading entity from Repository */ 
      Dataset dataset = datasetRepo.findByGuid(datasetGUID); 
      if (dataset != null) { 
       MongoLoader mongoLoader = new MongoLoader(); 
       boolean success = mongoLoader.loadMongoDB(dataset); 
       logger.info("Success: " + success); 
       if (success) { 
        /* Here is where I update entity attribute value, this is never flushed to DB */ 
        dataset.setRegistrationState(1); 
       } 
       wsr = getWebServiceReturn(success ? 0 : -1, "Successfully loaded dataset files into " + stType + " storage", "Failed to load dataset files into " + stType + " storage"); 
      } 

     } 
     return wsr; 
    } 

Danke

+0

Also - ich bin mir ziemlich sicher, dass die Entität, die von der Spring-Datenabfrage zurückkommt, nicht verwaltet wird (zumindest nicht so, wie ich das denke). Wenn ich 'entityManager.contains (dataset) 'starte, gibt das' false' zurück. Ich kann die Änderungen durch das Ausführen von 'datasetRepo.save (Dataset)' erhalten, wodurch die Änderungen zusammengeführt werden. Allerdings kann mir jemand sagen, warum die Entität, die von der Abfrage zurückkommt, nicht verwaltet wird und wie ich sie verwalten kann ? –

+1

Versuchen Sie, Ihre Methode 'storeDataset' mit' @Transactional' zu kommentieren. – Pau

+0

Sie sollten die Abfrageprotokolle im Ruhezustand aktivieren, um zu sehen, was unter den Deckblättern passiert. –

Antwort

0

Sie müssen die Methode der Anfrage-Mapping mit @Transactional zu annotieren.

Warum? Wenn Sie ein Objekt im Speicher ändern möchten und es dann in der Datenbank transparent aktualisiert wird, müssen Sie es in einer aktiven Transaktion ausführen.

Vergessen Sie nicht, dass Sie JPA verwenden (spring-data verwendet JPA) und wenn Sie möchten, dass Ihre Entität in einem managed state sein wird, benötigen Sie eine aktive Transaktion.

See:

Transparent-Update Sobald ein Unternehmen Objekt aus der Datenbank abgerufen (egal welche Art und Weise) kann es einfach im Speicher modifiziert werden von innen ein aktive Transaktion:

Employee employee = em.find(Employee.class, 1); 

em.getTransaction().begin(); 
employee.setNickname("Joe the Plumber"); 
em.getTransaction().commit(); 
Verwandte Themen