Hibernate 数据库中唯一密钥的重复项
我不熟悉Hibernate,因为遇到了一个问题,我放弃了尝试更新/合并mysql数据库表中的一个条目。我在表中的一列上有一个唯一的约束,我想在使用hibernate更改数据库中的某些值后对其进行更新,但它永远不起作用: 这是我的java类: 我正在使用session.mergeweatherToUpdate;在更改某些值后将其合并回数据库。但是合并失败,甚至saveOrUpdate也失败了 我的数据库中已经有一个citylondon条目,我想从表中提取它,合并一些更改并将其上传回数据库 以下是我得到的错误: 我尝试使用EntityManager使用persist方法解决它,但我无法在安装程序中安装它。我尝试了不同的方法来更新会话,但没有任何效果。我觉得完全迷路了 编辑: 这就是我试图拯救的方式:Hibernate 数据库中唯一密钥的重复项,hibernate,spring-boot,Hibernate,Spring Boot,我不熟悉Hibernate,因为遇到了一个问题,我放弃了尝试更新/合并mysql数据库表中的一个条目。我在表中的一列上有一个唯一的约束,我想在使用hibernate更改数据库中的某些值后对其进行更新,但它永远不起作用: 这是我的java类: 我正在使用session.mergeweatherToUpdate;在更改某些值后将其合并回数据库。但是合并失败,甚至saveOrUpdate也失败了 我的数据库中已经有一个citylondon条目,我想从表中提取它,合并一些更改并将其上传回数据库 以下是我
public void updateCityFromDatabase(Weather weatherToUpdate,String city){
// Create Session
Session session = factory.getCurrentSession();
// Begin Transaction
session.getTransaction().begin();
try{
LOGGER.info("reading the weather data...");
Query query = session.createQuery("from Weather wt where wt.city = :city");
query.setParameter("city",weatherToUpdate.getCity());
List<Weather> retrievedWeatherData = query.list();
if(retrievedWeatherData.get(0).getCity().equals(weatherToUpdate.getCity())){
LOGGER.info("City already exists and parameters are same");
session.save(weatherToUpdate);
}else{
session.clear();
}
session.getTransaction().commit();
LOGGER.info("City parameters Updated!");
factory.close();
}
首先,您必须了解在Hibernate中管理实体实例的工作方式。你可以从阅读指南开始 在您的示例中,从weatherToUpdate实体复制属性后,需要将retrievedWeatherData.get0对象作为参数传递给merge函数 复制可以手动完成,也可以使用ApacheCommons库中的helper实用程序函数完成。请参阅 因此,您的代码变成:
List<Weather> retrievedWeatherData = query.list();
Weather firstRetrievedWeatherData = retrievedWeatherData.get(0);
if (firstRetrievedWeatherData.getCity().equals(weatherToUpdate.getCity())) {
// Manually Copy properties values from weatherToUpdate to retrieved object
// Property value for id is excluded
firstRetrievedWeatherData.setCity(weatherToUpdate.getCity());
firstRetrievedWeatherData.setHeadline(weatherToUpdate.getHeadline());
// Copy more other properties
// Generate an update sql statement instead of insert
session.merge(firstRetrievedWeatherData);
}
最后,如果您选择使用Spring或Spring boot,我建议您使用来管理hibernate实体。这一点都不难,您可以不再担心管理数据库事务启动、提交、回滚,而且您还可以获得一些功能。您是否尝试过保存?相同错误java.sql.SQLIntegrityConstraintViolationException:Duplicate entry。。我没有得到的是,我只想更新字段并将其设置回。。但它不允许我。陷入这样的问题是非常令人沮丧的。我现在损失了2-3个小时。你能告诉我你是怎么做到的吗?是的,我已经更新了我的代码。请检查一下你的方法是否有效。我试过了,现在没有错误了。我现在就知道了,所以您需要先从数据库中获取数据,然后执行保存、更新操作。您可以检索一个hibernate管理的实体,您可以将其视为数据库中的记录,在其中执行操作。。不过,我建议你花点时间阅读。好的。是的,我正在读一些书,也在看一些视频来理解。非常感谢!
public void updateCityFromDatabase(Weather weatherToUpdate,String city){
// Create Session
Session session = factory.getCurrentSession();
// Begin Transaction
session.getTransaction().begin();
try{
LOGGER.info("reading the weather data...");
Query query = session.createQuery("from Weather wt where wt.city = :city");
query.setParameter("city",weatherToUpdate.getCity());
List<Weather> retrievedWeatherData = query.list();
if(retrievedWeatherData.get(0).getCity().equals(weatherToUpdate.getCity())){
LOGGER.info("City already exists and parameters are same");
session.save(weatherToUpdate);
}else{
session.clear();
}
session.getTransaction().commit();
LOGGER.info("City parameters Updated!");
factory.close();
}
List<Weather> retrievedWeatherData = query.list();
Weather firstRetrievedWeatherData = retrievedWeatherData.get(0);
if (firstRetrievedWeatherData.getCity().equals(weatherToUpdate.getCity())) {
// Manually Copy properties values from weatherToUpdate to retrieved object
// Property value for id is excluded
firstRetrievedWeatherData.setCity(weatherToUpdate.getCity());
firstRetrievedWeatherData.setHeadline(weatherToUpdate.getHeadline());
// Copy more other properties
// Generate an update sql statement instead of insert
session.merge(firstRetrievedWeatherData);
}