2011-03-28 10 views
9

He conseguido lo que quiero, pero parece que no puedo conseguirlo de una manera que los diseñadores de rieles están buscando. Básicamente, tengo (por favor, dejar de lado cuestiones pluralización/etc):Has_Many: Through o: finder_sql

humana Relaciones (Padre, Hijo)

Estoy tratando de obtener todos los descendientes de un solo padre, y el padre única para muchos descendientes (se supone solo un progenitor por cría).

puedo hacer esto de la siguiente manera en el modelo:

has_one  :parent, :through => :relationships, :foreign_key => :human_id, :source => :source_human 
has_many :offsprings, :finder_sql => 
      'SELECT DISTINCT offsprings.* ' + 
      'FROM humans offsprings INNER JOIN relationships r on ' + 
      'r.human_id = offsprings.id where r.source_human_id = #{id}' 

que tenía que hacer esto, porque la manera más agradable para hacerlo:

has_many :offsprings, :through => :relationships, :foreign_key => :source_human_id, :source => :human 

no es posible porque las claves externas son ignorados en has_many (de acuerdo con los documentos aquí: http://api.rubyonrails.org/classes/ActiveRecord/Associations/ClassMethods.html#method-i-has_many)

Sin embargo, ahora que estoy recibiendo este error: 0

DEPRECATION WARNING: String-based interpolation of association conditions is deprecated. Please use a proc instead. So, for example, has_many :older_friends, :conditions => 'age > #{age}' should be changed to has_many :older_friends, :conditions => proc { "age > #{age}" }. (called from irb_binding at (irb):1)

Sin embargo, no importa cómo hackeo en: condiciones aquí, no parece que: finder_sql quiera participar. ¿Alguna idea?

Respuesta

35

¿Y si lo hace

has_many :offsprings, :finder_sql => 
      proc { "SELECT DISTINCT offsprings.* " + 
      "FROM humans offsprings INNER JOIN relationships r on " + 
      "r.human_id = offsprings.id where r.source_human_id = #{id}" } 
+2

Damas y gérmenes, un ganador. Los documentos están incorrectos aquí, no haces a: condiciones en: finder_sql, solo lo compilas. – aronchick

4

En realidad, me gustaría escribir de esta manera:

has_many :offsprings, :finder_sql => proc {OFFSPRING_SQL % {id: id}} 

OFFSPRING_SQL = "SELECT DISTINCT offsprings.* 
        FROM humans offsprings 
        INNER JOIN relationships r 
         ON r.human_id = offsprings_id 
         WHERE r.source_human_id = %{id}" 

creo que tiene la asociación más fácil de entender, y hacer el SQL desnuda más fácil editar. También aprovecha la interpolación de parámetros basada en cadenas.

Cuestiones relacionadas