I mended all by myself. If someone has a similar problem, the code is down here.
I don't know if all changes were necessary, because I did all and after that proved the web app, but they sure are correct for my design so I'm not removing any of them. The changes are:
- I changed the getters and setters for the calendar field so they could get and set as if it were a Date field, but the precission of Calendar is working down there.
- I added the @Temporal annotation because of a Date field being part of the composite key of EstEmp.
- I used the @AssociationOverrides anottation for describing the @ManyToOne relation from the Incidencia to the EstEmp.
- The code over the getter of the EstEmp Object with composite key contained in Incidencia is almost the same, I needed to change something in the database because it wasn't prepared for having two relations with two EstEmp objects, but for the rest is similar.
- I used the @AttributeOverrides annotation for describing the mapping of part of the foreign key referencing the Date field of the foreign composite key. Maybe this is the unnecesary part and could be removed, because this is told too in the JoinColumns, but I'm not sure.
- I used as well @AttributeOverrides over the Id composite key field in EstEmp for describing the composite key, as the Manning book of Hibernate says.
Finally, the code:
Code:
/* The object containing the composite key of EstEmp */
@Embeddable
public class EstEmpId implements Serializable {
private Empleado empleado;
private Calendar tvi=Calendar.getInstance();
public EstEmpId() {}
public EstEmpId(Empleado empleado, Calendar tvi) {
this.empleado = empleado;
if(tvi!=null) this.tvi=tvi;
}
public EstEmpId(Empleado empleado, Date tvi) {
this.empleado = empleado;
if(tvi!=null) setTvi(tvi);
}
@ManyToOne(optional=false, fetch=FetchType.EAGER)
@JoinColumn(name="idEmp")
public Empleado getEmpleado() {
return empleado;
}
public void setEmpleado(Empleado empleado) {
this.empleado = empleado;
}
@Temporal(TemporalType.DATE)
public Date getTvi() {
return tvi.getTime();
}
public void setTvi(Date tvi) {
javax.swing.JOptionPane.showMessageDialog(new javax.swing.JFrame(), "tvi="+tvi);
this.tvi.setTime(tvi);
}
}
/* EstEmp, the referenced object */
@Entity
public class EstEmp {
private EstEmpId id;
private Calendar tvf;
private String numCuenta;
private String domicilio;
private Double sueldo;
private Puesto puesto;
public EstEmp() {}
public EstEmp(EstEmpId eei, Calendar tvf, String numCuenta,
String domicilio, Double sueldo, Puesto puesto) {
super();
this.id = eei;
this.tvf = tvf;
this.numCuenta = numCuenta;
this.domicilio = domicilio;
if(sueldo != null) this.sueldo = sueldo;
else this.sueldo = 0.0;
this.puesto = puesto;
}
@Id
@AttributeOverrides({
@AttributeOverride(name="idEmp", column= @Column(name="idEmp")),
@AttributeOverride(name="tvi", column= @Column(name="tvi"))
})
public EstEmpId getId() {
return id;
}
@ManyToOne(fetch=FetchType.EAGER)
@JoinColumn(name="idPuesto")
public Puesto getPuesto() {
return puesto;
}
@Temporal(TemporalType.DATE)
public Date getTvf() {
if(tvf!=null) return tvf.getTime();
else return null;
}
public String getNumCuenta() {
return numCuenta;
}
public String getDomicilio() {
return domicilio;
}
public Double getSueldo() {
return sueldo;
}
public void setId(EstEmpId estEmpId) {
this.id = estEmpId;
}
public void setTvf(Date tvf) {
if(tvf!=null) {
Calendar c = Calendar.getInstance();
c.setTime(tvf);
this.tvf = c;
}
else this.tvf = null;
}
}
/* Incidencia, the class wichs references to the composite foreign key */
@Entity
@AssociationOverrides({
@AssociationOverride(name="empAlta.id",
joinColumns= {
@JoinColumn(name="idEmpAlta", referencedColumnName="idEmp"),
@JoinColumn(name="tviAlta", referencedColumnName="tvi")
}),
@AssociationOverride(name="empBaja.id",
joinColumns= {
@JoinColumn(name="idEmpBaja", referencedColumnName="idEmp"),
@JoinColumn(name="tviBaja", referencedColumnName="tvi")
})
})
@AttributeOverrides({
@AttributeOverride(name="tviAlta", column= @Column(name="tviAlta")),
@AttributeOverride(name="tviBaja", column= @Column(name="tviBaja"))
})
public class Incidencia {
private Long numIncidencia;
private String nombre;
private Calendar fecha;
private String desc;
private EstEmp empAlta, empBaja;
private Sala sala;
public Incidencia() {}
public Incidencia(String nombre, Calendar fecha, String desc,
EstEmp empAlta, Sala sala) {
super();
this.nombre = nombre;
this.fecha = fecha;
this.desc = desc;
this.empAlta = empAlta;
this.sala = sala;
}
@Column(name = "idIncidencia")
@SequenceGenerator(name = "idIncidenciaGenerator", sequenceName = "IncidenciaSeq")
@Id
@GeneratedValue(strategy = GenerationType.AUTO, generator = "idIncidenciaGenerator")
public Long getNumIncidencia() {
return numIncidencia;
}
@ManyToOne(optional=false, fetch=FetchType.EAGER)
@JoinColumn(name="idSala")
public Sala getSala() {
return sala;
}
@ManyToOne(optional=false, fetch=FetchType.EAGER)
@JoinColumns({
@JoinColumn(name="tviAlta", insertable=true, updatable=false, referencedColumnName="tvi"),
@JoinColumn(name="idEmpAlta", insertable=true, updatable=false, referencedColumnName="idEmp")
})
public EstEmp getEmpAlta() {
return empAlta;
}
@ManyToOne(optional=true, fetch=FetchType.EAGER)
@JoinColumns({
@JoinColumn(name="tviBaja", insertable=false, updatable=true, referencedColumnName="tvi"),
@JoinColumn(name="idEmpBaja", insertable=false, updatable=true, referencedColumnName="idEmp")
})
public EstEmp getEmpBaja() {
return empBaja;
}
public String getNombre() {
return nombre;
}
@Column(name="fecha")
public Date getFecha() {
return fecha.getTime();
}
@Column(name="descripcion")
public String getDesc() {
return desc;
}
@Transient
public String getDate() {
return DateHandler.dateToString(fecha.getTime());
}
/* Rest of getters/setters down here */
}