Search code examples
rubyruby-on-rails-5nomethoderror

NoMethodError in Welcome#show


Here is the error I am getting:

error

Background:

I am trying to display a button based on whether an action is complete or not. Here is my code

<% if @courses_user.complete! %>
  <%= link_to "Completed", course, class: "block text-lg w-full text-center text-white px-4 py-2 bg-green hover:bg-green-dark border-2 border-green-dark leading-none no-underline" %>
<% else %>
  <%= link_to "View Modules", course, class: "block text-lg w-full text-center text-grey-dark hover:text-darker px-4 py-2 border-2 border-grey leading-none no-underline hover:border-2 hover:border-grey-dark" %>
<% end %>

In my courses_user model, I have

class CoursesUser < ApplicationRecord
  belongs_to :course
  belongs_to :user

  has_many :course_modules_users

  def completed!
    self.update_attributes(complete: true)
  end
end

and in the welcomeController I have

class WelcomeController < ApplicationController
  def show
    @courses = Course.all.order(created_at: :asc)
    @courses_user = CoursesUser.all
  end
end

But I'm getting a NoMethodError, any help is appreciated.


Solution

  • You have defined @courses_user = CoursesUser.all, so its a collection not a single object. And you can't call complete! on a collection, so is the error.

    Solution:

    Iterate through @courses_user and call complete! on each instance like so

    <% @courses_user.each do |cu| %>
      <% if cu.complete! %>
        <%= link_to "Completed", course, class: "block text-lg w-full text-center text-white px-4 py-2 bg-green hover:bg-green-dark border-2 border-green-dark leading-none no-underline" %>
      <% else %>
        <%= link_to "View Modules", course, class: "block text-lg w-full text-center text-grey-dark hover:text-darker px-4 py-2 border-2 border-grey leading-none no-underline hover:border-2 hover:border-grey-dark" %>
      <% end %>
    <% end %>
    

    Note:

    To avoid another potential error, you should change complete! to completed! as there is no method as complete! in your CoursesUser model.

    So the final code would be

    <% @courses_user.each do |cu| %>
      <% if cu.completed! %>
        <%= link_to "Completed", course, class: "block text-lg w-full text-center text-white px-4 py-2 bg-green hover:bg-green-dark border-2 border-green-dark leading-none no-underline" %>
      <% else %>
        <%= link_to "View Modules", course, class: "block text-lg w-full text-center text-grey-dark hover:text-darker px-4 py-2 border-2 border-grey leading-none no-underline hover:border-2 hover:border-grey-dark" %>
      <% end %>
    <% end %>