我可以使用Hibernate仅更新一个关系(一个字段)

时间:2015-11-25 11:27:30

标签: java hibernate

我有下一个关系:

@Entity
@Table(name = "STOCK", uniqueConstraints = @UniqueConstraint(columnNames = { "CODE", "INTERVAL", "DATE" }) )
public class StockEntity {

.....
many other fields like collections
.....

@ElementCollection
@CollectionTable(name = "PARAMETERS", joinColumns = @JoinColumn(name="SETTING_ID"))
@OneToMany(cascade = CascadeType.ALL, fetch = FetchType.EAGER)
@MapKeyEnumerated(EnumType.STRING)
private Map<LocalSetting.SettingType, LocalSetting> parameters = new HashMap<>();

}


@Entity
@Table(name = "LOCAL_SETTING")
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public class LocalSetting {

    @Id
    @Column(name = "SETTING_ID", unique = true, nullable = false)
    @GeneratedValue(strategy = GenerationType.SEQUENCE)
    private long settingId;
    .....
}

当我使用我的DAO时:

@Override
public void updateStocks(List<StockEntity> stocks) {
    Session session = sessionFactory.getCurrentSession();

    stocks.forEach(stock -> {
        session.update(stock);
        session.flush();
        session.clear();
    });
}

在日志跟踪中我注意到,当我只更改“参数”时,将更新StockEntity中的所有字段, 这意味着我也在更新很多其他参数,我可以简单地跳过

当我尝试使用下一个代码更新“参数”时:

@Override
public void updateParameters(List<StockEntity> stocks) {
    stocks.forEach(stock -> {
        for (Map.Entry<LocalSetting.SettingType, LocalSetting> entry : stock.getParameters().entrySet()) {
            sessionFactory.getCurrentSession().saveOrUpdate(entry.getValue());
        }
    });
}

但过程将像我将更新整个StockEntity一样 ,也许我可以分离另一个字段,直到我完成更新“参数”

2 个答案:

答案 0 :(得分:1)

按照规定here

session.update()

update将实体作为参数。但是您传递的是Map(我假设您要保存的LocalSetting实体)。

据我所知,不可能使用update(..)方法持久化对象集合。 请尝试以下代码来检查它是否适合您:

@Override
public void updateParameters(Map<LocalSetting.SettingType, LocalSetting> parameters) 
{

    for (Map.Entry<String, String> entry : map.entrySet())
    {
        sessionFactory.getCurrentSession().update(entry.getValue());
    }
    sessionFactory.getCurrentSession().commit();
    sessionFactory.getCurrentSession().close();  
}

是什么让我建议这个答案更多是您的问题(org.hibernate.MappingException)中的例外情况,它基本上告诉我们我们正在更新未映射的实体。

答案 1 :(得分:1)

您必须使用动态插入才能仅更新一个字段。语法是:

@org.hibernate.annotations.Entity(
    dynamicInsert = true
)

您可以在此处查看示例:Dynamic insert example

您还可以阅读此帖子why hibernate dynamic insert false by default,以便了解使用dynamicInsert = true时可能遇到的问题