Reputation: 445
I'm using will paginate bootstrap like this:
My model:
class Customer < ActiveRecord::Base
attr_accessible :city, :country, :name, :street, :zip
//... more code
has_many :contacts, :dependent => :destroy, :autosave => true
end
class Contact < ActiveRecord::Base
attr_accessible :name, :notice, :phone
//... more code
belongs_to :customer
end
Gemfile:
gem "will_paginate-bootstrap"
Partial which is able to generate paginated output in contacts/_pageable_contacts.html.erb:
<%
contacts = contacts.to_a.paginate( :page => params[:page] || 1, :per_page => 5 )
%>
<%= render(:partial => 'contacts/contacts', :locals => {:contacts => contacts})%>
<%= will_paginate contacts, renderer: BootstrapPagination::Rails, remote: true %>
Invocation inside contacts/create.js.erb:
<%
all = @contact.customer.contacts
%>
<%= render :partial => "contacts/pageable_contacts", :locals => { :contacts => all } %>
The links generated by will_paginate are as follows as long as this partial has been rendered in context of the Contacts controller (e.g. views/contacts/create.js.erb):
customers/3/contacts?page=1
customers/3/contacts?page=2
Now, I want to render this partial inside customer/show.html.erb like this:
<%= render :partial => 'contacts/pageable_contacts', :object => @customer.contacts, :as => :contacts %>
But the links returned by will_paginate are customer specific rather than contact specific. Apparently, will_paginate's accessing self (which is CustomerController) to build the links.
customers/3?page=1
customers/3?page=2
How can I tell the partial or will_paginate howto deal with it? Did I misunderstand the concept of MVC, routes or anything else? Am I using the associations between the models in a wrong way?
Any help appreciated! Thanks you SO. golbie
Upvotes: 0
Views: 719
Reputation: 445
I debugged will_paginate and detected that self is passed as "template":
def will_paginate(collection, options = {})
# early exit if there is nothing to render
return nil unless collection.total_pages > 1
options = WillPaginate::ViewHelpers.pagination_options.merge(options)
#............. more code
# render HTML for pagination
renderer.prepare collection, options, self #####<====== self is Customers Controller
renderer.to_html
end
My found a workaround: instead of using "render" mechanism I'm using an ajax request to call the index method of Contacts controller like this:
I. in customers/show.html.erb:
<div id="contacts">
</div>
<%= javascript_tag "ProtoSupport.fetchCustomersContacts('#{customer_contacts_path(@customer)}');" %>
<%= javascript_tag 'ProtoSupport.addAsyncPagination();' %>
II. in assets/javascript/application.js these two new methods in ProtoSupport:
fetchCustomersContacts : function(path) {
$.getScript(path);
},
addAsyncPagination : function() {
$(function() {
$(".pagination a").on("click", function() {
if( $(this).attr('href') == '#' ) return false;
$(".pagination").html("Page is loading...");
$.getScript(this.href);
return false;
});
});
}
The links are correct now (e.g. 'http://localhost:3000/customers/3/contacts?page=16'
) and when I click on a page the new data are loaded asynchronously.
golbie
Upvotes: 1