2011-11-23 16 views
6

de Ruby 1.9.2/carriles 3.1/desplegar en heroku -> PosgreSQLvolver cada fila n de la base de datos utilizando ActiveRecord en los carriles

Hola, Una vez que el número de líneas relativas a un objeto pasa a través de una cierta cantidad, yo desear retirar cada una de las enésimas filas. Es simplemente porque las filas se usan (en parte) para mostrar los datos para graficar, por lo que una vez que la cantidad de filas devueltas es superior a 20, es bueno devolver cada segundo, y así sucesivamente.

Esta pregunta parecía apuntar en la dirección correcta: ActiveRecord Find - Skipping Records or Getting Every Nth Record

Hacer un mod en el corredor número tenga sentido, pero utilizando básicamente:

@widgetstats = self.widgetstats.find(:all,:conditions => 'MOD(ROW_NUMBER(),3) = 0 ') 

no funciona, se devuelve un error:

PGError: ERROR: window function call requires an OVER clause 

Y cualquier intento de resolver eso con, por ejemplo, basando mi SOBRE sintaxis de la cláusula sobre las cosas que veo en la respuesta a esta cuestión:

Row numbering in PostgreSQL

termina en errores de sintaxis y no puedo conseguir un buen resultado.

¿Me está faltando una forma más obvia de devolver de manera eficiente cada enésima tarea o si estoy en el camino correcto? ¿Alguna sugerencia en el camino a seguir? Obviamente, devolver todos los datos y arreglarlos en rieles es posible, pero terriblemente ineficiente.

Gracias!

Respuesta

7

Creo que busca una consulta como esta:

SELECT * FROM (SELECT widgetstats.*, row_number() OVER() AS rownum FROM widgetstats ORDER BY id) stats WHERE mod(rownum,3) = 0 

Este es difícil de compilar con ActiveRecord, por lo que es posible que deba hacer algo como:

@widgetstats = self.widgetstats.find_by_sql(
    %{ 
    SELECT * FROM 
    (
     SELECT widgetstats.*, row_number() OVER() AS rownum FROM widgetstats ORDER BY id 
    ) AS stats 
    WHERE mod(rownum,3) = 0 
    } 
) 

Obviamente, querrá cambiar el orden utilizado y agregar cualquier cláusula WHERE u otras modificaciones que se adapten a sus necesidades.

2

Si tuviera que resolver esto, yo solo escribiría el SQL, como el SQL al que se vinculó. Usted puede hacer esto con

my_model.connection.execute('...') 

o simplemente obtener los números de identificación y encontrar por id

ids = (1..30).step(2) 
my_model.where(id => ids) 
Cuestiones relacionadas