Tumladhir
Tumladhir

Reputation: 170

Using @GeneratedValue(strategy=GenerationType.IDENTITY) in populated database causes PK constraint error

I'm trying to add FeedbackItem items to my database. The general idea is that an existing object of type Group can receive multiple FeedbackItem objects. Afterwards I update the object:

groupDAO.startTransaction();
groupDAO.update(selectedGroup);
groupDAO.commitTransaction();

//in groupDAO
public T update(T entity){
   return em.merge(entity);
}

I'm not suring whether it is JPA causing the issue or not, but the following error will appear:

Internal Exception: java.sql.SQLIntegrityConstraintViolationException: The statement was aborted because it would have caused a duplicate key value in a unique or primary key constraint or unique index identified by 'SQL170430012202680' defined on 'FEEDBACKITEM'.

After some more debugging I found the following entries:

[EL Fine]: sql: 2017-04-30 01:22:14.977-- #### VALUES (?, ?) bind => [sampleText, 2]

[EL Fine]: sql: 2017-04-30 01:22:14.997--ClientSession(889348271)--Thread(Thread[JavaFX Application Thread,5,main])--VALUES(1)

Does VALUES(1) mean that it's trying to insert the object under the ID 1? It's the only lead I currently have. My database is populated with 10 entries, having an ID ranging from 1 to 10.

Below is the class I'm trying to persist to the database:

@Entity
public class FeedbackItem implements Serializable{
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private int feedbackId;

    private String feedback;

    @ManyToOne(cascade = CascadeType.PERSIST)
    private User ownerFeedback;

    protected FeedbackItem(){

    }
}

I tested my code without @GeneratedValue(strategy=GenerationType.IDENTITY) and assigned ID's manually. This works without any issues.

EDIT: below is the Group entity:

@Entity
public class Group implements IReadOnlyGroup {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private int groupId;
    private String name;

    @OneToMany(mappedBy = "group")
    private List<Action> actions;

    @OneToMany(cascade = CascadeType.PERSIST)
    private List<Proposal> proposals;

    @OneToMany(mappedBy = "group")
    private List<Motivation> motivations;

    @OneToOne(mappedBy = "group")
    private GroupState currentState;

    public Groep() {
    }
}

The Group object contains the FeedbackItem objects indirectely. Each Proposal stores one FeedbackItem

Entity
public class Proposal {
    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long id;

    @Temporal(TemporalType.TIMESTAMP)
    private Date date = null;

    @ManyToMany
    private List<Action> actions;

    @OneToOne
    private FeedbackItem feedbackitem;

    boolean approved;

    protected Proposal() {

    }

    public Proposal ( List<Action> actions, String feedback, boolean approved, User owner){
        this.date = new Date();
        this.actions = actions;
        this.approved = approved;
        this.feedbackitem = new FeedBackItem(feedback, owner);
    }
}

Upvotes: 0

Views: 1249

Answers (1)

Peter Š&#225;ly
Peter Š&#225;ly

Reputation: 2933

@OneToMany(cascade = CascadeType.PERSIST) 
private List<Proposal> proposals;

Means that Proposal entities are persisted together with Group, but not merged. Other entities should be persisted separately before assigning and persisting Group entity. I would try remove this cascade attribute, and check if problem still exists.

Upvotes: 1

Related Questions