Search code examples
ruby-on-railspartialsrenderpartial

Does rails automatically pass '@variables' into partial?


I have a simple setup:

class EventsController < ApplicationController
  def edit
    @user = User.find(params[:user_id])
    @event = Event.find(params[:id])
  end
end

events\edit.html.erb:

<h1>Edit <%= @user.name %>'s event</h1>

<%= render 'form' %>

events\_form.html.erb:

<%= form_for [@user, @event] do |f| %>

  <%= f.label :title %>
  <%= f.text_field :title %>

  <%= f.label :description %>
  <%= f.text_area :description %>

  <%= f.submit %>
<% end %>

To my biggest surprise this code is working and I am not getting any errors. Form partial knows about @user and @event! I always thought I have to pass parameters as locals in order to access them in the partial, so the render from the view have to be:

<%= render 'form', user: @user, event: @event %>

And form_for line should be changed to:

<%= form_for [user, event] do |f| %>

Am I missing something here? Is it one of those days when I confused my self so much that I should probably get some sleep?

I am running this on Rails 4.1.4 and events are nested resources of user if that changes anything.


Solution

  • Your parameter is an instance variable. As such it is available to any partials rendered in the view.

    You can check out more about rendering on the rails guides: http://guides.rubyonrails.org/getting_started.html#rendering-a-partial-form

    It's good practice to pass in variables to partials as locals, as its easier to reuse the partial in other actions:

    http://guides.rubyonrails.org/layouts_and_rendering.html#passing-local-variables

    Also if you try to access a local variable you didn't pass into the partial, your view with explode, while an instance variable will just be nil. Having the view explode is, in my opinion, easier to debug.