Using will_paginate and .limit(x) together.
Hi
It appears that will_paginate and .limit(x) will not work together. So this didn't work:
(I am trying to get 150 most recent records and paginate them)
@articles = Article.where.not(site_id: 'HIDE')
.limit(150)
.order('articles.created_at DESC')
.paginate(:page => params[:page], :per_page => 30)
But this does work:
(using the total_entries method of will_paginate)
@articles = Article.where.not(site_id: 'HIDE')
.order('articles.created_at DESC')
.paginate(:page => params[:page], :per_page => 30,total_entries: 150)
BUT @articles still pulls all 4500 records which isnt very efficient and also @articles.count returns 4500 rather than 150.
Is there away I can just get the 150 records from the DB and paginate them?
Thanks to craftycanuck in the Slack channel for helping me get this far,
Simon
Hey Simon,
One super important thing here is that pagination uses both limit
and order
to make pages. When you add limit
in on top of that, you're going to likely break pagination because of that.
Are you trying to limit the number of pages displayed?
Thanks Chris
I want the 150 most recent Articles paginated in 5 pages of 30.
I have managed a workaround but would love to understand how I could accomplish the original problem.
You're definitely doing something that is outside the scope of most pagination gems. What I would probably do is customize the view template to only show the last 5 pages links. This would visually make it so you could only see the first X items and then you can have your controller also verify the page # is between 1 and 5 so the users can't go outside those boundaries.
What does your solution look like right now?
Hi Chris
Thanks for your continued input.
My problem was that I wanted to display "Here are the last 150 articles" but the view has other options when it might show less or more articles so 150 was populated by @articles.count. The problem is when you use @articles.count on a paginated active record set it returns the whole table count rather than the number you limited the pagination set to.
My work around was to create a method called getarticlecount.
Which does this:
def getarticlecount(view)
if view == "150"
return "150"
else
return @articles.count
end
end
Made accessible to the view by adding this in the controller:
helper_method :getarticlecount
Rendered in the view by this:
<%= pluralize(getarticlecount(params[:view]), "result") %>
Not sure if the breaks any rails or ruby best practises but it does the job! Open to refactoring.
Simon
That works. The other thing you can do is look at @articles.total_entries
I believe with will_paginate which will give you the count of all the results, not just the current page. It's either that or total_count
on that or Kaminari.
Your solution is simple enough though so I would stick with that. 👍