views:

331

answers:

1

I am trying to map the following:

public class Person{
  ...
  @ManyToMany(cascade = { CascadeType.PERSIST, CascadeType.MERGE })
  @JoinTable(name = "person_categories", joinColumns = @JoinColumn(name = "personId"), inverseJoinColumns = @JoinColumn(name = "categoryId"))
  private Set<Category> categories

  ...
}

public class Category {
  @Id
  @GeneratedValue(strategy = GenerationType.AUTO)
  @Column(name = "categoryId")
  private Integer id;

  @Column(unique = true)
  private Sting name

  ...
}

When I attempt to save a Person object, the categories are inserted, but duplicates are stored into the table. How can I ensure each category is unique in its table and while maintaining transitive persistence? I have tried making the name column unique, but that only helped by throwing constraint errors.

+1  A: 

If you don't override hashCode() and equals() to be meaningful for the Category class, then you will get duplicates in your Set (if you're adding duplicates to begin with). If the name field is what differentiates objects, try:

public int hashCode() {
    return name.hashCode();
}

public Object equals (Object o) {
    if (o instanceof Category) {
        return ((Category)o).name.equals(this.name);
    }
    return false;
}
Kevin