9

I've got the following schema in DB (simplified)

MainTable(
    ID primary key
    SOMEFIELD
    CODE_FK1 -- references OtherTable1 CODE (without declared foreign key)
    CODE_FK2 -- references OtherTable2 CODE (without declared foreign key)
    ... Other fields used
)

OtherTable1(
    CODE primary key
    LABEL
    ... other fields not used
)

OtherTable2(
    CODE primary key
    LABEL
    ... other fields not used
)

I'm asking if there is any way to define my Entity for main table in order to use directly labels from my other tables, i.e without defining entities for these other table.

I cannot change the DB schema, which is really awful (there are labels/code couples everywhere, defined in multiples tables). And If it was possible, this solution would allow to keep my code simple, since I don't really need these other entities.

I guess it would result something like that:

@Entity
public class MainEntity{
    @Id
    private Integer ID;

    @Column(name="SOMEFIELD")
    private String SomeField;

    @SomeAnnotation to Join CODE_FK_1 with OtherTable1.CODE
    @SomeAnnotation like @Column(name="LABEL", table="OtherTable1")
    private String Label1;

    @SomeAnnotation to Join CODE_FK_1 with OtherTable1.CODE
    @SomeAnnotation like @Column(name="LABEL", table="OtherTable1")
    private String Label1;

}

Thanks by advance for your help!

mdomenjoud
  • 103
  • 1
  • 2
  • 7
  • 1
    I really doubt if this is possible with JPA (on entity level relationships with other entities are defined, not the way how to get the fields in joined entities). Have you considered those two options: a) map all relevant tables to JPA entities, and perform query when you need it; b) use JDBC to simplify the life, if there's not much of DB interaction? – Art Licis Dec 23 '10 at 12:01

2 Answers2

16

Another possibility would be using the @Formula annotation to fetch the value from the other table. This will automatically generate a subselect whenever you load your Entity.

I think you'll need something like this:

    @Entity
public class MainEntity{
    @Id
    private Integer ID;

    @Column(name="SOMEFIELD")
    private String SomeField;

    @Formula("(SELECT ot1.LABEL FROM OtherTable1 ot1 WHERE ot1.CODE = CODE_FK_1)")
    private String Label1;

}

There is little information about this in the [Hibernate docs][1], so you may need some trial and error to get it right (but you should be able to work it out with hibernate.show_sql=true.

There are 2 possible downsides to this approach:

  1. This is hibernate-specific code
  2. This is plain SQL, and may thus be database-specific

HTH

[1]: http://docs.jboss.org/hibernate/stable/annotations/reference/en/html_single/#entity-hibspec-property hibernate docs

Mopper
  • 1,677
  • 2
  • 18
  • 41
2

You can use the @SecondaryTable annotation. See this example:

https://github.com/hibernate/hibernate-orm/blob/823a5c1ede1869fd97471e3b8ebe7ec4ac8068e4/hibernate-core/src/test/java/org/hibernate/test/annotations/join/Dog.java#L20-L24

jpkroehling
  • 13,881
  • 1
  • 37
  • 39
  • Thanks for your suggestion, but we laready tried it. In fact, we obtained an exception : org.hibernate.AnnotationException: SecondaryTable JoinColumn cannot reference a non primary key. I found an issue posted on Hibernate's bugtracker : http://opensource.atlassian.com/projects/hibernate/browse/HHH-4987 . – mdomenjoud Dec 23 '10 at 12:55
  • Then I recommend commenting in that JIRA. Don't forget to provide a test case :-) Otherwise, it will still be a bug in the next version. – jpkroehling Dec 23 '10 at 13:01
  • I just changed the post to fix the link. – jpkroehling Mar 28 '19 at 16:43