Par défaut, le mélange de ces 3 ingrédients ne fonctionne pas sous Rails.
La solution est là :
I dove into RoR Pagination yesterday (ActionController::Pagination), and while it’s great for paginating all data in a model, it really sucks for paginating data from an activerecord association (and by really sucks I mean doesn’t support).
Here’s the problem. Say I have a user who has a collection of photos:
class User < ActiveRecord::Base has_many :photos, :conditions => 'photos.is_deleted = false', :order => 'photos.created_at DESC' end
I want to have the ability to feed the user’s photos to the paginator. Unfortunately, the
paginate
function simply takes a collection id, and will not accept a set of data (an association, in this case). So, if I want to paginate photos on a user, I have to do this:@photo_pages, @photos = paginate :photos, :conditions => ["photos.user_id=? AND is_deleted = false", @user.id], :order => "photos.created_at DESC"
What a mess. Now i’ve lost the benefits of my association, since I have to define the association as part of the pagination rules. Very suprised Rails handles things this way, as it seems to violate the basic DRY principles. Anyways, I only had to write code like this a few times to realize how much of a pain in the ass it is, and I created a “paginate_association” method to help me out.
def paginate_association(object, assoc_name, find_options = {}, per_page = 10) page = (params[:page] || 1).to_i item_count = object.send(assoc_name.to_s + '_count') offset = (page-1)*per_page @items = object.send(assoc_name).find(:all, {:offset => offset, :limit => per_page}.merge(find_options)) @item_pages = Paginator.new self, item_count, per_page, page return @item_pages, @items end
I added this to my ApplicationController (application.rb), and now I can paginate assocations til the cows come home.
@photo_pages, @photos = paginate_association @user, :photos, :order => 'created_at'
This helper uses the Rails Pagination stuff, so you can easily use
paginate
orpaginate_association
with the same view. Great!You can also pass additional “find” arguments, such as
:order, :include, :join
, etc…Hopefully this is as useful for you as it’s been for me!