-->
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.  [ 4 posts ] 
Author Message
 Post subject: Self Referencing Association and Annotations?
PostPosted: Thu Apr 10, 2008 1:20 pm 
Newbie

Joined: Tue Mar 18, 2008 11:23 am
Posts: 8
Straight to it:

I have a class that is a Map. Each Task in this map can be a Sub-Task to many Tasks and have many Sub-Tasks. I am swapping over to JPA annotations for the project and am running into a little trouble making the association work. I keep getting this error from my unit tests:

Initial SessionFactory creation failed.org.hibernate.MappingException: Foreign key (FK852BA54E906BF3CF:subtasks [sub_task])) must have same number of columns as the referenced primary key (subtasks [parent_task,sub_task])

This is what I had in hbm.xml files that was working fine:

Task Configure:

<hibernate-mapping default-lazy="false">

<class name="com.tak.impl.task.TaskImpl" table="tasks">
<id name="id" column="id">
<generator class="native"/>
</id>
<property name="name"/>
<property name="startdate" type="date"/>
<property name="enddate" type="date"/>
<property name="dependant" type="boolean"/>
<property name="taskorder"/>
<property name="notes" type="text" />
<property name="type" />
<property name="ownerid" type="int" />
<property name="complete" type="boolean" />

<set name="subtasks" table="subtasks">
<key column="parent_task"/>
<many-to-many column="sub_task" class="com.tak.impl.task.TaskImpl" fetch="join"/>
</set>
</class>

</hibernate-mapping>

Sub-Task Configure:

<hibernate-mapping>

<class name="com.tak.impl.subtask.SubTaskImpl" table="subtasks">
<id name="id" column="id">
<generator class="native"/>
</id>
<property name="subTask" column="sub_task"/>
<property name="parentTask" column="parent_task"/>
</class>

</hibernate-mapping>

This is what I have now in annotations:

Task Class:

@Entity
@Table(name = "tasks")
public class TaskImpl implements Task{
//Properties
@Id @GeneratedValue
@Column(name = "id")
private int id;

public int getId()
{
return this.id;
}

< ... Lots of other getters and setters ... >

@ManyToMany(cascade = CascadeType.ALL, fetch = FetchType.EAGER, targetEntity = com.tak.impl.subtask.SubTaskImpl.class)
@JoinTable(
name = "subtasks",
joinColumns = {@JoinColumn( name = "parent_task" )},
inverseJoinColumns = {@JoinColumn( name = "sub_task" )}
)
private Set subtasks = new HashSet<Task>();

public Set getSubtasks()
{
return this.subtasks;
}

public void setSubtasks(Set subtasks)
{
this.subtasks = subtasks;
}

< ... Lots of other getters and setters ... >
}

SubTasks Class:

@Entity
@Table( name = "subtasks" )
public class SubTaskImpl{
//Properties
@Id @GeneratedValue
@Column( name = "id" )
private int id;

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

public int getId()
{
return this.id;
}

@Column( name = "parent_task" )
private int parentTask;

public void setParentTask(int parentTask)
{
this.parentTask = parentTask;
}

public int getParentTask()
{
return this.parentTask;
}

@Column( name = "sub_task" )
private int subTask;

public void setSubTask(int subTask)
{
this.subTask = subTask;
}

public int getSubTask()
{
return this.subTask;
}
//Constructors
public SubTaskImpl(){}

public SubTaskImpl(int id, int parentTask, int subTask)
{
this.id = id;
this.subTask = subTask;
this.parentTask = parentTask;
}
}

I summon the Gurus of Hibernate to show me the simple thing I am missing?

Thanks,

---L


Top
 Profile  
 
 Post subject: Solved...
PostPosted: Thu Apr 10, 2008 1:35 pm 
Newbie

Joined: Tue Mar 18, 2008 11:23 am
Posts: 8
Turns out it was quite simple.

My Many-To-Many Annotation was pointing to the SubTaskImpl, which is wrong, because it is returning a set of Tasks. Silly me.

It should have looked like this, for anyone who runs into this problem:

@ManyToMany(cascade = CascadeType.ALL, fetch = FetchType.EAGER, targetEntity = com.tak.impl.task.TaskImpl.class)
@JoinTable(
name = "subtasks",
joinColumns = {@JoinColumn( name = "parent_task" )},
inverseJoinColumns = {@JoinColumn( name = "sub_task" )}
)


Top
 Profile  
 
 Post subject:
PostPosted: Thu Apr 10, 2008 1:38 pm 
Hibernate Team
Hibernate Team

Joined: Fri Oct 05, 2007 4:47 pm
Posts: 2536
Location: Third rock from the Sun
Hi,
I'm no guru and didn't completely understand the error,
but anyway it's weird you have mapped the
Code:
@Column( name = "sub_task" ), @Column( name = "parent_task" )

to int values, they should be a reference to the entity, as a set or other collection.
I think that because of this he isn't understanding them as FKs;
you may have other problems there but maybe this is confusing things a bit;
maybe you get a better error message if you fix that.

Also as you choose ManyToMany you will need a bridge-table, so I don't think you should have FKs in the subtask table.

regards,
Sanne


Top
 Profile  
 
 Post subject:
PostPosted: Thu Apr 10, 2008 1:41 pm 
Hibernate Team
Hibernate Team

Joined: Fri Oct 05, 2007 4:47 pm
Posts: 2536
Location: Third rock from the Sun
nice you solved, I came too late.
Sanne


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 4 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.