在JPA中更新现有实体

时间:2017-09-01 23:23:00

标签: java hibernate jpa persistence

我使用JPA和Hibernate 5.2.10.Final(Oracle数据库),并在Weblogic 12.2.1上部署。

我们说我有2个表:CustomerLastActivity

Customer {
  id int,
  name String,
  last_activity_id int not null
}

LastActivity {
  id int,
  customerName String,
  date Date
}

有一种One to Many关系:Customer只有一个Activity而一个Activity有很多Customers

我有添加Customer的功能,当LastActivity表中的记录不存在时,必须创建Customer表中的记录,否则日期必须更新。

我的代码看起来像这样(为了问题而简化):

public Response createCustomer(Request request) {
  String name = request.getName();
  Customer customer = new Customer(name);
  LastActivity activity = activityDao.findByCustomerName(name)
      .orElseGet(LastActivity.from(name));
  activity.setDate(ZonedDateTime.now());
  customer.setActivity(activityDao.update(activity));
  return Response.of(customer);
}

我的update方法很简单:

return entityManager.merge(entity);

当我添加一个尚未存在的新CustomerActivity时 - 它会使用我指定的日期正确创建。问题是活动已经存在 - 更新没有发生。在日志中,Activities表上只有一个选择查询,然后在Customers表上正确插入,但日期是旧的。

我尝试过的一些事情:

public T update(T entity) {
  EntityManager manager = getEntityManager();
  T updated = manager.contains(entity) ? entity : manager.persist(entity);
  manager.flush();
  return updated;
}

同样的事情,没有改变。也:

  • 不用冲洗
  • 执行merge而不是仅在包含返回true时返回实体
  • 单独冲洗
  • 因为该实体是"附加"
  • ,所以没有

尝试添加CascadeType.MERGE ...仍然没有。唯一有用的是:

public T update(T entity) {
  EntityManager manager = getEntityManager();
  manager.detach(entity);
  return manager.merge(entity);
}

它完成了我想要它做的事情,但它在Activity表上添加了额外的选择查询(只需ID,但仍然,我想避免这样做。)

我实际上设法解决了#34;使用CriteriaUpdate的问题,但我不喜欢这个,似乎我缺乏关于JPA / Hibernate的一些基本知识,所以我不想这样离开它。

0 个答案:

没有答案