Hibernate: Error accessing field [private java.lang.Integer ] by reflection for persistent property
Asked Answered
Q

7

15

I have strange issue when I try to get entities property:

Hibernate: 
    select
        tarifklsk0_.ID as ID1_12_0_,
        tarifklsk0_.FK_TARIF as FK_TARIF2_12_0_,
        tarifservp1_.FK_TARIF as FK_TARIF2_11_1_,
        tarifservp1_.ID as ID1_11_1_,
        tarifservp1_.ID as ID1_11_2_,
        tarifservp1_.FK_TARIF as FK_TARIF2_11_2_,
        tarifservp1_.N1 as N3_11_2_ 
    from
        TR.TARIFXKLSK tarifklsk0_ 
    left outer join
        TR.TARIF_SERV_PROP tarifservp1_ 
            on tarifklsk0_.FK_TARIF=tarifservp1_.FK_TARIF 
    where
        tarifklsk0_.ID=?
Jun 13, 2016 7:38:26 AM org.hibernate.event.internal.DefaultLoadEventListener doOnLoad
INFO: HHH000327: Error performing load command : org.hibernate.property.access.spi.PropertyAccessException: Error accessing field [private java.lang.Integer TarifKlsk.fkTarif] by reflection for persistent property [TarifKlsk#fkTarif] : 1027303
Exception in thread "main" org.hibernate.property.access.spi.PropertyAccessException: Error accessing field [private java.lang.Integer TarifKlsk.fkTarif] by reflection for persistent property [TarifKlsk#fkTarif] : 1027303
    at org.hibernate.property.access.spi.GetterFieldImpl.get(GetterFieldImpl.java:43)
    ....skipped...
Caused by: java.lang.IllegalArgumentException: Can not set java.lang.Integer field TarifKlsk.fkTarif to java.lang.Integer
    at sun.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:167)
    at sun.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:171)       

My entities:

TarifKlsk

import java.util.HashSet;
import java.util.Set;

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.OneToMany;
import javax.persistence.Table;

import org.hibernate.annotations.BatchSize;

@SuppressWarnings("serial")
@Entity
@Table(name = "TARIFXKLSK", schema="TR")
public class TarifKlsk implements java.io.Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name = "ID", updatable = false, nullable = false)
    private Integer id;

    @OneToMany(fetch = FetchType.EAGER)
    @JoinColumn(name="FK_TARIF", referencedColumnName="FK_TARIF")
    @BatchSize(size = 50)
    private Set<TarifServProp> tarifservprop = new HashSet<TarifServProp>(0);

    @Column(name = "FK_TARIF", updatable = false, nullable = false)
    private Integer fkTarif;

    public Integer getId() {
        return id;
    }

    public void setId(Integer id) {
        this.id = id;
    }

    public Set<TarifServProp> getTarifservprop() {
        return tarifservprop;
    }

    public void setTarifservprop(Set<TarifServProp> tarifservprop) {
        this.tarifservprop = tarifservprop;
    }

    public Integer getFkTarif() {
        return fkTarif;
    }

    public void setFkTarif(Integer fkTarif) {
        this.fkTarif = fkTarif;
    }

}

TarifServProp

import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;

@SuppressWarnings("serial")
@Entity
@Table(name = "TARIF_SERV_PROP", schema="TR")
public class TarifServProp implements java.io.Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.AUTO)
    @Column(name = "ID", updatable = false, nullable = false)
    private Integer id;

    @Column(name = "FK_TARIF", updatable = false, nullable = false)
    private Integer fkTarif;

    public Integer getId() {
        return id;
    }

    @Column(name = "N1", updatable = false, nullable = false)
    private Integer n1;

    public void setId(Integer id) {
        this.id = id;
    }

    public Integer getFkTarif() {
        return fkTarif;
    }

    public void setFkTarif(Integer fkTarif) {
        this.fkTarif = fkTarif;
    }

    public Integer getN1() {
        return n1;
    }

    public void setN1(Integer n1) {
        this.n1 = n1;
    }

}

My test module:

    public static void main(String[] args) {
        SessionFactory sf = HibernateUtil.getSessionFactory();
        Session sess = sf.openSession();
        sess.beginTransaction();

        TarifKlsk k2=sess.get(TarifKlsk.class, 1027303);
        for (TarifServProp t : k2.getTarifservprop()) {
             System.out.println("Tar="+t.getN1());
        }

        System.out.println("End init");

What am I doing wrong? I've checked all fields of these entities and all of them named properly....

Updt My POM.xml

<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>
    <groupId>com.journaldev.hibernate</groupId>
    <artifactId>HibernateEHCacheExample</artifactId>
    <version>0.0.1-SNAPSHOT</version>
    <description>Hibernate Secondary Level Cache Example using EHCache implementation</description>

    <dependencies>
        <!-- Hibernate Core API -->
        <dependency>
            <groupId>org.hibernate</groupId>
            <artifactId>hibernate-core</artifactId>
            <version>5.1.0.Final</version>
        </dependency>
        <!-- EHCache Core APIs -->
        <!-- http://mvnrepository.com/artifact/net.sf.ehcache/ehcache-core -->
        <dependency>
            <groupId>net.sf.ehcache</groupId>
            <artifactId>ehcache-core</artifactId>
            <version>2.6.11</version>
        </dependency>

        <!-- http://mvnrepository.com/artifact/org.hibernate/hibernate-ehcache -->
        <dependency>
            <groupId>org.hibernate</groupId>
            <artifactId>hibernate-ehcache</artifactId>
            <version>5.2.0.Final</version>
        </dependency>

        <!-- EHCache uses slf4j for logging -->
        <dependency>
            <groupId>org.slf4j</groupId>
            <artifactId>slf4j-simple</artifactId>
            <version>1.7.5</version>
        </dependency>
    </dependencies>
</project>

Upd2

I've found out that my child entity doesn't contain records with fk_tarif corresponding to the fk_tarif from master... but I think it doesn't matter, why is error exists?

Quadrangular answered 13/6, 2016 at 1:47 Comment(3)
It is so weird, but when I set Hibernate version to 4.1.9.Final my code works well: ***** ***** Fetch Count=0 Second Level Hit Count=0 Second Level Miss Count=0 Second Level Put Count=0 Complete! May be it is bug in version hibernate version higher 4.1.9?Quadrangular
That solution helped me with this error. I hope you too. #24694353Cooe
In case it helps, I had the same error in a Spring Boot 2 + Hibernate 5 application. This error was caused by the spring devtools starter. If think this is kinda linked with the live reload.Qoph
E
2

It is bug in version 5.0 and 5.1.0 https://hibernate.atlassian.net/browse/HHH-10618

Eugenaeugene answered 3/10, 2016 at 14:41 Comment(1)
Still a bug in 5.2.0-FINAL. I resolved by reverting to 4.3.11-FINAL.Briscoe
N
2

I advice you to keep working with hibernate version 4.X.X instead of the version 5 because it's not 100% stable (more the 2000 issues).

https://hibernate.atlassian.net/projects/HHH/issues/HHH-11144?filter=allopenissues

Good luck

Notecase answered 3/10, 2016 at 16:55 Comment(0)
S
2

I am working with EAP7, which contains Hibernate Core {5.0.9.Final-redhat-1}

I have two entities:

@Entity
@Data
@EqualsAndHashCode(callSuper = true, doNotUseGetters = true)
@ToString(callSuper = true, doNotUseGetters = true)
public class Keuze extends MainTable {

@NonNull
String naam;

@Tolerate
public Keuze() {
}

}

and

@Entity
@Data
@EqualsAndHashCode(callSuper = true, doNotUseGetters = true, exclude = {"gegeven", "werkJaar", "keuze", "keuzes" })
@ToString(callSuper = true, doNotUseGetters = true, exclude = { "gegeven", "werkJaar", "keuze", "keuzes" })
public class Waarde extends MainTable {

@NonNull
@ManyToOne(optional = false, fetch = FetchType.LAZY)
Gegeven gegeven;

@NonNull
@ManyToOne(optional = false, fetch = FetchType.LAZY)
WerkJaar werkJaar;

String alfanumeriek;

Integer numeriek;

BigDecimal valuta;

@Lob
String tekst;

Boolean polair;

@OneToOne(fetch = FetchType.LAZY, cascade = CascadeType.MERGE)
Keuze keuze;

@ManyToMany(fetch = FetchType.EAGER, cascade = CascadeType.MERGE)
Set<Keuze> keuzes;

@Tolerate
public Waarde() {
}

}

They both extend from this class:

@MappedSuperclass
@Data
@Cacheable
public abstract class MainTable {

@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
Long id;

@Version
Long version;

}

When calling merge upon Waarde, it throws following error:

Caused by: org.hibernate.property.access.spi.PropertyAccessException: Error accessing field [java.lang.Long vo.cjsm.monitoring.data.schema.dynamic.main.MainTable.id] by reflection for persistent property [vo.cjsm.monitoring.data.schema.dynamic.field.Keuze#id] : Keuze(super=MainTable(id=1, version=0), naam=Leesmotivatie)
at org.hibernate.property.access.spi.GetterFieldImpl.get(GetterFieldImpl.java:43)
at org.hibernate.tuple.entity.AbstractEntityTuplizer.getIdentifier(AbstractEntityTuplizer.java:223)
at org.hibernate.persister.entity.AbstractEntityPersister.getIdentifier(AbstractEntityPersister.java:4601)
at org.hibernate.event.internal.DefaultMergeEventListener.onMerge(DefaultMergeEventListener.java:148)
at org.hibernate.internal.SessionImpl.fireMerge(SessionImpl.java:850)
at org.hibernate.internal.SessionImpl.merge(SessionImpl.java:832)
at org.hibernate.engine.spi.CascadingActions$6.cascade(CascadingActions.java:260)
at org.hibernate.engine.internal.Cascade.cascadeToOne(Cascade.java:398)
at org.hibernate.engine.internal.Cascade.cascadeAssociation(Cascade.java:323)
at org.hibernate.engine.internal.Cascade.cascadeProperty(Cascade.java:162)
at org.hibernate.engine.internal.Cascade.cascadeCollectionElements(Cascade.java:431)
at org.hibernate.engine.internal.Cascade.cascadeCollection(Cascade.java:363)
at org.hibernate.engine.internal.Cascade.cascadeAssociation(Cascade.java:326)
at org.hibernate.engine.internal.Cascade.cascadeProperty(Cascade.java:162)
at org.hibernate.engine.internal.Cascade.cascade(Cascade.java:111)
at org.hibernate.event.internal.DefaultMergeEventListener.cascadeOnMerge(DefaultMergeEventListener.java:468)
at org.hibernate.event.internal.DefaultMergeEventListener.entityIsDetached(DefaultMergeEventListener.java:327)
at org.hibernate.event.internal.DefaultMergeEventListener.onMerge(DefaultMergeEventListener.java:170)
at org.hibernate.event.internal.DefaultMergeEventListener.onMerge(DefaultMergeEventListener.java:69)
at org.hibernate.internal.SessionImpl.fireMerge(SessionImpl.java:840)
at org.hibernate.internal.SessionImpl.merge(SessionImpl.java:822)
at org.hibernate.internal.SessionImpl.merge(SessionImpl.java:827)
at org.hibernate.jpa.spi.AbstractEntityManagerImpl.merge(AbstractEntityManagerImpl.java:1161)
... 149 more
Caused by: java.lang.IllegalArgumentException: Can not set java.lang.Long field vo.cjsm.monitoring.data.schema.dynamic.main.MainTable.id to java.lang.String
at sun.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:167)
at sun.reflect.UnsafeFieldAccessorImpl.throwSetIllegalArgumentException(UnsafeFieldAccessorImpl.java:171)
at sun.reflect.UnsafeFieldAccessorImpl.ensureObj(UnsafeFieldAccessorImpl.java:58)
at sun.reflect.UnsafeObjectFieldAccessorImpl.get(UnsafeObjectFieldAccessorImpl.java:36)
at java.lang.reflect.Field.get(Field.java:393)
at org.hibernate.property.access.spi.GetterFieldImpl.get(GetterFieldImpl.java:39)
... 171 more

By removing the ToString line of Lombok and adding my own implementation of toString by overriding the default one, the error message disappeared and the code was working back!

Now the entity looks like this:

@Entity
@Data
@EqualsAndHashCode(callSuper = true, doNotUseGetters = true)
public class Keuze extends MainTable {

@NonNull
String naam;

@Tolerate
public Keuze() {
}

@Override
public String toString() {

    return getId().toString();
}

}

So somehow, for an unknown reason the toString method has effect on how hibernate merges the code... Don't ask me how :-) It just seems to work. I tried everything else on the web with no luck!

Hope this helps for somebody else!

Saddler answered 18/5, 2017 at 12:52 Comment(0)
B
1

In my case the problem was that in my model the setter was auto-generated as

public void setComments(List comments){
}

without a type. Fixed it by setting it to List<Comment> comments

Brach answered 10/4, 2018 at 2:24 Comment(0)
D
1

I hit this same error after upgrading from Hibernate 4 to 5. At this time the hibernate bug doesn't seem to be fixed in any version up to 5.3. In my case this error happeneds while lazily fetching a collection of entity A which had an eager one-to-many relationship to B using a property from A which is not the primary key (I know, not a good relational model). It might actually be a more complicated edge case than just this, but I don't have time right now to reproduce this in a minimal test case).

In tracing through the hibernate code it appears that hibernate gets confused while trying to bind parameters for the query for B, and when it thinks its trying to get the foreign key, the property from object A, it, in fact, already has the property value. The code is treating the value as if it is the object A and ends up with the reflection error shown above.

I was able to get past this error by changing the one-to-many relationship to B to lazy. I hope this helps someone else.

Desireah answered 5/3, 2020 at 20:14 Comment(0)
W
1

In my case it was not a bug but pure developer-error:

@OneToMany(mappedBy = "tableCollection", targetEntity = Diagram.class)
// had to be replaced with 
@OneToMany(mappedBy = "tableCollection", targetEntity = Table.class)

i had the targetEntity wrong and therefore got a cryptic error.

Maybe it saves some hours someone.

Winze answered 24/5, 2023 at 17:25 Comment(0)
S
0

Instead of using : setParameter("name", variable containing the value); I had sloved this by using :

setParameter("name", variable containing the value, StandardBasicTypes.INTEGER);

and importing the correct Library :

import org.hibernate.type.StandardBasicTypes;
Subside answered 28/1 at 1:59 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.