views:

3830

answers:

3

I have a pojo that is object A , of table TableA

TableA (int a1,int a2).

To fill the table I run a query that returns (int a1, int a2, boolean b3) (and runs multiple data checks)

b3 is not valid in TableA , but I still want to use the same pojo for both (it's a very big pojo , and it will be a major code duplication to have one just for the sake of the query)

I've declared in the pojo

@Transient
Boolean getB3() {..}
void setB3(Boolean b3) {..}

And in the query I declared that I expect to get the b3 value:

<return> ...
<return-property name="b3" column="b3"/>
...
</return>

But Hibernate just ignores the parameter and never use "setB3()".. When I remove the @Transient , it works (and then fail when inserting to the table , naturally) - so all the names are correct

How can I fix this?

Thanks!

A: 

Where is your Id annotation? Is it on a getter or setter or is it on a field?

If it is on a field hibernate will only look at fields to find other annotations.

Access type

The accessType attribute is no longer available in @Entity, @EmbeddableSuperclass, @Embeddable. The access type of a given entity is guessed from the @Id or @EmbeddedId annotation position. If an entity has @Id on a field, the access type will be field and all the annotations will be read on fields. Same for methods. @MappedSuperclass (formerly @EmbeddableSuperclass) and @Embeddable inherit the access type from their >owning entity.

Annotating both field and method with @Id for a given entity is forbiddden.

If for some reason you want to mix the access types in a given Entity or between an Entity and its MappedSuperclass/Embeddable, you can use the Hibernate specific @AccessType annotation (please refer to the reference documentation for more information).

This is from http://www.hibernate.org/398.html

Jens Schauder
I didn't really get what you're saying , I'm sorry
yossale
I am saying basically the same as the other answer
Jens Schauder
A: 

Have you mixed annotations on fields and methods?

For example, this wont work:

@Entity
public class A {
    @Id
    @GeneratedValue
    private Long id;

    @Column
    private String b;

    private String c;

    public void setB(String b) { this.b = b; }
    public String getB() { return b; }

    @Transient // inconsistent with other annotations
    public void setC(String c) { this.c = c; }
    public String getC() { return c; }
}

Whereas this will:

@Entity
public class A {
    @Id
    @GeneratedValue
    private Long id;

    @Column
    private String b;

    @Transient // consistent with other annotations
    private String c;

    public void setB(String b) { this.b = b; }
    public String getB() { return b; }

    public void setC(String c) { this.c = c; }
    public String getC() { return c; }
}
toolkit
Nope , Everything is in it's right place , but it still doesn't work :(
yossale
A: 

Ok, different idea. I guess since you marked the property as transient hibernate will neither load nor stor the property.

One solution could be to make to classes. One without the b property. And the second one extending from the first using the mappedSuperclass annotation.

Or you could try mapping it with some formula that just provides some default value (e.g. false). So for the 'normal' case you hibernate would use the formula, resulting in some default value, and for your special query you use whatever logic is in that query.

Jens Schauder
About the formula - Good idea , but it won't work - because the result is based on other fields in the query , which are not in the table. Regarding the other option , I'm trying to avoid this , because it will require also an interface + 2 classes , and all I want is a pojo :(
yossale
whats so bad about 2 classes and an interface, as long as there is no duplication?
Jens Schauder
I think I wasn't clear about what I meant with the formular approach. Edited the answer to clarify it.
Jens Schauder