user5198598
user5198598

Reputation:

Ruby on rails test error

I am learning to make tests for a ruby on rails application, and I appear to have run into an issue. I am trying to login a user as I do not have access to the session[:user_id] inside these two tests. So I have made a method inside the test_helper that defines these methods in my create_categories_test, and they run, but when I set a login for them, it returns this error:

(byebug) post login_path session: [{username: user.username, password: password}]
*** NoMethodError Exception: undefined method `[]' for nil:NilClass

This is my helper method in test_helper.rb

ENV['RAILS_ENV'] ||= 'test'
require File.expand_path('../../config/environment', __FILE__)
require 'rails/test_help'

class ActiveSupport::TestCase
  # Setup all fixtures in test/fixtures/*.yml for all tests in alphabetical order.
  fixtures :all

  # Add more helper methods to be used by all tests here...
  def sign_in_as(user, password)
    post login_path, session: {username: user.username, password: password}
  end
end

Note: I put a debugger inside my method and ran the same line of code which returned nil(for some reason)

Here's my code for my create_categories_test.rb

def setup
  @user = User.create(username: "John", email: "[email protected]",    password: "password", admin: true)
end

test "get new category form and create category" do
  sign_in_as(@user, "password")
  get new_category_path
  assert_template 'categories/new'
  assert_difference 'Category.count' do
    post_via_redirect categories_path, category: {name: "sports"}
  end
  assert_template 'categories/index'
  assert_match "sports", response.body
end

test "invalid category submission results in failure" do
  sign_in_as(@user, "password")
  get new_category_path
  assert_template 'categories/new'
  assert_no_difference 'Category.count', 1 do
    post categories_path, category: {name: " "}
  end
  assert_template 'categories/new'
  assert_select 'h2.panel-title'
  assert_select 'div.panel-body'    
end

My login controller:

class SessionsController < ApplicationController
  def new  
  end  

  def create
    user = User.find_by(username: params[:sessions][:username])
    if user  && user.authenticate(params[:sessions][:password])
      session[:user_id] = user.id
      flash[:success] = "You have successfully logged in"
      redirect_to user_path(user)
    else
      flash.now[:danger] = "There was something wrong with your login details"
      render 'new'
    end
  end

  def destroy
    session[:user_id] = nil
    flash[:success] = "You have successfully logged out"
    redirect_to root_path
  end
end

Upvotes: 0

Views: 162

Answers (1)

Roman Kiselenko
Roman Kiselenko

Reputation: 44360

I assume the problem in your params in the post method:

post login_path session: [{username: user.username, password: password}]  

You post an array [{username: user.username, password: password}], but controller expect an hash:

post login_path session: {username: user.username, password: password}  

Also your login helper:

#session: {}
post login_path, session: {username: user.username, password: password}
                 ^^^^^^^

But controller expect:

#sessions: {}
user = User.find_by(username: params[:sessions][:username])
                                      ^^^^^^^^

Probably this is off-topic question, because it's about a simple typo in the code.

Upvotes: 1

Related Questions