Search code examples
ruby-on-railsassociationssimple-form

rails simple_form association on new join table record


I keep getting error "undefined method `model_name' for nil:NilClass" when I try to create a new record of my model UserLanguage that has two foreign keys: language and user.

the language_id of the new UserLangauge object is nil after form submit.

user_languages#new view

<%= simple_form_for(@user_language) do |f| %>
  <%= f.association :language, label_method: :name, value_method: :id, include_blank: false, include_hidden: false %>
  <%= f.input :proficiency, collection: @proficiencies, include_blank: false, include_hidden: false %>
  <%= f.submit "Add Language"%>
<% end %>

user_languages controller

def new
    @user_language = UserLanguage.new

    ...

end

def create
    user_language = UserLanguage.new(user_language_params)
    user_language.user = current_user

    if user_language.save
      redirect_to my_account_path
    else
      render :new
    end
  end

private

  def user_language_params
    params.require(:user_language).permit(:language, :proficiency, :seeking, :sharing)
  end

I assign user with current_user (devise), but am unable to get the language to associate with the new user_langauge record....

I even tried manually assigning @user_language.language_id = params[:language] from the from data right before saving the object, but then the langauge_id is just assigned 0 for unknown reason.


Solution

  • The problem is that you are assigning user_language = ... in your create method. This assigns a local variable instead of an instance variable. A local variable is only available in that lexical scope (the create method in this case) while Rails exposes the controllers instance variables to the view.

    You can rewrite this method to:

    def create
      @user_language = current_user.user_languages
                                   .new(user_language_params)
      if @user_language.save
        redirect_to my_account_path
      else
        render :new
      end
    end
    

    This assumes that you have setup a has_many :user_languages relation in your User class.