Does hibernate preserve the order of a LinkedHashSet and if so, how?

12,663

First: I assume you are talking about a relationship between two entities. Something like

@Entity
public class A {
@ManyToMany
    @JoinTable(name = "A_B", joinColumns = { @JoinColumn(name = "A_fk") }, inverseJoinColumns = { @JoinColumn(name = "B_fk") })
    private Set<B> bSet = new LinkedHashSet<B>();
}

Hibernate does not preserve the order by itself!

If you have a look at the classes used when entity A is loaded from the database, then the Set bSet is of type PersistentSet, which is a wrapper around another Set, and this is (in my case) a normal HashSet. (HashSet does not preserve the order of its elements.)

Even if Hibernate used List or LinkedHashSet, it is still inadvisable to base the implementation on the natural (not guaranteed) database order. For MySQL it is some kind of anti-pattern.

But you can use the @Sort annotation (org.hibernate.annotations.Sort) to make your sorting explicit. For example:

@OneToMany(mappedBy = "as")
@Sort(type = SortType.COMPARATOR, comparator = MyBComparator.class);
public SortedSet<C> cs;

@see: Ordering return of Child objects in JPA query


Added by Łukasz Rzeszotarski on 1th Sep 2012:

But we have to remember that using @Sort annotation causes sorting objects in memory (jvm) and not in sql. Instead we can use @OrderBy annotation that causes sorting on the sql server side. Both of these annotations have in my (Łukasz Rzeszotarski ) opinion one weakness that set up ordering by default. I (Łukasz Rzeszotarski ) would rather hibernate uses own LinkedHashSet implementation when it 'sees' that order by clause is used.

@see: Hibernate ordering in sql

Share:
12,663

Related videos on Youtube

Erik Stens
Author by

Erik Stens

Updated on December 26, 2020

Comments

  • Erik Stens
    Erik Stens over 3 years

    Does hibernate preserve the order of a LinkedHashSet and if so, how? In case this depends on the type of database, I'd like to know this for PostgreSQL.

    Background:

    I know what a LinkedHashSet is for, and the reason I'm asking this is because I'm logging the names of some functions I execute to a 'logError' table that has a many-to-many relation to some 'functionName' table. I need these functions to remain in the same order as when I executed them, so first I find the corresponding 'functionName' objects, put them in a LinkedHashSet (after each function that failed) and then I persist the 'logError' object.

    Now when I get the 'logError' object from the database again, will it still be ordered? And if so, I was curious how this is done by Hibernate.

    • Rémi Vennereau
      Rémi Vennereau over 13 years
      Have you tried annotating with @OrderColumn? (maybe that is a JPA annotation)
  • Rémi Vennereau
    Rémi Vennereau over 13 years
    LinkedHashSet has insertion order
  • Ralph
    Ralph almost 12 years
    @Łukasz Rzeszotarski: if you edit someones post again in this way, then make at least clear that this was your statement, and not the original authors one!