使用 ActiveRecord::Relation 时的 RSpec 匹配器

ilr*_*ein 5 ruby activerecord rspec ruby-on-rails

所以这是我要测试的方法:

def self.by_letter(letter)
  where("lastname LIKE ?", "#{letter}%").order(:lastname)
end
Run Code Online (Sandbox Code Playgroud)

这里有一个简单的问题,#{letter} 后面的百分号到底是做什么的?跟格式化有关系吗?

这是测试该方法的规范的一部分:

    context 'method "by_letter"' do
    it 'returns and ordered list by letter' do
      theon = Contact.create!(
        firstname: "Theon", 
        lastname: "Greyjoy", 
        email: "tgreyjoy@ironprice.com"
        )
      rob = Contact.create!(
       firstname: "Rob", 
       lastname: "Stark", 
       email: "rstark@winterfell.com" 
       )
      tyrion = Contact.create!(
       firstname: "Tyrion", 
       lastname: "Lannister", 
       email: "tlannister@kingslanding.com" 
       )
      result = Contact.by_letter("S")
      expect(result).to include("Snow")
    end
  end
Run Code Online (Sandbox Code Playgroud)

这是我在运行上述测试后获得的输出日志(哦,请记住,在规范的早期我创建了一个“Jon Snow”,他应该按字母顺序在“Stark”之前弹出):

    Failures:

  1) Contact method "by_letter" returns and ordered list by letter
     Failure/Error: expect(result).to include("Snow")
       expected #<ActiveRecord::Relation [#<Contact id: 1, firstname: "Jon", lastname: "Snow", email: "lordcommander@nightswatch.com", created_at: "2014-11-14 17:17:55", updated_at: "2014-11-14 17:17:55">, #<Contact id: 3, firstname: "Rob", lastname: "Stark", email: "rstark@winterfell.com", created_at: "2014-11-14 17:17:56", updated_at: "2014-11-14 17:17:56">]> to include "Snow"
       Diff:
       @@ -1,2 +1,3 @@
       -["Snow"]
       +[#<Contact id: 1, firstname: "Jon", lastname: "Snow", email: "lordcommander@nightswatch.com", created_at: "2014-11-14 17:17:55", updated_at: "2014-11-14 17:17:55">,
       + #<Contact id: 3, firstname: "Rob", lastname: "Stark", email: "rstark@winterfell.com", created_at: "2014-11-14 17:17:56", updated_at: "2014-11-14 17:17:56">]
Run Code Online (Sandbox Code Playgroud)

我错过了什么?我的测试不应该通过,因为我返回了一个包含我指定的字符串的集合吗?是否有一些复杂性,因为它不是常规数组而是某种代理数组?我需要做什么才能通过考试?

Aru*_*hit 5

result是一个ActiveRecord::Relation对象。所以你应该做如下: -

expect(result).to include(rob)
Run Code Online (Sandbox Code Playgroud)

rob姓氏为"Stark",因此Contact.by_letter("S")将包含rob过滤列表中。


sam*_*amg 3

尝试expect(result.first).to include("Snow")

你也可以说(最好):

expect(result.first.lastname).to eq("Snow")