pagination image

Anyone who’s used Ruby on Rails has likely needed to implement pagination, and for that you probably used WillPaginate. Although it’s been possible to use WillPaginate with Sequel for some time now, we’ve only just seen the first Roda GEM released. After some experiementation, it turns out adding pagination to our Roda app is actually pretty easy.

Requirements

We’ll be building on top of my Roda Blog tutorial so if you don’t already have an application to try this with then you should take a look at that first.

Here’s the versions and GEMs I’ll be using for this tutorial;

  • Roda 2.3
  • PostgreSQL 9.3
  • Sequel 4.23
  • roda-will_paginate 0.0.4

Enabling the plugin

Our first task is too add roda-will_paginate to our Gemfile – don’t forget to bundle install once you’ve done that.

# ./Gemfile
gem "roda-will_paginate", ">= 0.0.4"

The plugin only handles generating the HTML links on your view pages, so we need to make sure our blogs Post collection includes the required WillPaginate methods. As the plugin README states, “That would mean adding current_page, per_page, offset, total_entries, total_pages as methods of your collection and including WillPaginate::CollectionMethods in your collections as well.”

That’s quite a bit of work, but lucky for us we’re using Sequel, and WillPaginate supports that out-of-the-box.

# ./myapp.rb
require "will_paginate/sequel"
require "roda/will_paginate/bootstrap_pagination_renderer"

class Myapp < Roda
  # ...
  DB.extension(:pagination)
  plugin :will_paginate, renderer: :bootstrap
  # ...

  route do |r|
    r.root do
      page =  Integer(r["page"] || 1)
      @posts = Post.reverse_order(:created_at).paginate(page, 10)
      view("homepage")
    end
  end
end

It may not seem like there’s much going on here, but I think it’s worth giving each piece a short explanation;

  • require "will_paginate/sequel" ensures all the needed pagination methods are automatically added to our @posts collection.
  • require "roda/will_paginate/bootstrap_pagination_renderer" my blog tutorial uses Twitter Boostrap, and roda-will_paginate is able to render the HTML tags/attributes that Bootstrap needs.
  • DB.extension(:pagination) Sequel has built in support for pagination, and is enabled via this extension.
  • plugin :will_paginate, renderer: :bootstrap when enabling the pagination pluging we also tell it to use the Bootstrap renderer.

The final additions to our App class is to make sure we are paginating the collection. paginate() is a Sequel method which takes two arguments. The first is the current page number, and the second (the value 10) is the number of records Sequel should return per page.

If we were to add just the page parameter to paginate, our app will blow up when no page param is provided, but by using r["page"] || 1 we make sure we at least have a value.

Sequel expects an integer value so we cast it using Integer(). This is not a particularly robust solution, but is adequate for demonstration purposes.

Finally, we add the view helper. Just like with WillPaginate in Rails, this is super simple.

<!-- ./views/homepage.erb -->

<% @posts.each do |post| %>
  <!-- display the post -->
<% end %>

<%= will_paginate @posts %>

While this may not be quite as simple as it is in Ruby on Rails, there really is only a little extra work involved.