[JPA] HowTo : UniqueConstraint and ManyToOne

4,546 views
Skip to first unread message

Cyrille37

unread,
Apr 13, 2011, 6:15:41 PM4/13/11
to play-framework
Hi,
Sorry to ask a JPA question, but I'm fully in Play! and have this
problem :

I would like the unicity of an Entity field AND the manyToOne
relation, like this simplified code :

@Entity
Category {
String code ;
}

@Entity
@Table(uniqueConstraints = {
@UniqueConstraint(columnNames = {"code", "category_id"})})
Categoryvalue {

@Column(name = "code")
String code ;

@ManyToOne(optional = false)
@Column(name = "category_id")
Category category ;
}

But when starting the application, JPA complains :
JPA error
A JPA error occurred (Unable to build EntityManagerFactory):
@Column(s) not allowed on a @ManyToOne property:
CategoryValue.category

Ok, I understand that I can't naming the column for the ManyToOne
relation, seems to be a JPA's rule, but how to implement the case ?
Have you got a idea on how to get around ?

Thanks a lot
Cyrille

robfig

unread,
Apr 13, 2011, 6:57:03 PM4/13/11
to play-fr...@googlegroups.com
You don't need the @Column annotations here -- Hibernate's default naming convention will result in the same column names. 

But if you do want the annotation, you need to use @JoinColumn instead. 

Cyrille37

unread,
Apr 13, 2011, 7:08:47 PM4/13/11
to play-framework
> e.g.http://stackoverflow.com/questions/4121485/columns-not-allowed-on-a-m...

Thanks,
I've try :

@Entity
Category {
String code ;
}

@Entity
@Table(uniqueConstraints = {
@UniqueConstraint(columnNames = {"code", "category_id"})})
Categoryvalue {
@Column(name = "code")
String code ;
@ManyToOne(optional = false)
@JoinColumn(name="category_id")
Category category ;
}

But JPA say it could not find 'category_id' ...

JPA error
A JPA error occurred (Unable to build EntityManagerFactory): Unable to
create unique key constraint (code, category_id) on table
CategoryValue: category_id not found

I'm a bit lost ...
With SQL it's so easy to create an Unique Index ...

Cyrille.

robfig

unread,
Apr 13, 2011, 7:26:25 PM4/13/11
to play-fr...@googlegroups.com
I think you have to use the field names instead of the SQL names.

e.g.
@UniqueConstraint(columnNames = {"code", "category"})}) 


Cyrille37

unread,
Apr 13, 2011, 7:30:41 PM4/13/11
to play-framework
Thanks a lot for your help !
=> A JPA error occurred (Unable to build EntityManagerFactory): Unable
to create unique key constraint (code, category) on table
CategoryValue: category not found

.. grrrrr ... I read many doc about JPA but I still lost ...

Rob Figueiredo

unread,
Apr 13, 2011, 7:45:09 PM4/13/11
to play-fr...@googlegroups.com
Sorry, I'm not sure why it doesn't work.  Do your models both extend play.db.jpa.Model ? 

(You do have the option to create and manage the table yourself, rather than putting in annotations to get Hibernate to do it, which always seems easier to me.)



--
You received this message because you are subscribed to the Google Groups "play-framework" group.
To post to this group, send email to play-fr...@googlegroups.com.
To unsubscribe from this group, send email to play-framewor...@googlegroups.com.
For more options, visit this group at http://groups.google.com/group/play-framework?hl=en.


Cyrille37

unread,
Apr 13, 2011, 7:54:18 PM4/13/11
to play-framework

On 14 avr, 01:45, Rob Figueiredo <rob...@gmail.com> wrote:
> Sorry, I'm not sure why it doesn't work.  Do your models both
> extend play.db.jpa.Model ?

My models extends play.db.jpa.GenericModel.

Do you think Play! has something to do with tables creation ? I think
it's only a Hibernate job, don't you ?

> (You do have the option to create and manage the table yourself, rather than
> putting in annotations to get Hibernate to do it, which always seems easier
> to me.)

Sure, I'm proficient too in SQL than JPA. But with Play! it seems that
all stuff has to be done in Java to keep it clear and simple ... ;-)

Cheers
Cyrille.

Cyrille37

unread,
Apr 13, 2011, 8:08:49 PM4/13/11
to play-framework
Argh!!!

I found the cause:
hibernate.globally_quoted_identifiers=true
I removed this option, and all tables were created ...

In some error message I could see that sometime fields are named with
backtick and sometime not. It was because of the option that JPA could
not find the "category_id" field.

Now UniqueConstraint and JoinColumn do the job ! it's work !!!
AAaahhhh... so good.

this code compile, create tables, and the famous unique index on
(code,category_id)

@Entity
Category {
String code ;
}

@Entity
@Table(uniqueConstraints = {
@UniqueConstraint(columnNames = {"code", "category_id"})})
Categoryvalue {
@Column(name = "code")
String code ;
@ManyToOne(optional = false)
@JoinColumn(name="category_id")
Category category ;
}

Such a bad day ... The lesson is : NEVER USE
"hibernate.globally_quoted_identifiers=true"

Thanks a lot Rob !

Cheers,
Cyrille.

Rob Figueiredo

unread,
Apr 13, 2011, 9:39:22 PM4/13/11
to play-fr...@googlegroups.com
Wow, I'm very surprised that was the problem.  Glad it's working for you though! 

Cyrille37

unread,
Apr 13, 2011, 9:48:13 PM4/13/11
to play-framework
On 14 avr, 03:39, Rob Figueiredo <rob...@gmail.com> wrote:
> Wow, I'm very surprised that was the problem.  Glad it's working for you
> though!

So am I ! I like the concept of this option, it's why I used it. But
it finally make me down on several subjects (/@db, ...).

I didn't explore yet, but I've swithed to Play 1.2, and perhaps it's
bring with a new Hibernate version. I don't know yet, I'll make some
comparisons thrusday with Play 1.1.1...

It's time for me to have a sleep (03:47am in france ;-)

By, and thanks again for your support !
Reply all
Reply to author
Forward
0 new messages