Hibernate version:
3.2.6
Name and version of the database you are using:
MySQL 5.0.1 (Hibernate is configured for MySQL5InnoDB dialect)
Hello,
I've got a simple OneToOne relationship between Site and SiteRuntime entities (PKs are not shared or anything like that), where SiteRuntime contains some info aboud Site.
My use case is simple:
Code:
Site site = new Site();
SiteRuntime rt = new SiteRuntime();
site.setRuntime(rt);
rt.setSite(site);
em.persist(site); //ok
And later, in a different transaction:
Code:
em.createQuery("delete from Site s where s.name='text'").executeUpdate(); // exception, see below.
The exception:
Code:
javax.persistence.EntityExistsException: org.hibernate.exception.ConstraintViolationException: could not execute update query
at org.hibernate.ejb.AbstractEntityManagerImpl.throwPersistenceException(AbstractEntityManagerImpl.java:612)
at org.hibernate.ejb.QueryImpl.executeUpdate(QueryImpl.java:58)
...
Caused by: com.mysql.jdbc.exceptions.MySQLIntegrityConstraintViolationException: Cannot delete or update a parent row: a foreign key constraint fails (`db1/site_runtime`, CONSTRAINT `FK2627A2C06DE06746` FOREIGN KEY (`SITE_ID`) REFERENCES `site` (`SITE_ID`))
at com.mysql.jdbc.SQLError.createSQLException(SQLError.java:1011)
...
I also verified that "ON DELETE CASCADE" is NOT added at the db level - bad news since I do bulk deletion which will fail without it. BUT: if the relationship between Site and SiteRuntime was OneToMany, the db schema DOES contain "ON DELETE CASCADE" and all is OK.
Any ideas what I'm doing wrong?
Here are the entities:
Code:
@Entity
public class Site implements Serializeable {
public Site() {}
@Id @GeneratedValue @Column(name = "SITE_ID", nullable = false)
private Long id;
public Long getId() { return id; }
public void setId(Long id) { this.id = id; }
@Column(name = "SITE_NAME", nullable = true)
private String name;
public String getName() { return this.name; }
public void setName(String siteName) { this.name = siteName; }
// if I change the relationship below to OneToMany, all is OK,
// but then I'm forced to change the type of the member to some
// collection, and I wish to avoid that...
@OnDelete(action=OnDeleteAction.CASCADE)
@OneToOne(cascade=CascadeType.ALL, fetch=FetchType.LAZY, mappedBy="site")
private SiteRuntime runtime;
public SiteRuntime getRuntime() { return runtime; }
public void setRuntime(SiteRuntime runtime) { this.runtime = runtime; }
...
}
@Entity
public class SiteRuntime implements Serializeable {
public SiteRuntime() {
}
@Id
@GeneratedValue
@Column(name = "SITE_RUNTIME_ID", nullable = false)
private Long id;
public Long getId() { return id; }
public void setId(Long id) { this.id = id; }
@OneToOne(fetch = FetchType.LAZY, optional=false)
@JoinColumn(name="SITE_ID", nullable=false)
private Site site;
public Site getSite() { return site; }
public void setSite(Site site) {
this.site = site;
if (site != null) this.siteId = site.getId();
}
@Column(name="SITE_ID", nullable=false, insertable=false, updatable=false)
private Long siteId;
public Long getSiteId() { return siteId; }
public void SiteId(Long siteId) { this.siteId = siteId; }
...
}