Ruby on Rails Coursera测试中的类Bug

时间:2018-01-13 16:55:50

标签: ruby-on-rails ruby rspec

我目前正在参加Coursera的免费 Ruby on Rails简介课程。我正在进行第三项任务,其中包含创建People类,其中您具有搜索功能等功能。

当我使用他们设计的单元测试运行rspec时,我遇到了一个奇怪的错误。我99%肯定错误在于单元测试。具体来说,在我触摸任何文件之前 ,我收到以下错误:

        raise <<-EOS
        #{description} accessed in #{article} #{hook_expression} hook at:
          #{CallerFilter.first_non_rspec_line}

        `let` and `subject` declarations are not intended to be called
        in #{article} #{hook_expression} hook, as they exist to define state that
        is reset between each example, while #{hook_expression} exists to
        #{hook_intention}.
        EOS

      RuntimeError:
        let declaration `class` accessed in an `after(:context)` hook at:
          /Users/<username>/.rvm/gems/ruby-2.4.0/gems/rspec-core-3.7.1/exe/rspec:4:in `<top (required)>'

        `let` and `subject` declarations are not intended to be called
        in an `after(:context)` hook, as they exist to define state that
        is reset between each example, while `after(:context)` exists to
        cleanup state that is shared across examples in an example group.

对于初学者,我并不完全理解他们用来描述他们的测试的语法。其次,这是Coursera类的作者写的原始测试文件:

require 'rspec'
require 'rspec/its'
require_relative '../module2_lesson3_formative.rb'

describe "lesson3" do

  context "check results" do
    p1 = Person.new("Ivana", "Trump")
    p2 = Person.new("Eric", "Trump")
    p3 = Person.new("Melania", "Trump")
    p4 = Person.new("Marla", "Maples")

    it "unexpected search result" do
      expect(Person.search("Trump").size).to be == 3
    end
  end

  context "check instance properties" do
    subject(:john) { Person.new("Chris", "Christie") }

    it "missing first_name" do
      is_expected.to respond_to(:first_name)
    end

    it "missing last_name" do
      is_expected.to respond_to(:last_name)
    end

  end

  context "check class properties" do
    subject(:class) { Person }

    it "missing search" do
      is_expected.to respond_to(:search)
    end
  end
end

我希望当我运行rspec时,有人可以向我解释调试信息。我正在使用RSpec 3.7,我猜是问题,因为它表明它可能是版本升级的东西here。这也可以解释这个类的作者没有故意推翻坏代码的事实。对我来说解决这个问题的最佳方法是什么?为什么这样的行是这样的:

subject(:john) { Person.new("Chris", "Christie") }

状况不好?非常感谢!真的很感激你的时间:)

2 个答案:

答案 0 :(得分:1)

这似乎解决了rspec抱怨的问题:

describe "lesson3" do

  subject { person } # ADDED THIS LINE
  context "check results" do
    p1 = Person.new("Ivana", "Trump")
    p2 = Person.new("Eric", "Trump")
    p3 = Person.new("Melania", "Trump")
    p4 = Person.new("Marla", "Maples")

    it "unexpected search result" do
      expect(Person.search("Trump").size).to be == 3
    end 
  end

  context "check instance properties" do
    let(:person) { Person.new("Chris", "Christie") } # CHANGED THIS LINE

    it "missing first_name" do
      is_expected.to respond_to(:first_name) 
    end 

    it "missing last_name" do
      is_expected.to respond_to(:last_name) 
    end 

  end

  context "check class properties" do
    let(:person) { Person } # CHANGED THIS LINE

    it "missing search" do
      is_expected.to respond_to(:search) 
    end 
  end
end

我仍然不确定为什么,或者差异是什么意思。我希望有人能够更深入地解释它。

答案 1 :(得分:1)

为了更改规范的主题类别,您可以根据每个示例“重新定义”主题,或者根据需要进行重新定义。

当尝试使用let或subject更改规范主题的类时,您会收到详细的错误(警告)消息:

  

letsubject声明不打算在。中调用   after(:context)挂钩,因为它们存在以定义重置的状态   每个例子之间

因此,您无法明确设置主题的类,因为它将在每个运行示例中重置。

您可以使用subject将主题设置为“检查类属性”上下文中的Person对象,这样is_expected将检查响应类方法搜索的此对象,像:

context "check class properties" do
  subject { Person }

  it 'missing search' do
    is_expected.to respond_to(:search)
  end
end