Still duking it out with Hibernate...
I'm using Hibernate-Annotations instead of hbm.xml files for my beans, but I'm currently running into a problem where the SQL that Hibernate is generating references nonexistent database columns.
For instance, here is the code:
Query q = session.createQuery("FROM Status ORDER BY post_date DESC");
(it is retrieving a list of Status
objects, ordered from most recent to least recent, and each Status
object contains its own list of Comment
objects...yes, think Facebook posts)
And here is the query it generates:
Hibernate: select status0_.pid as pid1_, status0_.content as content1_, status0_.owner_uid as owner5_1_, status0_.parent_pid as parent6_1_, status0_.post_date as post4_1_, status0_.type as type1_ from POSTS status0_ order by post_date DESC limit ?
The problem is, within that query, it references status0_.owner_uid
and status0_.parent_pid
, but those fields do not exist in the database. When I change the query manually to use status0_.owner
and status0_.parent
, respectively, and feed it to MySQL, it works perfectly.
There are four classes involved.
A User
, which has no concept of anything else in the system (relevant fields below):
@Entity
@Embeddable
@Table(name="USERS")
public class User {
@Id
@GeneratedValue
@Column(name="uid")
private Integer uid;
...
}
A Post
, an abstract superclass for Comment
and Status
that are stored in the same table and differentiated via a column type
(relevant fields below):
@Inheritance(strategy=InheritanceType.SINGLE_TABLE)
@DiscriminatorColumn(
name="type",
discriminatorType=DiscriminatorType.STRING
)
@MappedSuperclass
@Entity
@Embeddable
@Table(name="POSTS")
public abstract class Post {
@Id
@GeneratedValue
@Column(name="pid")
private Integer pid;
@ManyToOne
@Embedded
private Post parent;
@ManyToOne
@Embedded
private User owner;
@Column(name="post_date")
private Timestamp postDate;
@Column(name="content")
private String content;
@Column(name="type", updatable=false)
private String type;
...
}
A Status
class, subclassing Post
; sets parent
to null and also contains a list of Comment
s (relevant fields below):
@Entity
@Table(name="POSTS")
@DiscriminatorValue("status")
public class Status extends Post {
@OneToMany(mappedBy="parent")
@OrderBy("postDate asc")
private List<Comment> children;
...
}
A Comment
class, subclassing Post
; has a non-null parent
(entire class posted below):
@Entity
@DiscriminatorValue("comment")
@Table(name="shannonq_posts")
public class Comment extends Post {
// this class is literally empty
}
In summary: I have no idea why Hibernate is appending the embedded class' IDs into the query, resulting in a non-existent column. Ideally I would have liked to have added the @Column(name="parent")
annotation to these fields, but it seems that Hibernate doesn't allow this particular annotation to fields labeled with @ManyToOne
.
Any help is appreciated! Thank you!
Edit: FYI, if I manually change the columns in my database to match what Hibernate is generating, I get another error: Cannot instantiate abstract class or interface: Post
. Obviously my configuration is incorrect. :P