2010-01-08 6 views
6

Me estoy golpeando la cabeza contra lo que creo que sería un problema muy simple de resolver en Grails:Grails: clasificación de salida de lista sin tener que tener un SortedSet o modelo comparable?

Digamos que tengo un modelo de carrito de compras; entonces un carrito de clases que tiene muchos artículos, y cada artículo pertenece al carro. En general, no me importa el orden de los artículos en el carro, no me importa en qué orden están almacenados, calculados, etc. SIN EMBARGO, quiero VISUALIZARlos en el mismo orden. Me parece que esta lógica debería poder existir TOTALMENTE en la capa de vista, pero las únicas soluciones que he podido encontrar me dicen que declare elementos como SortedSet en la capa del modelo. Esto también afecta mi capa de controlador, ya que las simples operaciones de lista como .collect {} ahora requieren saltos sintácticos adicionales para mantener las conversiones de tipo correctas y preservar mi clasificación.

Para mí, esto es una locura, ¡así que me estoy perdiendo algo simple! ¿Hay alguna manera, por ejemplo, de hacer algo como <g:each in="${cart.items.sort{it.name}}"> o algo similar, de modo que pueda imponer una orden de visualización consistente SOLAMENTE en la capa de salida/vista? EDITAR - Vea la respuesta de Matt a continuación; una versión de esto realmente funciona.

¡Gracias por cualquier consejo o sugerencia!

Respuesta

4

This 3rd party tag parece que hará lo que necesita. Si no, siempre puedes hacer tu propia etiqueta. La clase Tag podía hacer la clasificación como esta

class SortTagLib { 

    static namespace = 'sort' 

    def sort = { attrs -> 

     // A closure that does the sorting can be passed as an attribute to the tag. 
     // If it is not provided the default sort order is used instead 
     def sorter = attrs.sorter ?: {item1, item2 -> item1 <=> item2} 
     sorter = sorter as Comparator   

     // The collection to be sorted should be passed into the tag as a parameter 
     Collections.sort(attrs.items, sorter) 
    } 
} 

Esta etiqueta podría ser utilizado para ordenar una colección de objetos por su propiedad de nombre así:

<sort:sort items="someCollection" sorter="${someComparatorClosure}"/> 

la recogida como el mencionado por someCollection habrá ordenados en el lugar cuando se ejecuta la etiqueta.

+0

Eso es genial. Eventualmente tropecé con una solución similar en la misma línea usando un ProxyGenerator y la interfaz Comparator, pero el tuyo es mucho más limpio, y definitivamente el tipo de solución que estaba buscando. ¡Gracias! – bprotas

22

También puede utilizar los métodos de clasificación disponibles para Colecciones/Mapas como se define aquí: http://groovy.codehaus.org/api/org/codehaus/groovy/runtime/DefaultGroovyMethods.html

personalmente he encontrado que es bastante fácil de hacer esto en conjunción con una etiqueta <g:each/> en mi GSP:

<!-- Books sorted by title --> 
<g:each in="${ books.sort{a,b-> a.title.compareTo(b.title)} }"> 
    <p>Title: ${it.title}</p> 
    <p>Author: ${it.author}</p> 
</g:each> 

Para conocer más formas de manipular colecciones y mapas, recomiendo this page y this page respectivamente.

+0

Gracias Matt ... Tu solución también funciona, y también está muy limpia, aunque podría Jurar que probé esto antes y falló ... mi cerebro debe haber estado embarrado. ¡Gracias! – bprotas

+0

¡Hermoso! ¡Me gusta esto! +1 – Eldelshell

+0

Gracias Matt funciona muy bien – Vahid

Cuestiones relacionadas