Module: PaginationHelper
- Included in:
- ActionController::Base
- Defined in:
- app/helpers/pagination_helper.rb
Overview
Pagination Helper
Action Pack pagination for Active Record collections
Sam Stephenson <sstephenson at gmail dot com>
Pagination Helper aids in the process of paging large collections of Active Record objects. It offers macro-style automatic fetching of your model for multiple views, or explicit fetching for single actions. And if the magic isn’t flexible enough for your needs, you can create your own paginators with a minimal amount of code.
Unlike most helpers, Pagination Helper is available to all of Action Pack: it helps you query your models with Action Controller and render links in Action View.
Controller examples
Pagination Helper can handle as much or as little as you wish. In the controller, have it automatically query your model for pagination; or, if you prefer, create Paginator objects yourself.
Automatic pagination for every action in a controller
class PersonController < ApplicationController
helper :pagination
model :person
paginate :people, :order_by => 'last_name, first_name',
:per_page => 20
# ...
end
Each action in this controller now has access to a @people
instance variable, which is an ordered collection of model objects for the current page (at most 20, sorted by last name and first name), and a @person_pages
Paginator instance. The current page is determined by the @params['page']
variable.
Pagination for a single action
def list
@person_pages, @people =
paginate :people, :order_by => 'last_name, first_name'
end
Like the previous example, but explicitly creates @person_pages
and @people
for a single action, and uses the default of 10 items per page.
Custom/“classic” pagination
def list
@person_pages = Paginator.new self, Person.count, 10, @params['page']
@people = Person.find_all nil, 'last_name, first_name',
@person_pages.current.to_sql
end
Explicitly creates the paginator from the previous example and uses Paginator#to_sql to retrieve @people
from the model.
View examples
Paginator Helper includes various methods to help you display pagination links in your views. (For information on displaying the paginated collections you retrieve in the controller, see the documentation for ActionView::Partials#render_collection_of_partials.)
Using Paginator#basic_html
Use the basic_html
method to get a simple list of pages (always including the first and last page) with a window around the current page. In your view, using one of the controller examples above,
<%= @person_pages.basic_html(self) %>
will render a list of links. For a list of parameters, see the documentation for Page#basic_html.
Using a paginator partial
If you need more advanced control over pagination links and need to paginate multiple actions and controllers, consider using a shared paginator partial. For instance, _why suggests this partial, which you might place in app/views/partial/_paginator.rhtml
:
<div class="counter">
Displaying <%= paginator.current.first_item %>
- <%= paginator.current.last_item %>
of <%= paginator.item_count %>
<%= link_to(h('< Previous'), paginator.current.previous.to_link) +
" | " if paginator.current.previous %>
<%= paginator.basic_html(self, 4) %>
<%= " | " + link_to(h('Next >'), paginator.current.next.to_link) if
paginator.current.next %>
</div>
Then in your views, simply call
<%= render_partial "partial/paginator", @person_pages %>
wherever you want your pagination links to appear.
Thanks
Thanks to the following people for their contributions to Pagination Helper:
-
Marcel Molina Jr (noradio), who provided the idea for and original implementation of Paginator::Window, as well as endless mental support.
-
evl, who pointed out that Page#link_to should take and merge in a hash of additional parameters.
-
why the lucky stiff, who wrote a lovely article on the original Pagination Helper alongside the first implementation of Paginator#base_html, created Page#first_item and Page#last_item, and who provided inspiration for revising Pagination Helper to make it more “Rails-ish.”
-
xal, who saw the limitations of having only the macro-style paginate method and suggested the single-action version, and who also suggested the automatic inclusion into ActionController::Base.
-
jbd for feedback and debugging help.
-
##rubyonrails on Freenode and the Rails mailing list.
Defined Under Namespace
Modules: ClassMethods Classes: Paginator
Constant Summary collapse
- OPTIONS =
A hash holding options for controllers using macro-style pagination
Hash.new
- DEFAULT_OPTIONS =
The default options for pagination
{ :class_name => nil, :per_page => 10, :parameter => 'page', :conditions => nil, :order_by => nil }
Class Method Summary collapse
-
.included(base) ⇒ Object
:nodoc:.
-
.validate_options!(collection_id, options, in_action) ⇒ Object
:nodoc:.
Instance Method Summary collapse
-
#paginate(collection_id, options = {}) ⇒ Object
Returns a paginator and a collection of Active Record model instances for the paginator’s current page.
Class Method Details
.included(base) ⇒ Object
:nodoc:
140 141 142 143 |
# File 'app/helpers/pagination_helper.rb', line 140 def self.included(base) #:nodoc: super base.extend(ClassMethods) end |
.validate_options!(collection_id, options, in_action) ⇒ Object
:nodoc:
145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 |
# File 'app/helpers/pagination_helper.rb', line 145 def self.(collection_id, , in_action) #:nodoc: .merge!(DEFAULT_OPTIONS) {|key, old, new| old} = [:class_name, :per_page, :parameter, :conditions, :order_by] << :actions unless in_action unknown_option_keys = .keys - raise ActionController::ActionControllerError, "Unknown options: #{unknown_option_keys.join(', ')}" unless unknown_option_keys.empty? [:singular_name] = Inflector.singularize(collection_id.to_s) [:class_name] ||= Inflector.camelize([:singular_name]) end |
Instance Method Details
#paginate(collection_id, options = {}) ⇒ Object
Returns a paginator and a collection of Active Record model instances for the paginator’s current page. This is designed to be used in a single action; to automatically paginate multiple actions, consider ClassMethods#paginate.
options
are:
:class_name
-
the class name to use, if it can’t be inferred by singularizing the collection name.
:per_page
-
the maximum number of items to include in a single page. Defaults to 10.
:parameter
-
the CGI parameter from which the current page is determined. Defaults to ‘page’; i.e., the current page is specified by
@params['page']
. :conditions
-
optional conditions passed to Model.find_all.
:order_by
-
optional order parameter passed to Model.find_all and Model.count.
177 178 179 180 |
# File 'app/helpers/pagination_helper.rb', line 177 def paginate(collection_id, ={}) PaginationHelper.(collection_id, , true) paginator_and_collection_for(collection_id, ) end |