title: org.hibernate.exception.ConstraintViolationException: Duplicate entry for key 'PRIMARY'
body: <p>I have a Book class which has a many to many mapping with the Author class. 
  So in the database, the tables are: Book--------Book_Author-------Author.
  Book_Author contains two columns which are Book_Id and Author_Id.
  Now whenever the application is up there is no problem in the save or update but on doing any of this operation second time there is a duplicate primary key  exception "Duplicate entry '123-147' for key 'PRIMARY'" corresponding to the insertion operation happening twice - one for the value of author selected currently and another for the previous request. 
  I have used trace in logger to detect the value of variables. The log is as follows:</p>
  
  <pre><code>SQL:104 - update Book set Availability=?, Copies_Issued=?, Description=?, Image=?, In_Stock=?, Isbn=?, Published_Year=?, Publisher_Name=?, status=?, Title=?, Total_Stock=? where Book_Id=?
  BasicBinder:83 - binding parameter [1] as [VARCHAR] - AVAILABLE
  BasicBinder:83 - binding parameter [2] as [INTEGER] - 0
  BasicBinder:83 - binding parameter [3] as [VARCHAR] - Test description
  BasicBinder:83 - binding parameter [4] as [VARCHAR] - 1414741446090.jpg
  BasicBinder:83 - binding parameter [5] as [INTEGER] - 123
  BasicBinder:71 - binding parameter [6] as [VARCHAR] - &lt;null&gt;
  BasicBinder:83 - binding parameter [7] as [INTEGER] - 2014
  BasicBinder:83 - binding parameter [8] as [VARCHAR] - Test pub.
  BasicBinder:71 - binding parameter [9] as [VARCHAR] - &lt;null&gt;
  BasicBinder:83 - binding parameter [10] as [VARCHAR] - Test book 12
  BasicBinder:83 - binding parameter [11] as [INTEGER] - 123
  BasicBinder:83 - binding parameter [12] as [INTEGER] - 123
  SQL:104 - delete from Book_Author where Book_Id=?
  BasicBinder:83 - binding parameter [1] as [INTEGER] - 123
  SQL:104 - insert into Book_Author (Book_Id, Author_Id) values (?, ?)
  BasicBinder:83 - binding parameter [1] as [INTEGER] - 123
  BasicBinder:83 - binding parameter [2] as [INTEGER] - 147
  SQL:104 - insert into Book_Author (Book_Id, Author_Id) values (?, ?)
  BasicBinder:83 - binding parameter [1] as [INTEGER] - 123
  BasicBinder:83 - binding parameter [2] as [INTEGER] - 147
  SqlExceptionHelper:143 - SQL Error: 1062, SQLState: 23000
  SqlExceptionHelper:144 - Duplicate entry '123-147' for key 'PRIMARY'
  GenericDaoImpl:100 - Update operation FAILED org.hibernate.exception.ConstraintViolationException: Duplicate entry '123-147' for key 'PRIMARY'
  HibernateFactory:133 - rolling back transaction
  HibernateFactory:117 - closing session
  AbstractBatchImpl:205 - HHH000010: On release of batch it still contained JDBC statements
  </code></pre>
  
  <p>Now as it can be seen that the first 123,147 is there because on update I didn't changed the authorName and the second one is because I changed it in previous request which was for the first time application was up. </p>
  
  <p>The Book class is as follows:</p>
  
  <pre><code>package com.dao.dto;
  
  import java.util.HashSet;
  import java.util.Set;
  
  import javax.persistence.CascadeType;
  import javax.persistence.Column;
  import javax.persistence.Entity;
  import javax.persistence.FetchType;
  import javax.persistence.GeneratedValue;
  import javax.persistence.Id;
  import javax.persistence.JoinColumn;
  import javax.persistence.JoinTable;
  import javax.persistence.ManyToMany;
  import javax.persistence.OneToMany;
  import javax.persistence.Transient;
  
  import org.codehaus.jackson.annotate.JsonManagedReference;
  import org.hibernate.annotations.Fetch;
  import org.hibernate.annotations.FetchMode;
  import org.springframework.web.multipart.MultipartFile;
  
  // TODO: Auto-generated Javadoc
  /**
   * The Class Book.
   */
  @Entity
  public class Book implements java.io.Serializable {
  
      /** The Constant serialVersionUID. */
      private static final long serialVersionUID = 1L;
  
      /** The book id. */
      private int bookId;
  
      /** The title. */
      private String title;
  
      /** The isbn. */
      private String isbn;
  
      /** The image. */
      private String image;
  
      /** The in stock. */
      private int inStock;
  
      /** The copies issued. */
      private int copiesIssued;
  
      /** The published year. */
      private int publishedYear;
  
      /** The publisher name. */
      private String publisherName;
  
      /** The description. */
      private String description;
  
      /** The availability. */
      private String availability;
  
      /** The total stock. */
      private int totalStock;
  
      /** The file. */
      private MultipartFile file;
  
      private String status;
  
      /** The authors. */
      private Set&lt;Author&gt; authors = new HashSet&lt;Author&gt;(0);
  
      /** The categories. */
      private Set&lt;Category&gt; categories = new HashSet&lt;Category&gt;(0);
  
      /** The languages. */
      private Set&lt;Language&gt; languages = new HashSet&lt;Language&gt;(0);
  
      /** The users favorite. */
      private Set&lt;User&gt; usersFavorite = new HashSet&lt;User&gt;(0);
  
      /** The return requests. */
      private Set&lt;ReturnRequest&gt; returnRequests = new HashSet&lt;ReturnRequest&gt;(0);
  
      /** The delivery requests. */
      private Set&lt;DeliveryRequest&gt; deliveryRequests = new HashSet&lt;DeliveryRequest&gt;(
              0);
  
      /**
       * Gets the book id.
       * 
       * @return the book id
       */
      @Id
      @GeneratedValue
      @Column(name = "Book_Id")
      public int getBookId() {
          return bookId;
      }
  
      /**
       * Sets the book id.
       * 
       * @param bookId
       *            the new book id
       */
      public void setBookId(int bookId) {
          this.bookId = bookId;
      }
  
      /**
       * Gets the title.
       * 
       * @return the title
       */
      @Column(name = "Title")
      public String getTitle() {
          return title;
      }
  
      /**
       * Sets the title.
       * 
       * @param title
       *            the new title
       */
      public void setTitle(String title) {
          this.title = title;
      }
  
      /**
       * Gets the copies issued.
       * 
       * @return the copies issued
       */
      @Column(name = "Copies_Issued")
      public int getCopiesIssued() {
          return copiesIssued;
      }
  
      /**
       * Sets the copies issued.
       * 
       * @param copiesIssued
       *            the new copies issued
       */
      public void setCopiesIssued(int copiesIssued) {
          this.copiesIssued = copiesIssued;
      }
  
  
  
      public String getStatus() {
          return status;
      }
  
      public void setStatus(String status) {
          this.status = status;
      }
  
      /**
       * Gets the isbn.
       * 
       * @return the isbn
       */
      @Column(name = "Isbn")
      public String getIsbn() {
          return isbn;
      }
  
      /**
       * Sets the isbn.
       * 
       * @param isbn
       *            the new isbn
       */
      public void setIsbn(String isbn) {
          this.isbn = isbn;
      }
  
      /**
       * Gets the image.
       * 
       * @return the image
       */
      @Column(name = "Image")
      public String getImage() {
          return image;
      }
  
      /**
       * Sets the image.
       * 
       * @param image
       *            the new image
       */
      public void setImage(String image) {
          this.image = image;
      }
  
      /**
       * Gets the in stock.
       * 
       * @return the in stock
       */
      @Column(name = "In_Stock")
      public int getInStock() {
          return inStock;
      }
  
      /**
       * Sets the in stock.
       * 
       * @param inStock
       *            the new in stock
       */
      public void setInStock(int inStock) {
          this.inStock = inStock;
      }
  
      /**
       * Gets the total stock.
       * 
       * @return the total stock
       */
      @Column(name = "Total_Stock")
      public int getTotalStock() {
          return totalStock;
      }
  
      /**
       * Sets the total stock.
       * 
       * @param totalStock
       *            the new total stock
       */
      public void setTotalStock(int totalStock) {
          this.totalStock = totalStock;
      }
  
      /**
       * Gets the published year.
       * 
       * @return the published year
       */
      @Column(name = "Published_Year")
      public int getPublishedYear() {
          return publishedYear;
      }
  
      /**
       * Sets the published year.
       * 
       * @param publishedYear
       *            the new published year
       */
      public void setPublishedYear(int publishedYear) {
          this.publishedYear = publishedYear;
      }
  
      /**
       * Gets the publisher name.
       * 
       * @return the publisher name
       */
      @Column(name = "Publisher_Name")
      public String getPublisherName() {
          return publisherName;
      }
  
      /**
       * Sets the publisher name.
       * 
       * @param publisherName
       *            the new publisher name
       */
      public void setPublisherName(String publisherName) {
          this.publisherName = publisherName;
      }
  
      /**
       * Gets the description.
       * 
       * @return the description
       */
      @Column(name = "Description")
      public String getDescription() {
          return description;
      }
  
      /**
       * Sets the description.
       * 
       * @param description
       *            the new description
       */
      public void setDescription(String description) {
          this.description = description;
      }
  
      /**
       * Gets the availability.
       * 
       * @return the availability
       */
      @Column(name = "Availability")
      public String getAvailability() {
          return availability;
      }
  
      /**
       * Sets the availability.
       * 
       * @param availability
       *            the new availability
       */
      public void setAvailability(String availability) {
          this.availability = availability;
      }
  
      /**
       * Gets the authors.
       * 
       * @return the authors
       */
      @JsonManagedReference
      @ManyToMany(fetch = FetchType.EAGER)
      @JoinTable(name = "Book_Author", joinColumns = { @JoinColumn(name = "Book_Id", nullable = false) }, inverseJoinColumns = { @JoinColumn(name = "Author_Id", nullable = false) })
      public Set&lt;Author&gt; getAuthors() {
          return authors;
      }
  
      /**
       * Sets the authors.
       * 
       * @param authors
       *            the new authors
       */
      public void setAuthors(Set&lt;Author&gt; authors) {
          this.authors = authors;
      }
  
      /**
       * Gets the categories.
       * 
       * @return the categories
       */
      @JsonManagedReference
      @ManyToMany(fetch = FetchType.EAGER)
      @JoinTable(name = "Book_Category", joinColumns = { @JoinColumn(name = "Book_Id", nullable = false) }, inverseJoinColumns = { @JoinColumn(name = "Category_Id", nullable = false) })
      public Set&lt;Category&gt; getCategories() {
          return categories;
      }
  
      /**
       * Sets the categories.
       * 
       * @param categories
       *            the new categories
       */
      public void setCategories(Set&lt;Category&gt; categories) {
          this.categories = categories;
      }
  
      /**
       * Gets the languages.
       * 
       * @return the languages
       */
      @ManyToMany(fetch = FetchType.EAGER)
      @JoinTable(name = "Book_Language", joinColumns = { @JoinColumn(name = "Book_Id", nullable = false) }, inverseJoinColumns = { @JoinColumn(name = "Language_Id", nullable = false) })
      public Set&lt;Language&gt; getLanguages() {
          return languages;
      }
  
      /**
       * Sets the languages.
       * 
       * @param languages
       *            the new languages
       */
      public void setLanguages(Set&lt;Language&gt; languages) {
          this.languages = languages;
      }
  
      /**
       * Gets the users favorite.
       * 
       * @return the users favorite
       */
      @ManyToMany(fetch = FetchType.EAGER, cascade = CascadeType.ALL)
      @JoinTable(name = "User_Favorite", joinColumns = { @JoinColumn(name = "Book_Id", nullable = false) }, inverseJoinColumns = { @JoinColumn(name = "User_Id", nullable = false) })
      public Set&lt;User&gt; getUsersFavorite() {
          return usersFavorite;
      }
  
      /**
       * Sets the users favorite.
       * 
       * @param usersFavorite
       *            the new users favorite
       */
      public void setUsersFavorite(Set&lt;User&gt; usersFavorite) {
          this.usersFavorite = usersFavorite;
      }
  
      /**
       * Gets the file.
       * 
       * @return the file
       */
      @Transient
      public MultipartFile getFile() {
          return file;
      }
  
      /**
       * Sets the file.
       * 
       * @param file
       *            the new file
       */
      public void setFile(MultipartFile file) {
          this.file = file;
      }
  
      /*
       * (non-Javadoc)
       * 
       * @see java.lang.Object#toString()
       */
      @Override
      public String toString() {
          return getTitle();
      }
  
      /**
       * Gets the return requests.
       * 
       * @return the return requests
       */
      @OneToMany(fetch = FetchType.EAGER, mappedBy = "book")
      public Set&lt;ReturnRequest&gt; getReturnRequests() {
          return returnRequests;
      }
  
      /**
       * Sets the return requests.
       * 
       * @param returnRequests
       *            the new return requests
       */
      public void setReturnRequests(Set&lt;ReturnRequest&gt; returnRequests) {
          this.returnRequests = returnRequests;
      }
  
      /**
       * Gets the delivery requests.
       * 
       * @return the delivery requests
       */
      @OneToMany(fetch = FetchType.EAGER, mappedBy = "book")
      public Set&lt;DeliveryRequest&gt; getDeliveryRequests() {
          return deliveryRequests;
      }
  
      /**
       * Sets the delivery requests.
       * 
       * @param deliveryRequests
       *            the new delivery requests
       */
      public void setDeliveryRequests(Set&lt;DeliveryRequest&gt; deliveryRequests) {
          this.deliveryRequests = deliveryRequests;
      }
  
      /*
       * (non-Javadoc)
       * 
       * @see java.lang.Object#hashCode()
       */
      @Override
      public int hashCode() {
          final int prime = 31;
          int result = 1;
          result = prime * result + bookId;
          return result;
      }
  
      /*
       * (non-Javadoc)
       * 
       * @see java.lang.Object#equals(java.lang.Object)
       */
      @Override
      public boolean equals(Object obj) {
          if (this == obj) {
              return true;
          }
          if (obj == null) {
              return false;
          }
          if (getClass() != obj.getClass()) {
              return false;
          }
          Book other = (Book) obj;
          if (bookId != other.bookId) {
              return false;
          }
          return true;
      }
  
  }
  </code></pre>
  
  <p>The Author class is as follows:</p>
  
  <pre><code>package com.dao.dto;
  
  import java.io.Serializable;
  import java.util.HashSet;
  import java.util.Set;
  
  import javax.persistence.Column;
  import javax.persistence.Entity;
  import javax.persistence.FetchType;
  import javax.persistence.GeneratedValue;
  import javax.persistence.Id;
  import javax.persistence.JoinColumn;
  import javax.persistence.JoinTable;
  import javax.persistence.ManyToMany;
  import javax.persistence.Table;
  
  import org.codehaus.jackson.annotate.JsonBackReference;
  import org.hamcrest.Factory;
  import org.hibernate.annotations.Fetch;
  import org.hibernate.annotations.FetchMode;
  
  // TODO: Auto-generated Javadoc
  /**
   * The Class Author.
   */
  @Entity
  @Table(name = "Author")
  public class Author implements Serializable {
  
      /** The Constant serialVersionUID. */
      private static final long serialVersionUID = 1L;
  
      /** The author id. */
      private int authorId;
  
      /** The author name. */
      private String authorName;
  
      /** The description. */
      private String description;
  
      /** The books. */
      private Set&lt;Book&gt; books = new HashSet&lt;Book&gt;(0);
  
      /**
       * Gets the author id.
       * 
       * @return the author id
       */
      @Id
      @GeneratedValue
      @Column(name = "Author_Id")
      public int getAuthorId() {
          return authorId;
      }
  
      /**
       * Sets the author id.
       * 
       * @param authorId
       *            the new author id
       */
      public void setAuthorId(int authorId) {
          this.authorId = authorId;
      }
  
      /**
       * Gets the author name.
       * 
       * @return the author name
       */
      @Column(name = "Author_Name", nullable = false)
      public String getAuthorName() {
          return authorName;
      }
  
      /**
       * Sets the author name.
       * 
       * @param authorName
       *            the new author name
       */
      public void setAuthorName(String authorName) {
          this.authorName = authorName;
      }
  
      /**
       * Gets the description.
       * 
       * @return the description
       */
      @Column(name = "Description")
      public String getDescription() {
          return description;
      }
  
      /**
       * Sets the description.
       * 
       * @param description
       *            the new description
       */
      public void setDescription(String description) {
          this.description = description;
      }
  
      /*
       * (non-Javadoc)
       * 
       * @see java.lang.Object#toString()
       */
      public String toString() {
          return getAuthorName();
      }
  
      /**
       * Gets the books.
       * 
       * @return the books
       */
      @JsonBackReference
      @ManyToMany(mappedBy ="authors" ,fetch = FetchType.LAZY)
      public Set&lt;Book&gt; getBooks() {
          return books;
      }
  
      /**
       * Sets the books.
       * 
       * @param books
       *            the new books
       */
      public void setBooks(Set&lt;Book&gt; books) {
          this.books = books;
      }
  
  }
  </code></pre>
  
  <p>Initially I was getting NonUniqueObjectException which I removed by removing the cascade. Now I am stuck on this one. Kindly, explain the cause of this error. Thank you. </p>