我使用Hibernate保存对象时遇到以下错误:
object references an unsaved transient instance - save the transient instance before flushing
我使用Hibernate保存对象时遇到以下错误:
object references an unsaved transient instance - save the transient instance before flushing
这个错误有很多可能性,其他可能性也可能出现在添加页面或编辑页面。在我这个案例中,我试图保存一个AdvanceSalary对象。问题是,在编辑AdvanceSalary时,employee.employee_id为空,因为我没有设置employee.employee_id。我使用了一个隐藏字段并进行了设置,我的代码完全正常运行。
@Entity(name = "ic_advance_salary")
@Table(name = "ic_advance_salary")
public class AdvanceSalary extends BaseDO{
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Column(name = "id")
private Integer id;
@ManyToOne(fetch = FetchType.EAGER)
@JoinColumn(name = "employee_id", nullable = false)
private Employee employee;
@Column(name = "employee_id", insertable=false, updatable=false)
@NotNull(message="Please enter employee Id")
private Long employee_id;
@Column(name = "advance_date")
@DateTimeFormat(pattern = "dd-MMM-yyyy")
@NotNull(message="Please enter advance date")
private Date advance_date;
@Column(name = "amount")
@NotNull(message="Please enter Paid Amount")
private Double amount;
@Column(name = "cheque_date")
@DateTimeFormat(pattern = "dd-MMM-yyyy")
private Date cheque_date;
@Column(name = "cheque_no")
private String cheque_no;
@Column(name = "remarks")
private String remarks;
public AdvanceSalary() {
}
public AdvanceSalary(Integer advance_salary_id) {
this.id = advance_salary_id;
}
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public Employee getEmployee() {
return employee;
}
public void setEmployee(Employee employee) {
this.employee = employee;
}
public Long getEmployee_id() {
return employee_id;
}
public void setEmployee_id(Long employee_id) {
this.employee_id = employee_id;
}
}
this.lastName = lastName;
this.isAdmin = isAdmin;
this.accountStatus = "Active";
this.setNewPassword(password);
this.timeJoin = new Date();
create();
this.lastName = lastName;
this.isAdmin = isAdmin;
this.accountStatus = "Active";
this.timeJoin = new Date();
create();
this.setNewPassword(password);
在Hibernate中,还有另一种可能会导致此错误。您可能会将对象A
的未保存引用设置为已附加实体B
,并想要持久化对象C
。即使在这种情况下,您仍将获得上述错误。
案例1: 当我尝试创建一个父对象并将其引用保存到其子对象中,然后执行其他DELETE / UPDATE查询(JPQL)时,我遇到了此异常。因此,我在创建父对象和使用相同的父引用创建子对象后,只需flush()新创建的实体即可。这对我起作用了。
案例2:
父类
public class Reference implements Serializable {
@Id
@Column(precision=20, scale=0)
private BigInteger id;
@Temporal(TemporalType.TIMESTAMP)
private Date modifiedOn;
@OneToOne(mappedBy="reference")
private ReferenceAdditionalDetails refAddDetails;
.
.
.
}
子类:
public class ReferenceAdditionalDetails implements Serializable{
private static final long serialVersionUID = 1L;
@Id
@OneToOne
@JoinColumn(name="reference",referencedColumnName="id")
private Reference reference;
private String preferedSector1;
private String preferedSector2;
.
.
}
.
.
reference.setRefAddDetails(null);
reference = referenceDao.create(reference);
entityManager.flush();
.
.
解决这个问题的简单方法是保存两个实体。 首先保存子实体,然后保存父实体。 因为父实体依赖于子实体的外键值。
下面是一个简单的一对一关系示例
insert into Department (name, numOfemp, Depno) values (?, ?, ?)
Hibernate: insert into Employee (SSN, dep_Depno, firstName, lastName, middleName, empno) values (?, ?, ?, ?, ?, ?)
Session session=sf.openSession();
session.beginTransaction();
session.save(dep);
session.save(emp);
@Entity
public class User {
@Id
private Long id;
}
@Entity
public class Address {
@Id
private Long id;
@JoinColumn(name="user_id")
@OneToOne
private User user;
}
interface AddressRepository extends JpaRepository<Address, Long> {
Address findByUser(User user);
}
User user = new User(); // this is transient, does not have id populated
// user.setId(1L) // works fine if this is uncommented
addressRepository.findByUser(user); // throws exception
错误的一个可能原因是父实体值的设置不存在;例如,对于部门-员工关系,您必须编写以下内容以修复错误:
Department dept = (Department)session.load(Department.class, dept_code); // dept_code is from the jsp form which you get in the controller with @RequestParam String department
employee.setDepartment(dept);