1

I have 3 Java classes (BaseEntity, User, Role) that are working correctly with Hibernate. Both User and Role are a subclass of BaseEntity. I have a table for my users and a table for my roles. There is a join table for the mapping of users to roles. All annotations used are javax.persistence annotations.

@MappedSuperclass
public abstract class BaseEntity {
   private String id;
   private Timestamp entityCreation;
   private Timestamp entityUpdate;
   ...
}

@Entity
@Table(name="roles")
public class Role extends BaseEntity {
   private String description;
   private String name;
   ...
}

@Entity
@Table(name="users")
public class User extends BaseEntity {
   private String username;
   private String password;

   @ManyToMany( cascade = { CascadeType.DETACH, CascadeType.MERGE, CascadeType.PERSIST, CascadeType.REFRESH }, fetch = FetchType.LAZY )
   @JoinTable( name = "users_roles", joinColumns = { @JoinColumn( name = "user_id" ) }, inverseJoinColumns = { @JoinColumn( name = "role_id" ) } )
   private Set<Role> roles;
   ...
}

For various reasons I need to extend my model and have a superclass for Role. This superclass needs to have a self-reference. My idea was to use the @Inheritance annotation with the joined strategy here, but I keep getting an error from Hibernate. From what I read Hibernate should understand that it needs to do a join to get attributes from the superclass.

@Entity
@Table("authorities")
@Inheritance(strategy=InheritanceType.JOINED)
public class Authority extends BaseEntity {
   private String name;

   @ManyToMany( cascade = { CascadeType.DETACH, CascadeType.MERGE, CascadeType.PERSIST, CascadeType.REFRESH }, fetch = FetchType.LAZY )
   @JoinTable( name = "authorities_includes", joinColumns = { @JoinColumn( name = "authority_id" ) }, inverseJoinColumns = { @JoinColumn( name = "include_id" ) } )
   private Set<Authority> includes;
   ...
}

@Entity
@Table(name="roles")
public class Role extends Authority {
   private String description;
   ...
}

The error I'm getting:

[WARN] [18:30:04.004] [] org.hibernate.engine.jdbc.spi.SqlExceptionHelper - SQL Error: -5501, SQLState: 42501 [ERROR] [18:30:04.004] [] org.hibernate.engine.jdbc.spi.SqlExceptionHelper - user lacks privilege or object not found: ROLE1_.NAME

The Hibernate SQL output:

[DEBUG] [18:30:04.004] [] org.hibernate.SQL - 
    select
        roles0_.user_id as user_id1_22_1_,
        roles0_.role_id as role_id2_23_1_,
        role1_.id as id1_18_0_,
        role1_.entity_creation as entity_c2_18_0_,
        role1_.entity_update as entity_u3_18_0_,
        role1_.name as name4_18_0_ 
    from
        odm_users_roles roles0_ 
    inner join
        odm_roles role1_ 
            on roles0_.role_id=role1_.id 
    where
        roles0_.user_id=?

I am using Hibernate 4.2.19

As you can see, Hibernate is trying to select the value of the name attribute from the authority table, which is correct, but is then complaining that that column does not exist on that table.

How do I fix this issue?

Johanneke
  • 5,443
  • 4
  • 20
  • 33
  • I don't know if it is possible to mix inheritance strategies in the same entity hierarchy. – Bilal BBB Jul 21 '15 at 20:09
  • @Boutaya Bilal: mixing inheritance strategies in the same entity hierarchy is possible but outside of JPA specification, thus support depends on JPA provider. – wypieprz Jul 21 '15 at 21:08
  • You are missing @Entity annotation in Authority class. However, let me tell you that years ago I made a proof of concept about mix inheritance strategies using Hibernate 3.6, I figured out that it doesn't work at least for this version. – Guillermo Jul 21 '15 at 21:12
  • @wypieprz : I think it is possible using SecondaryTable annotation only. – Bilal BBB Jul 21 '15 at 22:41
  • @Guillermo sorry, my Authority class does have an `@Entity` annotation, I just forgot to add it to my post. – Johanneke Jul 22 '15 at 07:36
  • @BoutayaBilal I will look into using `@SecondaryTable` annotation, although I feel like this isn't right for my use case (I will have multiple subclasses of `Authority` in the feature...) – Johanneke Jul 22 '15 at 07:38
  • 1
    Ok, so I described the error wrong. The error is that Hibernate *does* try to select from the correct table, but that table does not seem to have the specified column. When looking through debug logs, I can clearly see the column being added to the authorities table, and the validation process is succesfully finished by Hibernate. I have discovered that it is only my integration test that fails. When building and deploying my application, I can successfully query for Authority and Role objects... – Johanneke Jul 22 '15 at 14:26

0 Answers0