17

This works:

<hibernate-mapping>
    <class name="Train" table="Trains">

        <id column="id" name="id" type="java.lang.String" length="4">
            <generator class="assigned" />
        </id>
        <set name="trips" cascade="all">
            <key column="trainId"/>
            <one-to-many class="Trip"/>
        </set>

    </class>
</hibernate-mapping>

But my trips are all naturally ordered by their scheduledDate. I would like to replace the Set with a List. Changing the collection to:

        <list name="trips" cascade="all" order-by="scheduledDate">
            <key column="trainId"/>
            <one-to-many class="Trip"/>
        </list>

does not work, since it now requires an <index/>. I don't want to add an index to my table, because the ordering is given by the date.

Any way this can be done? Or should I just get the Set from Hibernate, and then sort it myself in code? Seems unnecessary when we already have it ordered by the DB.

Magnar
  • 28,550
  • 8
  • 60
  • 65

2 Answers2

32

Actually, this can be done with <bag>, <set> or <map> mappings. <bag> uses java.util.List semantics but does not maintain element indexes. By specifying it's order-by attribute, its elements will be ordered as part of SELECT:

<bag name="trips" cascade="all" order-by="scheduledDate">
    <key column="trainId"/>
    <one-to-many class="Trip"/>
</bag>

Note that order-by attribute needs to specify column name(s), not property name. The above can be mapped to java.util.List, you can do the same with java.util.Set by using <set> mapping. No need for comparators :-)

Details are here

Andy
  • 8,749
  • 5
  • 34
  • 59
ChssPly76
  • 99,456
  • 24
  • 206
  • 195
  • 2
    The posted link now gives a 404. Should be http://docs.jboss.org/hibernate/orm/3.6/reference/en-US/html/collections.html#collections-sorted – Saïd Feb 23 '12 at 17:28
0

I realized that using a List is not the correct way to store a collection of naturally ordered items.

The solution is to use a SortedSet (like a TreeSet) with a Comparator.

Magnar
  • 28,550
  • 8
  • 60
  • 65