In all cases you will need a composite key (since on the side of the bank the PK is composed the JPA should keep this template).
This can be done in two ways:
ID Entity + @IdClass
public class NotaAvaliacaoAlunoPK implements Serializable {
private Integer idAluno;
private Integer idAvaliacao;
// Outros campos da PK se existirem
// Getters & setters, equals e hashCode
}
@Entity
@IdClass(value=NotaAvaliacaoAlunoPK.class)
public class NotaAvaliacaoAluno implements Serializable {
@Id @Column(name="ID_ALUNO")
private Integer idAluno;
@Id @Column(name="ID_AVALIACAO")
private Integer idAvaliacao;
// Outros campos da PK se existirem
@Column
private String outroCampoQualquer;
// Getters & setters
}
Multiple columns of IDs + @EmbeddedId
@Embeddable
public class NotaAvaliacaoAlunoPK implements Serializable {
@Column(name="ID_ALUNO")
private Integer idAluno;
@Column(name="ID_AVALIACAO")
private Integer idAvaliacao;
// Getters & setters, equals e hashCode
}
@Entity
public class NotaAvaliacaoAluno implements Serializable {
@EmbeddedId
private NotaAvaliacaoAlunoPK id;
@Column
private String outroCampoQualquer;
}
The second decision is to know who sends on the Primary Key, whether it is the PK fields directly or whether they are the relationships with Aluno
and Avaliacao
.
Primary key fields, make relationships do not update the database:
@ManyToOne(fetch=FetchType.LAZY)
@JoinColumn(name="ID_ALUNO", insertable=false, updatable=false)
private Aluno aluno;
@ManyToOne(fetch=FetchType.LAZY)
@JoinColumn(name="ID_AVALIACAO", insertable=false, updatable=false)
private Avaliacao avaliacao;
If the relationships are, make sure that the PK fields do not update the database and that the entities of the relationships do (through @PrimaryKeyJoinColumn
):
@Column(name="ID_ALUNO", insertable=false, updatable=false)
private Integer idAluno;
@Column(name="ID_AVALIACAO", insertable=false, updatable=false)
private Integer idAvaliacao;
@ManyToOne(fetch=FetchType.LAZY)
@PrimaryKeyJoinColumn(name="ID_ALUNO")
private Aluno aluno;
@ManyToOne(fetch=FetchType.LAZY)
@PrimaryKeyJoinColumn(name="ID_AVALIACAO")
private Avaliacao avaliacao;
See that I did not even merit Element Collections to make it even more complicated but the use of collections may be a good idea if the evaluation note values do not make sense outside the context of the parent object.
On the "most correct" way of modeling a problem, there is no easy answer. It may be that in your application it makes more sense to manipulate ids directly, it might make more sense to build an ID object. Perhaps it makes more sense to deal with PK values directly (by inserting student ids and evaluations), perhaps the opposite makes sense (look up the Pupil object and the whole Evaluation object from the database and set up the relationships).
And there are still those who prefer to appeal to a good old map:
@OneToMany(mappedBy="aluno")
@MapKeyColumn(name="ID_AVALIACAO")
private Map<Integer, NotaAvaliacao> notas;