Semua pengujian Ruby yang meningkatkan: metode yang tidak ditentukan `otentikasi 'untuk nil: NilClass

132

Sebagian besar tes saya meningkatkan yang berikut dan saya tidak mengerti mengapa. Semua metode panggilan meningkatkan kesalahan 'otentikasi'. Saya telah memeriksa kode jika ada metode yang disebut "otentikasi" tetapi tidak ada metode seperti itu.

  1) Admin::CommentsController handling GET to index is successful
     Failure/Error: get :index
     undefined method `authenticate!' for nil:NilClass
     # ./spec/controllers/admin/comments_controller_spec.rb:9:in `block (3 levels) in <top (required)>'


  124) PostsController handling GET for a single post should render show template
     Failure/Error: get :show, :year => '2008', :month => '01', :day => '01', :slug => 'a-post'
     undefined method `authenticate' for nil:NilClass
     # ./app/controllers/application_controller.rb:18:in `set_current_user_for_model'
     # ./spec/controllers/posts_controller_spec.rb:131:in `do_get'
     # ./spec/controllers/posts_controller_spec.rb:140:in `block (3 levels) in <top (required)>'

Proyek ini dapat ditemukan di sana => https://github.com/agilepandas/enki jika Anda ingin menjalankan tes sendiri.

Jeffrey W.
sumber

Jawaban:

74

Saya sadar Anda menggunakan Rspec tetapi Anda dapat mengalami masalah yang sama dengannya Test::Unit. Anda hanya perlu menambahkan alat bantu tes yang dirancang untuktest/test_helper.rb

class ActiveSupport::TestCase
  include Devise::TestHelpers
end
Tim Fletcher
sumber
8

Jawaban di atas tidak bekerja untuk saya (RSpec 3.1)

Lihat https://stackoverflow.com/a/21166482/1161743 untuk solusi yang bekerja untuk saya.

Anda harus keluar dari pengguna anonim sebelum membuat variabel:

before :each do
  sign_out :user
end
Jonathan Lin
sumber
1
Juga, periksa apakah Anda belum memasukkan Rancangan :: TestHelpers beberapa kali karena ini dapat menyebabkan masalah.
Joseph Siefers
8

di RSpec

seperti yang disebutkan Jeffrey W., dalam jawabannya di atas -> untuk mengatur ini ke semua pengontrol:

RSpec.configure do |config|
  # ...
  config.include Devise::TestHelpers, type: :controller
  # ...
end

namun, jika ini hanya relevan untuk satu spek, Anda tidak perlu menyertakan alat bantu untuk semua spek pengontrol Anda, Anda bisa secara eksplisit menyertakan bantuan tersebut dalam satu blok yang menggambarkan blok pengontrol:

require 'spec_helper'
describe MyCoolController
  include Devise::TestHelpers

  it { } 
end
setara8
sumber
2

Saya mengalami kegagalan yang sama di salah satu proyek saya. Itu menggunakan Ruby 2.0.0-p598, Rails 3.2.21, RSpec 2.99. Ketika saya menjalankan semua spesifikasi bersama masalah terjadi. Ketika saya menjalankan spesifikasi secara terpisah, mereka lulus. Saya memiliki yang berikut ini di spec / spec_helper.rb saya:

RSpec.configure do |config|
  # ...
  config.include Devise::TestHelpers, type: :controller
  # ...
end

Saya menambahkan yang berikut ke deskripsi pertama di setiap file spec yang gagal. Ini tidak menyelesaikan masalah:

before :each do
  sign_out :user
end

Tidak juga:

after :each do
  sign_out :user
end

Mengambil inspirasi dari jawaban untuk pertanyaan stackoverflow ini , saya menjalankan kombinasi yang berbeda dari direktori rspec bersama-sama untuk mencari tahu mana yang dapat mengganggu satu sama lain. Pada akhirnya saya menemukan saya menelepon:

before() do #note no :each passed to before
  :
end

ketika saya mengubah semua kejadian ini menjadi:

before(:each) do
  :
end

Semua spesifikasi lulus tanpa kegagalan:

undefined method `authenticate' for nil:NilClass

Saya harap ini bisa membantu orang lain.

Cathal Curtis
sumber
0

Jika Anda bekerja dengan spec tampilan, Anda dapat rintisan current_user. Ini secara efektif menimpa current_userpembantu yang dipanggil dari pandangan Anda dengan apa pun yang dikembalikan. Begini caranya dengan rspec-3.2.3:

RSpec.describe "projects/show", type: :view do
  before(:each) do
    allow(view).to receive(:current_user).and_return(FactoryGirl.create(:user))
  end

  it "renders attributes in <p>" do
    render
    expect(rendered).to match(/whatever you want to regex match here/)
  end
end
Pete
sumber
-3

Sepertinya ada beberapa pembaruan pada kode sumber. ApplicationController menetapkan bahwa perlu ada authenticate_user!filter yang dijalankan sebelum permintaan apa pun. Utas ini memberikan beberapa latar belakang masalah:

http://groups.google.com/group/plataformatec-devise/browse_thread/thread/f7260ebe2d9f7316?fwc=1

Pada dasarnya, itu authenticate_user! fungsi ini adalah bagian dari Rails 3 (menggunakan devisefitur baru , yang saya tahu sedikit tentang). Jika aplikasi tidak dapat menemukan model Pengguna (baik karena masalah namespace atau alasan apa pun) maka metode tersebut akan gagal. Aplikasi "enki" yang Anda tautkan sekarang adalah aplikasi Rails 3. Itu bisa mengalami beberapa rasa sakit yang tumbuh saat ia bertobat.

Berin Loritsch
sumber
2
Jawaban ini adalah sekitar 99% omong kosong murni.
Maks.
-20

Ruby memberi tahu Anda, metode #authenticateitu belum ditolak nil. Anda dapat melakukannya dengan mudah dengan:

def nil.authenticate!
  puts "Bingo! Nil is now authentic!"
end

Dan kesalahan akan hilang.

Boris Stitnicky
sumber
1
tolong jangan lakukan ini. nil adalah nil, bukan objek yang valid dalam 90% kasus.
Tiago Peczenyj