2011-04-08 15 views
7

Entonces, tengo una aplicación con dos modelos. Foo tiene una barra, Bar pertenece a Foo.Rieles: busque el registro "has_one" que no tiene uno

Ahora, para crear un Foo debes tener que crear una barra para pertenecer a él, pero parece que se me escapó por las grietas porque en mi aplicación de producción ahora parece que tengo un Foo que de alguna manera se creó sin una Bar, y causa un error de 500.

Ahora, aquí está el problema:

puedo buscar: Bar.where(:foo=>nil) bien. Pero las barras huérfanas no son un problema, y ​​esto no me dice lo que necesito.

Necesito encontrar el Foo donde el Bar es nulo. Pero la base de datos almacena la relación en la tabla Bars, es decir, BarsTable tiene foo_id en ella, no hay nada en el FoosTable que me diga que le falta una barra.

Cuando uso Foo.find(#).bar obtendría nada por el único registro falso, pero tengo muchos registros.

Entonces, ¿alguien puede decirme cómo crear una consulta que devolvería el Foo que le falta es Bar?

Gracias!

Respuesta

7

no estoy seguro de lo que sería el código Ruby, pero creo que el SQL debe ser algo como:

SELECT * FROM foo donde ID NO EN (SELECCIONAR foo_id de Bar)

+4

Esto funcionó! - en Rails solo es 'Foo.where (" id NOT IN (SELECCIONE foo_id FROM Bar) ")' ¡Gracias! – Andrew

+0

En mi humilde opinión, la forma correcta de hacerlo es: 'Foo.joins (: bar)', que da como resultado una consulta SQL de 'SELECT \' foos \ '. * FROM \' foos \ 'INNER JOIN \' bars \ 'ON \' bars \ '. \' Foo_id \ '= \' foos \ '. \' Id \ ''. Puede optimizar esto aún más: 'Foo.includes (: bar) .joins (: bar)' puede ahorrarle algunas solicitudes posteriores al DB. –

2

Otra forma (sin usar SQL) sería hacer algo como:

Foo.all.select {| f | ! f.bar}

Esto devolvería una matriz de objetos Foo que no tienen un objeto Bar relacionado.

En este método, no está confiando en información de tabla específica. Si la columna foreign_key cambiara en la futura asociación Foo -> Bar, este método continuaría funcionando.

+0

¡Buen consejo, gracias! – Andrew

+0

Esto será mucho menos eficaz, ya que hará que se obtengan e instanciar objetos AR. – kranzky

Cuestiones relacionadas