2008-10-16 4 views
2

Je tente de rassembler quelques écrans de rapport de base. J'ai des requêtes SQL assez compliquées que je nourris dans la méthode find_by_sql d'ActiveRecord. Le problème que j'ai ici est que je perds l'ordre des colonnes comme indiqué dans la requête originale. Je suppose que c'est parce que la classe Hash ne conserve pas l'ordre d'entrée de ses clés.Ordre des résultats sur les rails à partir des rails ActiveRecord find_by_sql call

Y at-il un moyen de contourner ce problème? Dois-je utiliser une méthode différente, puis find_by_sql pour mes requêtes?

+0

Pourriez-vous expliquer pourquoi l'ordre des colonnes est significatif? Je ne suis pas drôle, je suis vraiment curieux. –

+0

L'ordre des colonnes est le même que celui que j'ai voulu afficher dans le rapport. –

Répondre

1

Vous avez raison en ce que le Ruby Hash ne conserve pas l'ordre. Cela fait partie du problème, vraiment - vous y accédez en utilisant la clé.

Je suppose que votre requête est écrite pour fournir les colonnes dans l'ordre dans lequel vous voulez les sortir et que vous espériez sortir les valeurs via une boucle? On dirait une idée assez décente, mais je ne peux pas penser à un moyen d'y parvenir sans au moins un peu de travail supplémentaire. Ce que je recommanderais est d'accéder explicitement aux colonnes par clé dans votre modèle, puisque vous allez probablement finir par appliquer des styles, en utilisant des fonctions auxiliaires comme number_with_delimiter, ce genre de chose. Pour obtenir quelque chose comme le raccourci mentionné ci-dessus, je suppose que vous pouvez créer un tableau de symboles dans l'ordre requis et extraire les valeurs du hachage dans une boucle. Quelque chose comme ça? (S'il vous plaît excusez-erb potentiellement douteux: Je suis un utilisateur haml!)

<% for row in @report.rows %> 
    <tr> 
    <% for col in [:a, :b, :c] %> 
     <td><%= row[col] %></td> 
    <% end %> 
    </tr> 
<% end %> 
+0

C'est ce que j'ai fini par faire. Nous avons un certain nombre de requêtes SQL pour les rapports de base. Ce que je voulais faire était de configurer les choses de manière à ce que je n'aie pas besoin de créer des contrôleurs/vues séparés pour chaque 'rapport' SQL (la page est la même à l'exception des données qui la peuplent). –

+0

le hachage conserve l'ordre dans ruby ​​1.9 je pense –

0

Comment créez-vous ces "écrans de rapport"? Sont-ils des modèles erb? Appelez-vous simplement .each sur des colonnes pour les imprimer?

Si c'est le cas, vous pouvez remplacer la méthode columns() dans vos modèles pour retourner un tableau ordonné.

+0

Utilisation du contrôleur/vue standard. Pour l'instant, j'ai un tableau séparé de noms de colonnes qui spécifient l'ordre dans lequel les colonnes doivent apparaître. Mais ce n'est pas DRY puisque le SQL a déjà ces noms de colonnes dans le bon ordre. Il devrait y avoir un meilleur moyen. –

2

J'aime utiliser Ruport pour les rapports. Il a une bonne intégration ActiveRecord et vous permet de contrôler l'ordre des colonnes et à peu près tout le reste. Et c'est assez simple à utiliser que je ne considère pas exagéré même pour des rapports "basiques".

1

dans des rails 3.2 et plus vous pouvez utiliser attribute_names pour chaque enregistrement de find_by_sql résultats. Ceci est documenté dans find_by_sql:

Exécute une commande requête SQL sur votre base de données et renvoie tous les résultats. Les résultats seront renvoyés sous forme de tableau avec les colonnes demandées encapsulées en tant qu'attributs du modèle que vous appelez cette méthode à partir de. Si vous appelez Product.find_by_sql, les résultats seront renvoyés dans un objet Product avec les attributs que vous avez spécifiés dans la requête SQL .

Si vous appelez une requête SQL complexe qui couvre plusieurs tables les colonnes spécifiées par le SELECT seront les attributs du modèle, si elles sont ou non colonnes du tableau correspondant

Pour modèles, vous pouvez utilisez column_names. Pour plus d'informations sur les variations voir autre réponse SA: How do you discover model attributes in Rails

Questions connexes