2016-08-18 3 views
1

У меня есть объект Пружина данных (с использованием JPA ж/Hibernate и MySQL) определяются как, например:Пружина изменения JPA данные лица не сохранилось

@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; 

У меня есть следующий репозиторий для этого объекта:

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); 
} 

Теперь - в контроллере я собираю набор данных, обновляя один из его атрибутов, и я ожидал, что это изменение атрибута будет сброшено в БД, но оно никогда не будет.

@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; 
    } 

Спасибо

+0

Итак, я уверен, что объект, возвращающийся из запроса данных Spring, не управляется (по крайней мере, не так, как я думаю). Если я запустил 'entityManager.contains (dataset)', это возвращает 'false'. Я могу получить изменения, которые сохраняются, запустив 'datasetRepo.save (dataset)', который объединяет изменения, однако может кто-то сказать мне, почему сущность, которая возвращается из запроса, не управляется и как я могу заставить ее управлять ? –

+1

Попробуйте аннотировать ваш метод 'storeDataset' как' @ Transactional' – Pau

+0

Вам нужно включить журналы запросов на гибернацию, чтобы узнать, что происходит под обложками. –

ответ

0

Вы должны аннотировать способ отображения запроса с @Transactional.

Почему? Если вы хотите изменить объект в памяти, а затем он прозрачно обновляется в базе данных, вам нужно сделать это внутри активной транзакции.

Не забывайте, что вы используете JPA (spring-data использует JPA), и если вы хотите, чтобы ваше лицо было в managed state, вам нужна активная транзакция.

См:

Transparent Update После того, как объект объект извлекается из базы данных (независимо от того, каким образом) он просто может быть изменен в памяти из внутри активная сделка:

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

em.getTransaction().begin(); 
employee.setNickname("Joe the Plumber"); 
em.getTransaction().commit(); 
Смежные вопросы