I am pretty new to Rails and keep getting the error below. Any help will be greatly appreciated. Please!
Error : undefined method `model_name' for NilClass:Class
Here is my memberships controller.
class MembershipsController < ApplicationController
def new
end
def create
#user = User.find_by_email(params[:email])
#project = Project.find(params[:project_id])
#membership = #project.memberships.build(project_id: #project.id, user_id: #user.id)
redirect_to project_url(#membership.project_id)
end
end
And Here is my form for membership.
It is nested underneath project routes.
<%= form_for([:project, #membership]) do |f|%>
<div class="field">
<%= f.label "Enter the email of the person you'd like to invite:" %>
<%= text_field_tag :email %>
</div>
<div class="actions">
<%= f.submit "Save", :class=>"btn btn-primary btn-large" %>
</div>
<% end %>
For your information, memberships table is a joining table between projects table and users table.
I can't figure out why I keep getting the error above. Maybe there is something I am missing. Help Please! Thanks!
One of the 2 objects #user or #project cannot be found. Though the result becomes nil. You cannot call a method on a nil object. To know better where the faulty object is log the results.
Rails.logger.debug #user.inspect
Rails.logger.debug #project.inspect
Your form should be form_for [#project, #membership] where #project is a Project instance, not :project.
Related
So, the set up is very simple. In my controller I have
class DriverController < ApplicationController
def index
end
def new
#driver = Driver.new
end
end
And the new.html.erb is
<h1>Driver#new</h1>
<%= form_for #driver do |f| %>
<%= f.submit %>
<% end %>
When I try to acess that new page it says: "undefined method `new' for Driver:Module"
When I change def new in my controller to def create for an example, this error goes away and it says that First argument in form cannot contain nil or be empty. What is the problem?
<h1>Driver#new</h1>
<%= form_for :driver, :url: drivers_path do |f| %>
<%= f.submit %>
<% end %>
In routes.rb
resourse :drivers
And further I would suggested you yo Visit Guide Ruby on Rails the-first-form
Hope this help you !!!
I don't know where the problem was, but I just did everything all over again, and it worked.
I am pretty sure it's a very noob mistake, but I don't understand why I can't add my form directly to my homepage without causing a NoMethodError.
This is my current setup, and it works perfectly fine.
view/front_pages/home.html.erb (my home page)
<!--declare :title to be SHOULD I GET THIS-->
<% provide(:title, "SHOULD I GET THIS") %>
<div class = "container">
<h1>Should I really spend money on this?</h1>
<h2>Let's crunch in some numbers and find out...</h2>
<%= link_to "Get Started", calculate_path, class: "btn btn-info " %>
</div>
view/users/new.html.erb (where my form is right now)
<% provide(:title, "Calculate")%>
<div class = "form-group container">
<%= simple_form_for #user do |form|%>
<%= form.error_notification%>
<%= form.input :price%>
<%= form.input :wallet%>
<%= form.button :submit, "Submit", class: "submit"%>
<%end%>
</div>
controllers/users_controller.rb
class UsersController < ApplicationController
def new
#user = User.new
end
end
However, I want the form to be directly on my home page so the users don't need to click an extra button to get to the form. I tried
view/front_pages/home.html.erb
<!--declare :title to be SHOULD I GET THIS-->
<% provide(:title, "SHOULD I GET THIS") %>
<div class = "container">
<h1>Should I really spend money on this?</h1>
<h2>Let's crunch in some numbers and find out...</h2>
<%= link_to "Get Started", calculate_path, class: "btn btn-info " %>
</div>
<div class = "form-group container">
<%= simple_form_for #user do |form|%>
<%= form.error_notification%>
<%= form.input :price%>
<%= form.input :wallet%>
<%= form.button :submit, "Submit", class: "submit"%>
<%end%>
</div>
and it returns me the NoMethodError. I thought it's because I did not initiate a #user variable in the front_page controller, so I tried
class FrontPagesController < ApplicationController
def new
#user = User.new
end
def home
end
end
but it still does not work. I am thinking it's some concept about MVC that I still am not quite grasping. What is wrong with my code and what should I keep in mind next time so I don't make the same mistake?
PS: I use simple_form gem to generate my form
Edit: The error message is undefined method `model_name' for NilClass:Class
Error is quite simple:
Undefined method `model_name' for NilClass:Class
This error means you're trying to call the model_name method on a variable which is not populated with any data. You are not calling this method; form_for is - meaning you basically need to have #user declared in your controller, as you rightly pointed out:
class FrontPagesController < ApplicationController
def new
#user = User.new
end
def home
end
end
--
#user
The problem is that you're using the home action - you're declaring your #user variable in the new action. This means it won't be set, as it won't be called.
You'll be best doing this:
class FrontPagesController < ApplicationController
def home
#user = User.new
end
end
This will make #user available in your home action, which should resolve the error for you!
You need specify the action for the form
<%= form_for :user, url: { action: create } do |f| %>
or you can use your path helper if you have a resource defined for user
<%= form_for :user, url: user_path do |f| %>
I'm trying to get the Wicked Wizard gem working on my Rails app. Once a user registers for the app (using Devise), they're redirected to this form:
income.html.erb
<%= form_for #finance, url: wizard_path, :method => :put do |f| %>
<div class="field">
What <strong>year</strong> were you born?<br>
<%= f.number_field :age %>
</div>
<div class="field">
What's your <strong>zip code</strong>?<br>
<%= f.number_field :zip %>
</div>
<%= f.submit %>
<% end %>
I generated a controller called finances_welcome_controller.rb that handles wizard_path:
class FinancesWelcomeController < ApplicationController
before_filter :authenticate_user!
include Wicked::Wizard
steps :income, :expenses
def show
#finance = Finance.find_all_by_user_id current_user[:id] || #finance = current_user.finances.build(finance_params)
render_wizard
end
def update
#finance = Finance.find_all_by_user_id current_user[:id]
#finance.update(params[:finance])
render_wizard #finance
end
When I click the submit button, I'm getting this error:
NoMethodError in FinancesWelcomeController#update
undefined method `update' for #<Array:0x00000104c6ff48>
Extracted source (around line #14):
def update
#finance = Finance.find_all_by_user_id current_user[:id]
**#finance.update(params[:finance])**
render_wizard #finance
end
Not sure why the update method hasn't been defined since this is the same syntax that my resource's model is using. The Wicked Wizard gem was successfully implemented on this app.
a method starting find_all_by will return an array of Active record instances... not just a single one. update only works on a single instance.
So, either you want to run through all the instances in the array... using an each - or you want to just fetch the first one using find_by instead of find_all_by
In the case of finding by an id... I'd recommend changing it to find_by
so:
#finance = Finance.find_by_user_id current_user[:id]
#finance.update_attributes(params[:finance])
I have created a simple form to create an instance of a modle and for some reason it is not calling the create method in the controller. Here is the form code:
<% #house.mates.each do |mate| %>
<p><%= mate.name %></p>
<% end %>
<h2>Add a new mate:</h2>
<%= form_for #mate do |f| %>
<p><%= f.label "Name" %>
<%= f.text_field :name %>
<%= f.hidden_field :house_id %>
</p>
<%= f.submit "Submit", :action => :create %>
<% end %>
Here is the controller code:
class MatesController < ApplicationController
def new
#mate = Mate.new
end
def create
#mate = Mate.new(params[:mate])
#mate.save
redirect_to house_path(current_house)
end
end
There is a many to one relationship between the Mate model and the House model... I am fairly new to rails but I have made other apps with similar forms, and I have never had this problem before. I can create and save Mate objects in the console, and I am not getting any errors, so it seem that somehow the controller method is not being called. Any help is much appreciated!
In fact, if other things have no problem, your #mate object should be created. You just can't see it in house page because you have not associated #mate with house in your code.
In your form you referred :house_id, but this attribute is nil when you rendering the form.
The reason is you have not assigned it in controller.
In controller you need to initialize #mate from house object to have house_id inside it
def new
#house = something
#mate = #house.mates.new # Instead of Mate.new
end
I currently have a simple app that includes user authentication through devise and a message model(the message model uses Jquery and Faye). Both are working fine independently, but I would like to add a user_id to the messages.
I have already updated the schema and models with the relationship, but I am having trouble inputting the necessary code to have the view and controller input the relationship into the db, while keeping the jquery working. I wasn't sure of the best way, but here I tried to create a hidden field that would pull the user_id, not sure if this is even possible. Here is the applicable code, any help is appreciated.
Message index.html.erb
<ul id="chat">
<%= render #messages %>
</ul>
<%= form_for Message.new, :remote => true do |f| %>
<div class="field">
<%= f.text_field :content %>
</div>
<div class="field">
<%= f.hidden_field :user_id %>
</div>
<div class="actions">
<%= f.submit "Send" %>
</div>
<% end %>
create.js.erb for messages
<% broadcast "/messages" do %>
$("#chat").append("<%= escape_javascript render(#user.message) %>");
<% end %>
$("#new_message")[0].reset();
Messages Controller
class MessagesController < ApplicationController
def index
if #authentications = current_user
#messages = Message.all
else
redirect_to authentications_url
flash[:notice] = "You need to sign in before answering questions"
end
end
def create
#user = User.find(params[:user_id])
#message = #user.message.create(params[:message])
end
end
I think you have everything you would need, but if not, let me know and I will be happy to provide it for you.
Thanks, everyone.
two things to correct,
1)use user association to create message instance in form(probably current_user if logged-in user create a message)
<%= form_for user.messages.new, :remote => true do |f| %> #// assuming its has many association
2) if it is has_many association then change association in create action
#message = #user.messages.create(params[:message])