takoblo

コード読んだめも

kaminariのactiverecord拡張部分を読む

Query Basics - kaminari/kaminiari にあるようなActiveRecordのモデルに生えるscope等がどうやって定義されているか調べる

REF

よんでみる

kaminari/kaminari-activerecord/lib/kaminari/activerecord/active_record_model_extension.rb

# frozen_string_literal: true
require 'kaminari/activerecord/active_record_relation_methods'

module Kaminari
  module ActiveRecordModelExtension
    extend ActiveSupport::Concern

    included do
      include Kaminari::ConfigurationMethods

      # Fetch the values at the specified page number
      #   Model.page(5)
      eval <<-RUBY, nil, __FILE__, __LINE__ + 1
        def self.#{Kaminari.config.page_method_name}(num = nil)
          per_page = max_per_page && (default_per_page > max_per_page) ? max_per_page : default_per_page
          limit(per_page).offset(per_page * ((num = num.to_i - 1) < 0 ? 0 : num)).extending do
            include Kaminari::ActiveRecordRelationMethods
            include Kaminari::PageScopeMethods
          end
        end
      RUBY
    end
  end
end

いかにも page メソッドを生成してそう.

included を辿っていくと active_record_extension -> active_record へたどりつく

kaminari-activerecord/lib/kaminari/activerecord.rb

ActiveSupport.on_load :active_record do
  require 'kaminari/activerecord/active_record_extension'
  ::ActiveRecord::Base.send :include, Kaminari::ActiveRecordExtension
end

ActiveSupport が load されたときに, ActiveRecord::Base を継承したクラスに対して上のevalが実行される.(kaminari-activerecord/lib/kaminari/activerecord/active_record_extension.rb で親クラスをみてる) kaminari/kaminari-core/lib/kaminari/config.rbKaminari.config.page_method_name には :page が入っているので,予想通りここで生成されてるのは page method .

(なんでわざわざconfigに入ってるんだろうと思ったけど rails g kaminari:config したときにメソッド名を指定できるようにしてるからだった.)

その他の各メソッドは,page メソッドの中で Kaminari::ActiveRecordRelationMethodsKaminari::PageScopeMethods を include して生やしてた.