-->
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: Hibernate inheritence problem ?
PostPosted: Tue Dec 04, 2007 9:32 am 
Newbie

Joined: Tue Dec 04, 2007 9:17 am
Posts: 2
Hello,

I'm using EJB 3.0 and jboss with an PgSQL database. hope you will be ables to unlock my problem.

I've a problem with requests on sublasses of a class tree (Entity beans). I got a org.hibernate.WrongClassException when trying to access data with a oneToMany relation.

My architecture is:

A <---- B <---- C

Code:

@Entity
@Table(name = "A")
@Inheritance(strategy = InheritanceType.SINGLE_TABLE)
@DiscriminatorColumn(name = "DTYPE", discriminatorType = DiscriminatorType.STRING)
@DiscriminatorValue("A_TYPE")
public class A implements java.io.Serializable {

   private Long id;
...
}

@Entity
@DiscriminatorValue("B_TYPE")
public class B extends A {
   
   // Associations
   private Collection<Obj> objSet = new ArrayList<Obj>();

        @OneToMany(mappedBy = "A")
   public Collection<Review> getObjSet() {
      return objSet;
   }

   public void setObjSet(Collection<Obj> objSet) {
      this.objSet = objSet;
   }
}

@Entity
@DiscriminatorValue("C_TYPE")
public class C extends B {
       ...
}

   


And Obj is defined like:

Code:

@Entity
@Table(name = "OBJ")
public class Obj {
        private B value;

        @ManyToOne
   @JoinColumn(name="A_ID")
   public AppPOI getValue() {
      return value;
   }

   public void setValue(B value) {
      this.value = value;
   }

}
   



When I create a new Obj and associate it to a B Entity it works. (correctly added to the DB, good ID pointing from OBJ to a "A like" entry)

Now when I try to access using this request:
SELECT obj FROM Obj obj WHERE obj.value.id=44549450

It gives me that error message:

Code:

org.hibernate.WrongClassException: Object with id: 44549450 was not of the specified subclass: C (Di
scriminator: B_TYPE)


I'm using using jboss 4.0.5 with seam and hibernate updated to version 3.2.5ga

Thanks for your help, I couldn't find an answer to my problem with the search function of this forum, I've passed so many times reading it at this point...

Paulin


Top
 Profile  
 
 Post subject:
PostPosted: Wed Dec 05, 2007 5:16 am 
Newbie

Joined: Tue Dec 04, 2007 9:17 am
Posts: 2
I found a possible explanation to this problem. It seem's the discriminant is'n't used when requesting by a one-to-many in an subclass. So a way to make hibernate consider the hierarchy is to force control on the Discriminator column.

With annotations, @Where should be used.
@Where(clause="POI_TYPE='B'")
and
@Where(clause="POI_TYPE='C'")

But in my example, I really don't understand where I have to place this clauses. Any help with this polymorphic request problem ?

Thanks

Paulin


Top
 Profile  
 
 Post subject:
PostPosted: Sat Jan 26, 2008 3:11 pm 
Regular
Regular

Joined: Mon Aug 20, 2007 6:47 am
Posts: 74
Location: UK
p.chevillon, I can confirm that your suggestion solves this problem. I found this thread by searching for the term "WrongClassException".

I imagine you have probably solved your problem by now, but in case not then let me show you how the @Where annotation fixed the issue in my case.

I'm afraid I'm not familiar with your technique of mapping methods rather than properties, so it's easier for me to show you from my class design.

This is my top level class

Code:

@Entity
@Table(name="FIELD_CATEGORY")
@Inheritance(strategy=InheritanceType.SINGLE_TABLE)
@DiscriminatorColumn(name = "FIELD_TYPE_ID", discriminatorType = DiscriminatorType.INTEGER)
public abstract class FieldCategory {
    // content not important
}



I have two concrete subclasses:

Code:

@Entity
@DiscriminatorValue("1")
public class RoleFieldCategory extends FieldCategory{
     @ManyToOne
     @JoinColumn(name = "CLIENT_ID", nullable = false)
     private Client client;

     // rest not important
}

@Entity
@DiscriminatorValue("2")
public class EmployeeFieldCategory extends FieldCategory{
     @ManyToOne
     @JoinColumn(name = "CLIENT_ID", nullable = false)
     private Client client;
     
     // rest not important

}



Then, in the Client class, I have a collection of EmployeeFieldCategory(s) and a collection of RoleFieldCategory(s)

Code:
  @OneToMany(mappedBy="client",fetch=FetchType.LAZY,targetEntity=RoleFieldCategory.class)
    @Fetch(FetchMode.SUBSELECT)
    @Where(clause="FIELD_TYPE_ID=1")
    private List<RoleFieldCategory> roleFieldCategories;
   
     @OneToMany(mappedBy="client",fetch=FetchType.LAZY,targetEntity=EmployeeFieldCategory.class)
    @Fetch(FetchMode.SUBSELECT)
    @Where(clause="FIELD_TYPE_ID=2")
    private List<EmployeeFieldCategory> employeeFieldCategories;



I theory Hibernate has enough information from the @OneToMany annotation to build the correct queries for these mappings, but without the @Where annotation I get a WrongClassExeption when I try to access either collection. I can only assume this is a bug in hibernate, though at least there is a workaround.

Notice that both concrete subclasses of FieldCategory have an instance of Client. The logical class design would be to have the Client property in the abstract FieldCategory class. However, hibernate will not accept @OneToMany(mappedBy="an inherited property") so I'm forced to have abstract getters and setters for a Client property in FieldCategory and reproduce the property in each and every concrete subclass. Again this is a flaw in hibernate as far as I'm concerned, but again at least there's a workaround.

I hope this helps you or someone else who happens to find this thread.


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.