def find_each(start: nil, finish: nil, batch_size: 1000, error_on_ignore: nil)
      if block_given?
        find_in_batches(start: start, finish: finish, batch_size: batch_size, error_on_ignore: error_on_ignore) do |records|
          records.each { |record| yield record }
        end
      else
        enum_for(:find_each, start: start, finish: finish, batch_size: batch_size, error_on_ignore: error_on_ignore) do
          relation = self
          apply_limits(relation, start, finish).size
        end
      end
    end
def find_each(start: nil, finish: nil, batch_size: 1000, error_on_ignore: nil)
      if block_given?
        find_in_batches(start: start, finish: finish, batch_size: batch_size, error_on_ignore: error_on_ignore) do |records|
          records.each { |record| yield record }
        end
      else
        enum_for(:find_each, start: start, finish: finish, batch_size: batch_size, error_on_ignore: error_on_ignore) do
          relation = self
          apply_limits(relation, start, finish).size
        end
      end
    end
Looping through a collection of records from the database
 (using the Scoping::Named::ClassMethods.all method, for example)
 is very inefficient since it will try to instantiate all the objects at once.

 In that case, batch processing methods allow you to work
 with the records in batches, thereby greatly reducing memory consumption.

 The #find_each method uses #find_in_batches with a batch size of 1000 (or as
 specified by the +:batch_size+ option).

   Person.find_each do |person|
     person.do_awesome_stuff
   end

   Person.where("age > 21").find_each do |person|
     person.party_all_night!
   end

 If you do not provide a block to #find_each, it will return an Enumerator
 for chaining with other methods:

   Person.find_each.with_index do |person, index|
     person.award_trophy(index + 1)
   end

 ==== Options
 * <tt>:batch_size</tt> - Specifies the size of the batch. Defaults to 1000.
 * <tt>:start</tt> - Specifies the primary key value to start from, inclusive of the value.
 * <tt>:finish</tt> - Specifies the primary key value to end at, inclusive of the value.
 * <tt>:error_on_ignore</tt> - Overrides the application config to specify if an error should be raised when
   an order is present in the relation.

 Limits are honored, and if present there is no requirement for the batch
 size: it can be less than, equal to, or greater than the limit.

 The options +start+ and +finish+ are especially useful if you want
 multiple workers dealing with the same processing queue. You can make
 worker 1 handle all the records between id 1 and 9999 and worker 2
 handle from 10000 and beyond by setting the +:start+ and +:finish+
 option on each worker.

   # In worker 1, let's process until 9999 records.
   Person.find_each(finish: 9_999) do |person|
     person.party_all_night!
   end

   # In worker 2, let's process from record 10_000 and onwards.
   Person.find_each(start: 10_000) do |person|
     person.party_all_night!
   end

 NOTE: It's not possible to set the order. That is automatically set to
 ascending on the primary key ("id ASC") to make the batch ordering
 work. This also means that this method only works when the primary key is
 orderable (e.g. an integer or string).

 NOTE: By its nature, batch processing is subject to race conditions if
 other processes are modifying the database.