minitest gem出错:NoMethodError:NoMethodError:nil的未定义方法`env':NilClass *

时间:2016-06-23 16:07:24

标签: ruby-on-rails devise tdd minitest guard

我正在尝试用minitest gem测试我的应用程序,我遇到了错误:

错误[“test_User_should_be_valid”,UserTest,2016-06-23 16:11:17 +0200]  test_User_should_be_valid#UserTest(1466691077.75s) NoMethodError:NoMethodError:nil的未定义方法`env':NilClass

解释我的工作是这样的: 所以我用命令创建了一个设计用户:  $ rails generate devise User 然后我对我的模型用户进行了一些验证:

class User < ActiveRecord::Base
  before_save { self.email = email.downcase }
  # Include default devise modules. Others available are:
  # :confirmable, :lockable, :timeoutable and :omniauthable
  devise :database_authenticatable, :registerable,
         :recoverable, :rememberable, :trackable, :validatable, :confirmable, :lockable

  VALID_NAME_REGEX = /\A[a-zA-Z]+\z/
  validates :name, presence: true,
                   length: { in: 2..50 },
                   format: { with: VALID_NAME_REGEX, message: "is allowed only letters" }
  VALID_EMAIL_REGEX = /\A[\w+\-.]+@[a-z\d\-.]+\.[a-z]+\z/i
  validates :email, length: { maximum: 255 },
                    format: { with: VALID_EMAIL_REGEX },
                    uniqueness: { case_sensitive: false }

end

在fixtures中创建users.yml之后:

default:
  email: 'default@example.com'
  name: "fulano"
  encrypted_password: <%= encrypted_password %>

并添加fixture_file_helper_test.rb:

module FixtureFileHelpers
  def encrypted_password(password = 'password123')
    User.new.send(:password_digest, password)
  end
end

ActiveRecord::FixtureSet.context_class.send :include, FixtureFileHelpers

然后我在我的user_test.rb中执行此操作:

require 'test_helper'

    class UserTest < ActiveSupport::TestCase
     include Devise::TestHelpers
      def setup
        @user = User.new(:default)
      end

      test "User should be valid" do
        assert @user.valid?
      end
    end

然后,当我尝试使用后卫测试时,我有一个错误:

ERROR["test_User_should_be_valid", UserTest, 2016-06-23 16:11:17 +0200]
 test_User_should_be_valid#UserTest (1466691077.75s)
NoMethodError:         NoMethodError: undefined method `env' for nil:NilClass

我认为这是因为它为User(UserController.rb)生成了一个控制器。有必要使用Devise创建这个控制器吗? 我创建了一个UsersControllerTest:

require "test_helper"

class UsersControllerTest < ActionController::TestCase
   include Devise::TestHelpers
  def setup
    @user = users :default
    sign_in @user
  end

  def teardown
    sign_out @user
  end
end

并且错误仍然存​​在。

使用Spring的My Guard文件:

guard :minitest, spring: true, all_on_start: false do
  watch(%r{^test/(.*)/?(.*)_test\.rb$})
  watch('test/test_helper.rb') { 'test' }
  watch('config/routes.rb')    { integration_tests }
  watch(%r{^app/models/(.*?)\.rb$}) do |matches|
    "test/models/#{matches[1]}_test.rb"
  end
  watch(%r{^app/controllers/(.*?)_controller\.rb$}) do |matches|
    resource_tests(matches[1])
  end
  watch(%r{^app/views/([^/]*?)/.*\.html\.slim$}) do |matches|
    ["test/controllers/#{matches[1]}_controller_test.rb"] +
    integration_tests(matches[1])
  end
  watch(%r{^app/helpers/(.*?)_helper\.rb$}) do |matches|
    integration_tests(matches[1])
  end
  watch('app/views/layouts/application.html.slim') do
    'test/integration/site_layout_test.rb'
  end
  # watch('app/helpers/sessions_helper.rb') do
  #   integration_tests << 'test/helpers/sessions_helper_test.rb'
  # end
  # watch('app/controllers/sessions_controller.rb') do
  #   ['test/controllers/sessions_controller_test.rb',
  #    'test/integration/users_login_test.rb']
  # end
  # watch('app/controllers/account_activations_controller.rb') do
  #   'test/integration/users_signup_test.rb'
  # end
  # watch(%r{app/views/users/*}) do
  #   resource_tests('users') +
  #   ['test/integration/microposts_interface_test.rb']
  # end
end

# Returns the integration tests corresponding to the given resource.
def integration_tests(resource = :all)
  if resource == :all
    Dir["test/integration/*"]
  else
    Dir["test/integration/#{resource}_*.rb"]
  end
end

# Returns the controller tests corresponding to the given resource.
def controller_test(resource)
  "test/controllers/#{resource}_controller_test.rb"
end

# Returns all tests for the given resource.
def resource_tests(resource)
  integration_tests(resource) << controller_test(resource)
end

的Gemfile:

source 'https://rubygems.org'

ruby "2.2.5"
gem 'rails', '4.2.5.2'
gem 'bootstrap-sass', '~> 3.3.6'
gem 'sass-rails', '>= 3.2'
gem 'uglifier', '>= 1.3.0'
gem 'coffee-rails', '~> 4.1.0'
gem 'jquery-rails'
gem 'turbolinks'
gem 'jbuilder', '~> 2.0'
gem 'sdoc', '~> 0.4.0', group: :doc

gem 'awesome_print'
gem "slim-rails"
gem 'devise'
gem 'simple_form'

group :development do
  gem "better_errors"
  gem "binding_of_caller"
  gem 'rails_layout'
  gem 'web-console'
end

group :development, :test do
  gem 'sqlite3'
  gem 'byebug'
  gem 'guard'
  gem 'guard-minitest'
  gem 'spring'
end

group :test do
  gem 'minitest-reporters', '1.0.5'
  gem 'mini_backtrace',     '0.1.3'
end

group :production do
  gem 'pg',             '0.17.1'
  gem 'rails_12factor', '0.0.2'
end

1 个答案:

答案 0 :(得分:0)

我有类似的问题。我认为您需要包含Devise::Test::ControllerHelpers并确认您创建的用户。

见下文

#test_helper.rb
class ActionController::TestCase
  include Devise::Test::ControllerHelpers
end



#users_controller_Test.rb
require "test_helper"

class UsersControllerTest < ActionController::TestCase
  def setup
    @user = users :default
    @user.confirm
    sign_in @user
  end

  def teardown
    sign_out @user
  end
end