Exception org.hibernate.PropertyAccessException: could not set a field value by reflection setter

2

I'm trying to map the following template in JPA with Hibernate:

Company table:

CREATE TABLE empresa (
  id_empresa INT(11) NOT NULL AUTO_INCREMENT ,
  PRIMARY KEY (id_empresa) )
ENGINE = InnoDB
DEFAULT CHARACTER SET = latin1
ROW_FORMAT = FIXED

Attendance group table:

CREATE TABLE grupo_atendimento' (
  id_grupo_atendimento INT(11) NOT NULL AUTO_INCREMENT ,
  ddd VARCHAR(2) NOT NULL ,
  PRIMARY KEY (id_grupo_atendimento) )
ENGINE = InnoDB

N-N associative table with extra field:

CREATE TABLE grupo_atendimento_empresa (
  'id_grupo_atendimento' INT(11) NOT NULL ,
  'id_empresa' INT(11) NOT NULL ,
  'contador' INT(11) UNSIGNED NOT NULL DEFAULT 0 ,
  PRIMARY KEY ('
id_grupo_atendimento', 'id_empresa') ,
  INDEX 'fk_tbl_fises_ddd_empresa_tbl_fises_ddd1' ('id_grupo_atendimento' ASC) ,
  INDEX 'fk_tbl_fises_ddd_empresa_tbl_empresa1' ('id_empresa' ASC) ,
  CONSTRAINT 'fk_tbl_fises_ddd_empresa_tbl_fises_ddd1'
    FOREIGN KEY ('id_grupo_atendimento' )
    REFERENCES 'infolog'.'tbl_fises_grupo_atendimento' ('id_grupo_atendimento' )
    ON DELETE NO ACTION
    ON UPDATE NO ACTION,
  CONSTRAINT 'fk_tbl_fises_ddd_empresa_tbl_empresa1'
    FOREIGN KEY ('id_empresa' )
    REFERENCES 'infolog'.'tbl_empresa' ('id_empresa' )
    ON DELETE NO ACTION
    ON UPDATE NO ACTION)
ENGINE = InnoDB

To reflect this model in Java, I created the classes below:

Company:

@Entity
@Table(name="empresa")
public class Empresa {

    @Id
    @GeneratedValue(strategy=GenerationType.IDENTITY) 
    @Column(name="id_empresa")
    private Integer id;

    @OneToMany(mappedBy = "empresa")
    private List<GrupoAtendimentoEmpresa> gruposAtendimento;

    public Integer getId() {
        return this.id;
    }

    public List<GrupoAtendimentoEmpresa> getGruposAtendimento() {
        return gruposAtendimento;
    }

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

    public void setGruposAtendimento(List<GrupoAtendimentoEmpresa> gruposAtendimento) {
        this.gruposAtendimento = gruposAtendimento;
    }
}

HomeGroup:

@Entity
@Table(name = "grupo_atendimento")
public class GrupoAtendimento {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "id_grupo_atendimento")
    private Integer id;

    @Column(name = "ddd")
    private String ddd;

    @OneToMany(mappedBy = "grupoAtendimento")
    private List<GrupoAtendimentoEmpresa> representantesTecnicos;

    public Integer getId() {
        return id;
    }

    public String getDdd() {
        return ddd;
    }

    public List<GrupoAtendimentoEmpresa> getRepresentantesTecnicos() {
        return representantesTecnicos;
    }

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

    public void setDdd(String ddd) {
        this.ddd = ddd;
    }

    public void setTechnicalRepresentatives(
            List<GrupoAtendimentoEmpresa> representantesTecnicos) {
        this.representantesTecnicos = representantesTecnicos;
    }
}

Association between Enterprise and GroupAtendance with the extra field, using another class as IdClass:

@Entity
@Table(name = "grupo_atendimento_empresa")
@IdClass(GrupoAtendimentoEmpresaId.class)
public class GrupoAtendimentoEmpresa {

    @Id
    @ManyToOne
    @JoinColumn(name = "id_grupo_atendimento")
    private GrupoAtendimento grupoAtendimento;

    @Id
    @ManyToOne
    @JoinColumn(name = "id_empresa")
    private Empresa empresa;

    @Column(name = "contador")
    private Integer contador;

    public GrupoAtendimento getGrupoAtendimento() {
        return grupoAtendimento;
    }

    public Empresa getEmpresa() {
        return empresa;
    }

    public Integer getContador() {
        return contador;
    }

    public void setGrupoAtendimento(GrupoAtendimento grupoAtendimento) {
        this.grupoAtendimento = grupoAtendimento;
    }

    public void setEmpresa(Empresa empresa) {
        this.empresa = empresa;
    }

    public void setContador(Integer contador) {
        this.contador = contador;
    }
}

And finally to IdClass:

public class GrupoAtendimentoEmpresaId implements Serializable {
    private static final long serialVersionUID = -3138856182021663633L;

    @Column(name = "id_grupo_atendimento")
    private int grupoAtendimento;

    @Column(name = "id_empresa")
    private int empresa;

    public int getGrupoAtendimento() {
        return grupoAtendimento;
    }

    public int getEmpresa() {
        return empresa;
    }

    public void setGrupoAtendimento(int grupoAtendimento) {
        this.grupoAtendimento = grupoAtendimento;
    }

    public void setEmpresa(int empresa) {
        this.empresa = empresa;
    }

    @Override
    public int hashCode() {
        return grupoAtendimento + empresa;
    }

    @Override
    public boolean equals(Object obj) {
        if (obj instanceof GrupoAtendimentoEmpresaId) {
            GrupoAtendimentoEmpresaId grupoAtendimentoEmpresaId = (GrupoAtendimentoEmpresaId) obj;
            return grupoAtendimentoEmpresaId.grupoAtendimento == grupoAtendimento
                    && grupoAtendimentoEmpresaId.empresa == empresa;
        }

        return false;
    }
}

With the database populated, I tried to run the code below:

GrupoAtendimentoEmpresaId id = new GrupoAtendimentoEmpresaId();
        id.setEmpresa(15513);
        id.setGrupoAtendimento(1);

        GrupoAtendimentoEmpresa grupoEmpresa = entityManager.find(
                GrupoAtendimentoEmpresa.class, id);

And I get the following exception:

javax.persistence.PersistenceException: org.hibernate.PropertyAccessException: could not set a field value by reflection setter of x.y.z.model.GrupoAtendimentoEmpresa.grupoAtendimento

I spent yesterday afternoon scouring the code and found no naming problems, and I made this implementation based on this Hebert's blog post .

Does anyone have any ideas? Thank you in advance.

    
asked by anonymous 08.10.2014 / 15:50

1 answer

3

Bruno,

In your GrupoAtendimentoEmpresa class, instead of using the @Id annotation in your Attributes group and company attributes, add two new attributes (integer type) that represent the ids of these entities and annotate them with @Id. Here's how your class should look:

@Entity
@Table(name = "grupo_atendimento_empresa")
@IdClass(GrupoAtendimentoEmpresaId.class)
public class GrupoAtendimentoEmpresa {

    @Id
    @Column(name = "id_grupo_atendimento", insertable = false, updatable = false)
    private int grupoAtendimentoId;

    @Id
    @Column(name = "id_empresa", insertable = false, updatable = false)
    private int empresaId;

    @ManyToOne
    @JoinColumn(name = "id_grupo_atendimento")
    private GrupoAtendimento grupoAtendimento;

    @ManyToOne
    @JoinColumn(name = "id_empresa")
    private Empresa empresa;

    @Column(name = "contador")
    private Integer contador;

    // Getters e Setters

}

I found this solution at this link: link

    
08.10.2014 / 19:01