Para usar limit y un order especial junto con find_each, debes combinar where, reorder y limit de la siguiente manera:

Model.where('created_at > ?', 2.days.ago).reorder('created_at DESC').limit(1000).find_each do |item|
  # Aquí ocurre la magia
  # Recuerda que Roma no se construyó en un día, ¡pero esta entrada la obtuvimos al instante!
end

Nota: Por defecto, find_each ordena las entradas por la clave primaria. Usa reorder para cambiar este orden dentro del limit. Es importante entender que el orden fuera del limit especificado no está garantizado.

Visualización: Tu secuencia de trabajo dentro del límite

📚📚📚📚📚📚    📚📚📚📚📚📚
 Estante 1 – Límite      Estante 2 – Límite 
[ 1 | 2 | 3 ]  ➡️   [ 4 | 5 | 6 ]

Intentamos elegir los mejores libros que están al final de cada estante (esto es order):

📚📚🌟🌟🌟🌟    📚📚🌟🌟🌟🌟
 Mejores libros al final del estante 
[ 3 | 4 | 5 | 6 ]  ➡️   [ 7 | 8 | 9 | 10 ]

¿Qué queremos decir con esto?

  • find_each = Trabajamos con cada estante por separado
  • limit = Hoy tenemos planeado leer solo dos estantes (¡impresionante!)
  • order = Queremos empezar con los mejores libros

Fundamentos de una consulta eficiente: procesamiento por lotes, ordenación y limitación

Noticias de Rails 6.1

En Rails 6.1, find_each incluye soporte nativo para ordenación inversa, lo que simplifica el uso de reorder para personalizar el orden en versiones modernas. Asegúrate de usar Rails 6.1 o superior para aprovechar esta funcionalidad.

Cuando el orden importa – crea tu propio procesamiento por lotes

Para versiones anteriores de Rails o para una ordenación compleja, crea tu propio método de procesamiento por lotes. Usa pluck para cachear IDs y procesar grupos en el orden original:

ids = Model.where('created_at > ?', 2.days.ago).order('created_at DESC').limit(1000).pluck(:id)
ids.each_slice(100) do |batch|
  Model.where(id: batch).find_each do |item|
    # Procesar item
  end
end

Uso cuidadoso de mixins

Ten cuidado al modificar objetos de ActiveRecord durante operaciones por lotes. Mantén el orden de clasificación para evitar problemas.

Prevención de duplicados

¿Estás ordenando por una columna con valores no únicos? Podrían aparecer registros duplicados. Desarrolla una estrategia para evitar duplicados en tus métodos.

Consulta: procesamiento por lotes con un orden y límite específicos

Utilizar el cacheo de IDs: un enfoque rápido

Al trabajar con grandes volúmenes de datos, usa el cacheo de IDs con pluck para procesar registros en grupos, garantizando consultas rápidas y un uso eficiente de la memoria.

Uso de la función FIELD() para usuarios de MySQL

Si usas MySQL, la función FIELD() permite mantener el orden de clasificación. Combínala con el cacheo de IDs para acelerar las consultas.

Los frutos de un enfoque inteligente

Aplica pluck para obtener atributos específicos de la base de datos, reduciendo la carga de memoria y acelerando el procesamiento.

Manejo cuidadoso de la memoria

Usa yield en tu ciclo para procesar una cantidad definida de registros. Organiza la ordenación correcta y verifica que el ciclo termine al alcanzar el limit.

El arte de las consultas eficientes y la gestión de la memoria

Uso racional de los datos

Aplica order y offset en consultas cíclicas para controlar el orden de los registros procesados, como manejar tu propia cinta transportadora personal.

Reflexiones sobre la memoria: el costo del cacheo

El cacheo de IDs acelera el proceso, pero requiere más memoria. Evalúa las ventajas y desventajas antes de decidir.

¿Trabajas con un gran volumen de datos? ¡Divide y vencerás!

Divide tu consulta en paquetes manejables para mantener el orden y usar la memoria de manera eficiente.

Materiales útiles

Categorizado en:

Ruby,