Im hoping that someone can shed light on what is probably a simple mistake. Im trying to pass a local variable, article, which is in the partial _article.html.erb, to another partial nested within _article.html.erb. When the partial code is in _article.html.erb, it works fine.I've tried many variations (including :locals) but cant seem to pass the local variable.
_article.html.erb
<% if current_user.favorited?(article) %>
<%= render :partial => 'unfavorite', :object => article %>
<% else %>
<%= render :partial => 'favorite', :object => article %>
<% end %>
_favorite.html.erb (both favorite and unfavorite are more or less the same, so I've only posted one)
<%= form_for current_user.favorites.find_by_article_id(article), :html => { :method => :delete, :class => 'unfavorite_form', }, :remote => true do |f| %>
<div><%= f.hidden_field :article_id %></div>
<%= image_submit_tag("vote-favorite-on.png", :alt => "Favorite", :id => "favorites_button", :title => "Remove from favorites") %>
<% end %>
The error message is:
undefined local variable or method `article' for #<#<Class:0x491c2b0>:0x6727a58>
The rails docs for rendering mention the use of object like this:
<%= render :partial => "customer", :object => #new_customer %>
And say that:
Within the customer partial, the customer variable will refer to #new_customer from the parent view.
Which makes it seem like the :object variable is translated into the name of the partial. So in your case, in _favorite, you'd have to use the favorite variable:
<%= form_for current_user.favorites.find_by_article_id(favorite), :html => { :method => :delete, :class => 'unfavorite_form', }, :remote => true do |f| %>
Personally I prefer the locals syntax, because then you can be explicit:
<%= render :partial => 'favorite', :locals => {:article => article} %>
Related
I'm trying a few different ways to define and pass the local variable to the partial, but it keeps saying it's undefined:
in Show file:
<% #startups.each do |startup| %>
<%= render :partial => "profile/startup" %>
<% end %>
in partial:
<%= simple_form_for [#commentable, #comment], :remote => true do |form| %>
<%= form.input :content, label: false, :input_html => { :id => "#{startup.user_id}" } %>
<%= form.submit "Submit" %>
<% end %>
These are the other ways I'm trying to pass the variable, but still getting undefined:
<%= render :partial => "user_comments/uac", object: startup, as: startup %>
<%= render :partial => "user_comments/uac", collection: startup, as: startup %>
<%= render :partial => "user_comments/uac", :locals => {:startup => startup} %>
Get rid of :partial. You haven't needed that in Rails for several versions.
The correct way of passing a local called startup to a partial is this:
render "profile/startup", startup: startup
I have a'Remove' button in a show erb of the trackers_controller.show:
<%= form_for :user_tracker, :url => user_tracker_path,:method => :delete do |f| %>
<%= f.hidden_field :tracker_id, :value => #tracker.id %>
<%= f.submit :save, :value => 'Remove' %>
<% end %>
This works fine and calls user_trackers_controller.destroy
The User models looks like:
has_many :user_trackers
has_many :trackers, :through => :user_trackers
If I put the exact same button in another erb I get this error:
No route matches {:action=>"show", :controller=>"user_trackers"}
I have a few different combinations like :html => {:method => :delete }
If I try it this way
<% current_user.user_trackers.each do |user_tracker| %>
<%= user_tracker.tracker %>
<%= form_for user_tracker, :method => :delete do |f| %>
<%= f.submit :delete, :value => 'Remove' %>
<% end %>
I get the same routing error
Here are the routes:
user_trackers GET /user_trackers(.:format) user_trackers#index
POST /user_trackers(.:format) user_trackers#create
new_user_tracker GET /user_trackers/new(.:format) user_trackers#new
edit_user_tracker GET /user_trackers/:id/edit(.:format) user_trackers#edit
user_tracker GET /user_trackers/:id(.:format) user_trackers#show
PUT /user_trackers/:id(.:format) user_trackers#update
DELETE /user_trackers/:id(.:format) user_trackers#destroy
I do not understand, why will it not pick up that this is a destroy when in an unrelated erb?
Edit:
This is one seems to work but the html generates ids and classes like edit_user_tracker_7 but also the javascript to make it a delete so it seems I still have something wrong:
<%= form_for user_tracker, :url => user_tracker_path(user_tracker), :method => :delete do |f| %>
<%= f.hidden_field :tracker_id, :value => user_tracker.tracker_id %>
<%= f.submit :delete, :value => 'Remove from my portfolio' %>
<% end %>
in first line it should be
:url => user_tracker_path(#user)
Its not a bug, he just have to know who to remove :) so he needs id (in REST).
Also :method should be in :html
:html => { :method => :delete }
or
html: { method: "delete" }
with 1.9+ notation.
full form_for
user_tracker_path(#user), :html => {:method => :delete} do |f| %>
ofc if in your case #user is current_user then you have to swap it :)
Sorry for typos & english i'm not native :)
Cheers!
I'm making a project for which I have a class online_score which has as one of its attributes an array called url of online_score_url objects. What I did up to now is the following.
views/online_score/new:
<div class="urlInput">
<% f.fields_for :url do |b| %>
<%= render "online_score_url_fields", :f => b %>
<% end %>
<%= add_url_link "Add Another link", f %>
</div>
views/online_score/_online_score_url_fields:
<div class="inputset">
<%= f.label :url %> <%= f.url_field :url, :value => "http://www.google.be"%>
<%= f.label :description %> <%= f.text_field :description %>
<%= link_to_remove_fields "remove", f %>
</div>
My problem is now that I want to be able to dynamically add inputs for online_score_urlobjects which I try to do with JQuery. I try to do this by rendering the partial like so:
helpers/online_scores_helper.rb:
def add_url_link(name, form)
link_to_function name do |page|
online_score_url = render(:partial => 'online_score_url_fields', :f => form )
page << %{
$('.links').append("#{ escape_javascript online_score_url }");
}
end
end
The problem is then that fseems to be undefined in the partial. I expect this has something to do with the line <% f.fields_for :url do |b| %> in my view which doesn't get executed via the dynamic adding. But I don't really know how to fix. I think I need an alternative for the form_formethod? How to do that?
I guess my main question is: how do I iterate over an array in a controlled way, and for every element create a set of input forms like in the partial AND be able to 'add' one or more dynamically?
Thanks for your time.
Try this one:
<%= render "online_score_url_fields", :locals => {:f => b} %>
this is beacuse :f is not a parameter for the render method. So you need to use :object, :collection or something locals with the syntax above.
The same here:
online_score_url = render(:partial => 'online_score_url_fields', :locals => {:f => form} )
In my routes file I have:
resources :features, :as => 'featured'
However, when I use the following:
<% form_for #feature, :html => { :multipart => true } do |f| -%>
<%= render :partial => "form", :locals => { :f => f } -%>
<p><%= submit_tag "Feature these submissions" -%></p>
<% end -%>
I receive this error:
"undefined method `features_path' for #<#:0x00000106228ec0>"
This is my "new" method in the "features_controller":
def new
#feature = Feature.new
#submissions = Submission.find(pending_featured_submissions)
end
Before I upgraded to Rails 3, Rails was able to figure out that I was using a custom named helper. Now it seems as though form_for is ignoring the line in my resources file and using features_path, when it should be used featured_path.
Maybe I'm doing something wrong, or missing something.
Thanks for looking =)
For what its worth I ended up having to specify the url in the form builder.
<% form_for #feature, :url => featured_index_path, :html => { :multipart => true } do |f| %>
You are using submit_tag. If you used the form object to submit then your path will be as defined in the form_for so instead of
<% form_for #feature, :html => { :multipart => true } do |f| -%>
<%= render :partial => "form", :locals => { :f => f } -%>
<p><%= submit_tag "Feature these submissions" -%></p>
<% end -%>
you should use
<%= form_for #feature, :html => { :multipart => true } do |f| -%> //Note the = sign
<%= render :partial => "form", :locals => { :f => f } -%>
<p><%= f.submit "Feature these submissions" -%></p>
<% end -%>
Note that because you are in Rails 3 not Rails 2, you should use the = symbol in your form declaration
I have a form partial that needs to render a remote_form_for or a form_for depending on the value of a local variable passed into it from the caller view. It looks like...
<% if ajax %>
<% remote_form_for #search, :url => {:action => :search_set, :controller => :searches, :stype => stype} do |f| %>
<% else %>
<% form_for #search, :url => {:action => :search_set, :controller => :searches, :stype => stype} do |f| %>
<% end %>
Obviously, I am getting a syntax error near the <%else %>, because its expect an "end".
What's the right way to do this?
you could make a helper method
def form_or_remote_form_for object, *opts, &proc
if ajax
remote_form_for object, *opts, &proc
else
form_for object, *opts, &proc
end
end
and then in your views it'd just be
<% form_or_remote_form_for #search, :url => {:action => :search_set, :controller => :searches, :stype => stype} do |f| %>