-->
These old forums are deprecated now and set to read-only. We are waiting for you on our new forums!
More modern, Discourse-based and with GitHub/Google/Twitter authentication built-in.

All times are UTC - 5 hours [ DST ]



Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 3 posts ] 
Author Message
 Post subject: TransientObjectException with Parent/Child relations
PostPosted: Wed Jun 30, 2010 5:10 pm 
Newbie

Joined: Fri Feb 10, 2006 2:20 pm
Posts: 9
Hi,

I have a basic one to many relation parent / child like in the chapter 21 of Hibernate references.
The cascade is from child to parent (persist cascade only because i don't want to delete the parent if I delete a child).
When I add a child to the parent and I save the child, I have a TransientObjectException...

Code:
@Entity
public class Parent implements Serializable {

  private static final long serialVersionUID = 1L;

  @Id
  @GeneratedValue(strategy = GenerationType.AUTO)
  private Long id;

  @OneToMany(mappedBy = "parent", orphanRemoval = true)
  private List<Child> childs;

  public List<Child> getChilds() {
    return childs;
  }

  public void setChilds(List<Child> childs) {
    this.childs = childs;
  }

  public void addChild(Child child) {
    if (childs == null) childs = new ArrayList<Child>();
    if (childs.add(child)) child.setParent(this);
  }

  public Long getId() {
    return id;
  }

  public void setId(Long id) {
    this.id = id;
  }
}


Code:
@Entity
public class Child implements Serializable {

  private static final long serialVersionUID = 1L;

  @Id
  @GeneratedValue(strategy = GenerationType.AUTO)
  private Long id;

  @ManyToOne(optional = false)
  @Cascade( { PERSIST, MERGE, REFRESH, SAVE_UPDATE, REPLICATE, LOCK, DETACH })
  private Parent parent;

  public Parent getParent() {
    return parent;
  }

  public void setParent(Parent parent) {
    this.parent = parent;
  }

  public Long getId() {
    return id;
  }

  public void setId(Long id) {
    this.id = id;
  }
}


Code:
@Test
public void test() {
  Parent parent = new Parent();
  Child child = new Child();
  parent.addChild(child);
  genericDao.saveOrUpdate(child);
}


But on the saveOrUpdate, I have this exception:

Code:
org.hibernate.TransientObjectException: object references an unsaved transient instance - save the transient instance before flushing: Child
  at org.hibernate.engine.ForeignKeys.getEntityIdentifierIfNotUnsaved(ForeignKeys.java:244)
  at org.hibernate.collection.AbstractPersistentCollection.getOrphans(AbstractPersistentCollection.java:911)
  at org.hibernate.collection.PersistentBag.getOrphans(PersistentBag.java:143)
  at org.hibernate.engine.CollectionEntry.getOrphans(CollectionEntry.java:373)
  at org.hibernate.engine.Cascade.deleteOrphans(Cascade.java:471)
  at org.hibernate.engine.Cascade.cascadeCollectionElements(Cascade.java:455)
  at org.hibernate.engine.Cascade.cascadeCollection(Cascade.java:362)
  at org.hibernate.engine.Cascade.cascadeAssociation(Cascade.java:338)
  at org.hibernate.engine.Cascade.cascadeProperty(Cascade.java:204)
  at org.hibernate.engine.Cascade.cascade(Cascade.java:161)
  at org.hibernate.event.def.AbstractSaveEventListener.cascadeAfterSave(AbstractSaveEventListener.java:476)
  at org.hibernate.event.def.AbstractSaveEventListener.performSaveOrReplicate(AbstractSaveEventListener.java:354)
  at org.hibernate.event.def.AbstractSaveEventListener.performSave(AbstractSaveEventListener.java:204)
  at org.hibernate.event.def.AbstractSaveEventListener.saveWithGeneratedId(AbstractSaveEventListener.java:130)
  at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.saveWithGeneratedOrRequestedId(DefaultSaveOrUpdateEventListener.java:210)
  at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.entityIsTransient(DefaultSaveOrUpdateEventListener.java:195)
  at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.performSaveOrUpdate(DefaultSaveOrUpdateEventListener.java:117)
  at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.onSaveOrUpdate(DefaultSaveOrUpdateEventListener.java:93)
  at org.hibernate.impl.SessionImpl.fireSaveOrUpdate(SessionImpl.java:677)
  at org.hibernate.impl.SessionImpl.saveOrUpdate(SessionImpl.java:669)
  at org.hibernate.engine.CascadingAction$5.cascade(CascadingAction.java:252)
  at org.hibernate.engine.Cascade.cascadeToOne(Cascade.java:392)
  at org.hibernate.engine.Cascade.cascadeAssociation(Cascade.java:335)
  at org.hibernate.engine.Cascade.cascadeProperty(Cascade.java:204)
  at org.hibernate.engine.Cascade.cascade(Cascade.java:161)
  at org.hibernate.event.def.AbstractSaveEventListener.cascadeBeforeSave(AbstractSaveEventListener.java:451)
  at org.hibernate.event.def.AbstractSaveEventListener.performSaveOrReplicate(AbstractSaveEventListener.java:288)
  at org.hibernate.event.def.AbstractSaveEventListener.performSave(AbstractSaveEventListener.java:204)
  at org.hibernate.event.def.AbstractSaveEventListener.saveWithGeneratedId(AbstractSaveEventListener.java:130)
  at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.saveWithGeneratedOrRequestedId(DefaultSaveOrUpdateEventListener.java:210)
  at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.entityIsTransient(DefaultSaveOrUpdateEventListener.java:195)
  at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.performSaveOrUpdate(DefaultSaveOrUpdateEventListener.java:117)
  at org.hibernate.event.def.DefaultSaveOrUpdateEventListener.onSaveOrUpdate(DefaultSaveOrUpdateEventListener.java:93)
  at org.hibernate.impl.SessionImpl.fireSaveOrUpdate(SessionImpl.java:677)
  at org.hibernate.impl.SessionImpl.saveOrUpdate(SessionImpl.java:669)
  at org.hibernate.impl.SessionImpl.saveOrUpdate(SessionImpl.java:665)


I've read a lot of post related to my problem on the web, but I didn't find any solution yet :-(
Any help would be very appreciated!
Thanks..


Top
 Profile  
 
 Post subject: Re: TransientObjectException with Parent/Child relations
PostPosted: Fri Jul 09, 2010 9:45 am 
Newbie

Joined: Fri Feb 10, 2006 2:20 pm
Posts: 9
The problem seems to be related to "orphanRemoval" because if I comment it on the parent:
Code:
@OneToMany(mappedBy = "parent" /*, orphanRemoval = true */)
private List<Child> childs;

It works! It save the child, then the parent.
But I really need the orphan to be deleted via the cascade when I remove a child from its parent.

I've opened a JIRA issue with a test case for this:
http://opensource.atlassian.com/project ... e/HHH-5364


Top
 Profile  
 
 Post subject: Re: TransientObjectException with Parent/Child relations
PostPosted: Fri Jul 09, 2010 5:09 pm 
Newbie

Joined: Fri Jul 09, 2010 4:13 pm
Posts: 2
Im not 100% about your problem b/c I use an older version of Hibernate with an XML configuration instead of an annotation based one.

However, it seems to be that your declarations might be a little off... Cascading means that when a parent is updated (save, update, delete, etc...) the operations trickle down to the children.

So you should only need to do:

parent.add(child1);
parent.add(child2);
session.saveOrUpdate(parent);

and the cascading will save the children as well. Similarly, if you delete the parent your children will get removed.

As such, I would think your cascade declaration should probably be on the parent object and not the child. I believe the orphanRemoval option aims to prevent orphans in the db but I am not 100% certain of its particulars. I think the cascade settings should be what you are looking for.

Also, the exception you are getting, appears to be related to the fact that your test method attempts to save the child to an unsaved parent. Thus, you are explicitly creating an orphan while you are telling hibernate to prevent orphan creation (with the removeOrphan option). That is why is works when you remove this option. Try saving the parent first and then add the child. Saving the parent again should save the child as well if your cascade settings are set to do so.

Keith


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 3 posts ] 

All times are UTC - 5 hours [ DST ]


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum

Search for:
© Copyright 2014, Red Hat Inc. All rights reserved. JBoss and Hibernate are registered trademarks and servicemarks of Red Hat, Inc.