Solved

Using @IdClass with @GeneratedValue

Posted on 2008-10-15
5
3,237 Views
Last Modified: 2013-12-22
I am using EJB3 persistence, JBoss, MySql.  I am able to have an entity with one primary key marked with @Id where this key is an autogenerated field with the annotation @GeneratedValue(strategy=GenerationType.AUTO).  The table is created with the primary key and when persisting objects, I see the id field being incremented.

Everything works fine until I started creating entites that have composite primary keys using @IdClass where one of those keys have @GeneratedValue(strategy=GenerationType.AUTO).  I can see that the table gets created with the correct primary key.  The problem is that the primary key field that has the @GeneratedValue attribute is not being incremented; it is always 0.

I have tried different combinations of putting the @Id and @GeneratedValue attributes on the fields and getters of the entity and the primary key class but nothing works.
0
Comment
Question by:leobaz2
  • 3
  • 2
5 Comments
 
LVL 4

Expert Comment

by:Mr_It
ID: 22738459
What is the use of a composite PK if you want to auto-generate one of the values? Isn't a single ID property unique enough to identify the entity? I really don't understand why you would like to have a composite PK if one of its properties is uniquely generated anyway. For me it makes no sense to have something like this.

Anyway, you simply cannot put @Id annotations in classes other than an entity, because it makes no sense.  The specs say:

'The Id annotation specifies the primary key property or field of an entity. The Id annotation may be applied in an entity or mapped superclass.'

It's normal that it will be ignored in the non-entity class. That's why it's always 0...

0
 
LVL 4

Expert Comment

by:Mr_It
ID: 22738917
Anyway, I understand that you might expect it to work with the IdClass thing, because the specs are unclear about this:

'The GeneratedValue annotation may be applied to a primary key property or
field of an entity or mapped superclass in conjunction with the Id annotation.'

If you have a composite PK, can we refer to one of the properties annotated with @Id as a primary key property? It's only a partial primary key property, not the primary key property itself. They should go into more detail about this...

Still, I don't see the purpose of having a composite key with one of the values unique. Maybe you are coding for an existing database?

Maybe vendor specific annotations can do the trick. I never came across a use case for this.

Good luck ;-)

0
 

Author Comment

by:leobaz2
ID: 22741757
I am going to have multiple clients sharing the same database but not the same data.  I originally had one primary key for every table that was auto generated.  I wanted to change it so that each primary key was composite on the auto generated column and the "client id".  This way, it would be impossible for a client to view another client's data.  Also, when I do a find I pass the client id along with the auto generate key which I liked.  

However, since I can't use composite primary keys with an auto generated field, I am doing a find on the auto generated field and then just verifying that the client id from the persisted object equals the logged on user's client id.
0
 
LVL 4

Accepted Solution

by:
Mr_It earned 125 total points
ID: 22747537
I think that it's even a better design, because in my opinion, a PK should never contain any logic.

Instead of checking the client ID after retrieval, you could use a Query object and put both the PK and the client ID in the WHERE clause and call the getSingleResult() method on it. Unless you want to treat 'no result' or 'result for other client' differently, of course.

Is it possible that the same client can have multiple logins (for example different roles) in the future that have access to the same data? If yes, beware that there will be multiple user id's for just one client id. You could already take that into account in your design.
0
 

Author Comment

by:leobaz2
ID: 22749612
I actually agree with you that primary keys should not have business logic even though the logic is minimal in this case.  I'll change my logic to use a where clause.

Thanks for your help.
0

Featured Post

Space-Age Communications Transitions to DevOps

ViaSat, a global provider of satellite and wireless communications, securely connects businesses, governments, and organizations to the Internet. Learn how ViaSat’s Network Solutions Engineer, drove the transition from a traditional network support to a DevOps-centric model.

Question has a verified solution.

If you are experiencing a similar issue, please ask a related question

Suggested Solutions

Title # Comments Views Activity
Which non-HTML GUI front end to use with Java? 3 24
add projects t working set in maven 2 16
collection output issue 9 36
Java 8 to Java 6 8 20
Go is an acronym of golang, is a programming language developed Google in 2007. Go is a new language that is mostly in the C family, with significant input from Pascal/Modula/Oberon family. Hence Go arisen as low-level language with fast compilation…
Java functions are among the best things for programmers to work with as Java sites can be very easy to read and prepare. Java especially simplifies many processes in the coding industry as it helps integrate many forms of technology and different d…
Viewers learn about the scanner class in this video and are introduced to receiving user input for their programs. Additionally, objects, conditional statements, and loops are used to help reinforce the concepts. Introduce Scanner class: Importing…
This tutorial explains how to use the VisualVM tool for the Java platform application. This video goes into detail on the Threads, Sampler, and Profiler tabs.

791 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question