Reputation: 41
OMG! i have been figuring out how to solve the following problem. I googled and tried all the possible ways, but no luck.
Caused by: Exception [EclipseLink-30005] (Eclipse Persistence Services - 2.3.2.v20111125-r10461): org.eclipse.persistence.exceptions.PersistenceUnitLoadingException
Exception Description: An exception was thrown while searching for persistence archives with ClassLoader: sun.misc.Launcher$AppClassLoader@93dee9
Internal Exception: javax.persistence.PersistenceException: Exception [EclipseLink-28018] (Eclipse Persistence Services - 2.3.2.v20111125-r10461): org.eclipse.persistence.exceptions.EntityManagerSetupException
Exception Description: Predeployment of PersistenceUnit [RateProfessorPU] failed.
Internal Exception: Exception [EclipseLink-7220] (Eclipse Persistence Services - 2.3.2.v20111125-r10461): org.eclipse.persistence.exceptions.ValidationException
Exception Description: The @JoinColumns on the annotated element [field professorId] from the entity class [class rateprofessor.database.entity.Rating] is incomplete. When the source entity class uses a composite primary key, a @JoinColumn must be specified for each join column using the @JoinColumns. Both the name and the referencedColumnName elements must be specified in each such @JoinColumn.
at org.eclipse.persistence.exceptions.PersistenceUnitLoadingException.exceptionSearchingForPersistenceResources(PersistenceUnitLoadingException.java:127)
at org.eclipse.persistence.jpa.PersistenceProvider.createEntityManagerFactory(PersistenceProvider.java:115)
at javax.persistence.Persistence.createEntityManagerFactory(Unknown Source)
at javax.persistence.Persistence.createEntityManagerFactory(Unknown Source)
at rateprofessor.database.DBFactory.<clinit>(DBFactory.java:27)
... 2 more
I'm using netbeans and eclipselink (jpa 2.0).
I attach the two table structures.
For Professor Table, the name and departmentID are the composite primary key and the id is the autogenerated unique key, which is the foreign key to the rating table.
Here are the java classes for the two tables:
Professor
@Entity
@Table(name = "professor", catalog = "rateprofessor", schema = "", uniqueConstraints = {
@UniqueConstraint(columnNames = {"id"})})
@XmlRootElement
@NamedQueries({
@NamedQuery(name = "Professor.findAll", query = "SELECT p FROM Professor p"),
@NamedQuery(name = "Professor.findByName", query = "SELECT p FROM Professor p WHERE p.professorPK.name = :name"),
@NamedQuery(name = "Professor.findByDepartmentID", query = "SELECT p FROM Professor p WHERE p.professorPK.departmentID = :departmentID"),
@NamedQuery(name = "Professor.findByEmail", query = "SELECT p FROM Professor p WHERE p.email = :email"),
@NamedQuery(name = "Professor.findByPhone", query = "SELECT p FROM Professor p WHERE p.phone = :phone"),
@NamedQuery(name = "Professor.findByTitle", query = "SELECT p FROM Professor p WHERE p.title = :title"),
@NamedQuery(name = "Professor.findById", query = "SELECT p FROM Professor p WHERE p.id = :id"),
@NamedQuery(name = "Professor.findByFirstName", query = "SELECT p FROM Professor p WHERE p.firstName = :firstName"),
@NamedQuery(name = "Professor.findByLastName", query = "SELECT p FROM Professor p WHERE p.lastName = :lastName")})
public class Professor implements Serializable {
private static final long serialVersionUID = 1L;
@EmbeddedId
protected ProfessorPK professorPK;
@Column(name = "email", length = 255)
private String email;
@Column(name = "phone", length = 255)
private String phone;
@Basic(optional = false)
@Column(name = "title", nullable = false, length = 255)
private String title;
@Basic(optional = false)
@Column(name = "id", nullable = false)
private int id;
@Column(name = "firstName", length = 45)
private String firstName;
@Column(name = "lastName", length = 45)
private String lastName;
@JoinColumn(name = "departmentID", referencedColumnName = "id", nullable = false, insertable = false, updatable = false)
@ManyToOne(optional = false)
private Department department;
@OneToMany(cascade = CascadeType.ALL, mappedBy = "professorId")
private Collection<Rating> ratingCollection;
public Professor() {
}
public Professor(ProfessorPK professorPK) {
this.professorPK = professorPK;
}
public Professor(ProfessorPK professorPK, String title, int id) {
this.professorPK = professorPK;
this.title = title;
this.id = id;
}
public Professor(String name, int departmentID) {
this.professorPK = new ProfessorPK(name, departmentID);
}
public ProfessorPK getProfessorPK() {
return professorPK;
}
public void setProfessorPK(ProfessorPK professorPK) {
this.professorPK = professorPK;
}
public String getEmail() {
return email;
}
public void setEmail(String email) {
this.email = email;
}
public String getPhone() {
return phone;
}
public void setPhone(String phone) {
this.phone = phone;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public int getId() {
return id;
}
public void setId(int id) {
this.id = id;
}
public String getFirstName() {
return firstName;
}
public void setFirstName(String firstName) {
this.firstName = firstName;
}
public String getLastName() {
return lastName;
}
public void setLastName(String lastName) {
this.lastName = lastName;
}
public Department getDepartment() {
return department;
}
public void setDepartment(Department department) {
this.department = department;
}
@XmlTransient
public Collection<Rating> getRatingCollection() {
return ratingCollection;
}
public void setRatingCollection(Collection<Rating> ratingCollection) {
this.ratingCollection = ratingCollection;
}
@Override
public int hashCode() {
int hash = 0;
hash += (professorPK != null ? professorPK.hashCode() : 0);
return hash;
}
@Override
public boolean equals(Object object) {
// TODO: Warning - this method won't work in the case the id fields are not set
if (!(object instanceof Professor)) {
return false;
}
Professor other = (Professor) object;
if ((this.professorPK == null && other.professorPK != null) || (this.professorPK != null && !this.professorPK.equals(other.professorPK))) {
return false;
}
return true;
}
@Override
public String toString() {
return "rateprofessor.database.entity.Professor[ professorPK=" + professorPK + " ]";
}
}
Rating
@Entity
@Table(name = "rating", catalog = "rateprofessor", schema = "")
@XmlRootElement
@NamedQueries({
@NamedQuery(name = "Rating.findAll", query = "SELECT r FROM Rating r"),
@NamedQuery(name = "Rating.findById", query = "SELECT r FROM Rating r WHERE r.id = :id"),
@NamedQuery(name = "Rating.findByDatetime", query = "SELECT r FROM Rating r WHERE r.datetime = :datetime"),
@NamedQuery(name = "Rating.findByClass1", query = "SELECT r FROM Rating r WHERE r.class1 = :class1"),
@NamedQuery(name = "Rating.findBySection", query = "SELECT r FROM Rating r WHERE r.section = :section")})
public class Rating implements Serializable {
private static final long serialVersionUID = 1L;
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
@Basic(optional = false)
@Column(name = "id", nullable = false)
private Integer id;
@Basic(optional = false)
@Column(name = "datetime", nullable = false)
@Temporal(TemporalType.TIMESTAMP)
private Date datetime;
@Column(name = "class", length = 45)
private String class1;
@Column(name = "section")
private Integer section;
@JoinColumn(name = "user_id", referencedColumnName = "id", nullable = false)
@ManyToOne(optional = false)
private User userId;
@JoinColumn(name = "grade", referencedColumnName = "id")
@ManyToOne
private Grade grade;
@JoinColumn(name = "comment_id", referencedColumnName = "id", nullable = false)
@ManyToOne(optional = false)
private Comment commentId;
@JoinColumn(name = "professor_id", referencedColumnName = "id", nullable = false)
@ManyToOne(optional = false)
private Professor professorId;
@OneToMany(cascade = CascadeType.ALL, mappedBy = "rating")
private Collection<RatingItem> ratingItemCollection;
public Rating() {
}
public Rating(Integer id) {
this.id = id;
}
public Rating(Integer id, Date datetime) {
this.id = id;
this.datetime = datetime;
}
public Integer getId() {
return id;
}
public void setId(Integer id) {
this.id = id;
}
public Date getDatetime() {
return datetime;
}
public void setDatetime(Date datetime) {
this.datetime = datetime;
}
public String getClass1() {
return class1;
}
public void setClass1(String class1) {
this.class1 = class1;
}
public Integer getSection() {
return section;
}
public void setSection(Integer section) {
this.section = section;
}
public User getUserId() {
return userId;
}
public void setUserId(User userId) {
this.userId = userId;
}
public Grade getGrade() {
return grade;
}
public void setGrade(Grade grade) {
this.grade = grade;
}
public Comment getCommentId() {
return commentId;
}
public void setCommentId(Comment commentId) {
this.commentId = commentId;
}
public Professor getProfessorId() {
return professorId;
}
public void setProfessorId(Professor professorId) {
this.professorId = professorId;
}
@XmlTransient
public Collection<RatingItem> getRatingItemCollection() {
return ratingItemCollection;
}
public void setRatingItemCollection(Collection<RatingItem> ratingItemCollection) {
this.ratingItemCollection = ratingItemCollection;
}
@Override
public int hashCode() {
int hash = 0;
hash += (id != null ? id.hashCode() : 0);
return hash;
}
@Override
public boolean equals(Object object) {
// TODO: Warning - this method won't work in the case the id fields are not set
if (!(object instanceof Rating)) {
return false;
}
Rating other = (Rating) object;
if ((this.id == null && other.id != null) || (this.id != null && !this.id.equals(other.id))) {
return false;
}
return true;
}
@Override
public String toString() {
return "rateprofessor.database.entity.Rating[ id=" + id + " ]";
}
}
Please help me. I seriously need help. Thanks you so much.
Upvotes: 1
Views: 7970
Reputation: 21145
The problem is that JPA does not allow you to have a foreign keys to fields that are not the target entities id fields. In your case, Rating has a professor_id column that is a foreign key to Id, but Id is not the primary key - name and departmentID within the embeddedId are. The simplest solution is to make the ID field within Professor the ID - as far as JPA is concerned anyway. The table itself does not need to change.
This will allow you to use the professor_id as a foreign key to Professor's ID column and remain portable among JPA providers, and still use Name + departmentID as the pk in the database.
Upvotes: 1