Все тесты Ruby: undefined метод `authenticate 'для nil: NilClass

Большинство моих тестов поднимают следующее, и я не понимаю, почему. Все методы вызова повышают ошибку "authenticate". Я проверил код, если был метод под названием "authenticate", но такого метода нет.

  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)>'

Проект можно найти там = > https://github.com/agilepandas/enki, если вы хотите запустить тесты самостоятельно.

Ответ 1

Этот вопрос был дан ответ в Twitter @MatthewClosson

@jeffehh Вам необходимо создать spec/support/devise.rb файл как здесь указано https://github.com/plataformatec/devise#test-helpers, чтобы включить помощников тестовых тестов #ruby

Спасибо еще раз.

Ответ 2

Я знаю, что вы используете Rspec, но вы можете столкнуться с этой же проблемой с помощью Test::Unit. Вам просто нужно добавить тестовые помощники при разработке test/test_helper.rb

class ActiveSupport::TestCase
  include Devise::TestHelpers
end

Ответ 3

Приведенный выше ответ не сработал у меня (RSpec 3.1)

См. fooobar.com/questions/46217/... для решения, которое сработало для меня.

Перед настройкой переменных вам нужно будет вывести анонимного пользователя:

before :each do
  sign_out :user
end

Ответ 4

в RSpec

как отметил Джеффри У. в своем ответе выше → , чтобы установить это для всех контроллеров:

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

однако, если это относится только к одной спецификации, вам не обязательно включать в себя помощников по разработке всех ваших спецификаций контроллеров, вы можете просто явно включить эти помощники в том, что один контроллер описывает блок:

require 'spec_helper'
describe MyCoolController
  include Devise::TestHelpers

  it { } 
end

Ответ 5

У меня были одни и те же неудачи в одном из моих проектов. Он использует Ruby 2.0.0-p598, Rails 3.2.21, RSpec 2.99. Когда я запускаю все спецификации вместе, проблема возникла. Когда я запускал спецификации в отдельности, они проходили. У меня есть следующее в моем spec/spec_helper.rb:

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

Я добавил следующее к первому описанию в каждом неудачном файле spec. Это не решило проблему:

before :each do
  sign_out :user
end

Также не было:

after :each do
  sign_out :user
end

Вдохновленный ответом на вопрос this stackoverflow, я запускал разные комбинации каталогов rspec, чтобы выяснить, какие из них могут мешать друг другу. В конце я обнаружил, что звоню:

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

когда я изменил все вхождения этого в:

before(:each) do
  :
end

Все спецификации прошли без сбоя:

undefined method `authenticate' for nil:NilClass

Я надеюсь, что это поможет другим.

Ответ 6

Если вы работаете со спецификацией вида, вы можете заглушить current_user. Это эффективно отменяет помощник current_user, вызванный из вашего представления, с возвращаемым. Здесь, как с 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

Ответ 7

Похоже, что есть некоторые обновления исходного кода. ApplicationController указывает, что перед любым запросом должен выполняться фильтр authenticate_user!. Этот поток содержит некоторые сведения о проблемах с ним:

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

По сути, функция authenticate_user! является частью Rails 3 (с использованием новой функции devise, о которой я мало знаю). Если приложение не может найти модель пользователя (из-за проблем с пространством имен или по какой-либо причине), метод не будет работать. Приложение "enki", с которым вы связались, теперь является приложением Rails 3. Он может испытывать несколько растущих болей, поскольку он преобразуется.

Ответ 8

Ruby сообщает вам, что метод #authenticate еще не был остановлен на nil. Вы можете сделать это легко:

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

И ошибка исчезнет.