测试 请教 RSpec 的 Stub

匿名 · 2013年01月17日 · 最后由 leonkaiyu 回复于 2013年01月17日 · 3441 次阅读

let(:product) { stub(name: 'Test') }

let(:product) { stub(:product, name: 'Test') }

感觉在使用上面没有什么区别,但多增加的一个符号:product,有什么特别作用吗?

# File 'lib/rspec/mocks/methods.rb', line 31

def stub(message_or_hash, opts={}, &block) if Hash === message_or_hash message_or_hash.each {|message, value| stub(message).and_return value } else __mock_proxy.add_stub(caller(1)[0], message_or_hash.to_sym, opts, &block) end end 没有找到 add_stub 方法参数说明,不知道如果定义了 :product,第二个参数就是这个消息的参数了吗?因为我看那个 Hash 传给了 opts。

你找错源码了,你用的 stub 是创建 Mock 对象的,你看的源码是 method_stub。你关注的地方的相关源码如下:

https://github.com/rspec/rspec-mocks/blob/master/lib/rspec/mocks/example_methods.rb#L40-L42

def stub(*args)
  declare_double('Stub', *args)
end

一路跟踪到这里 https://github.com/rspec/rspec-mocks/blob/master/lib/rspec/mocks/test_double.rb#L22-L26

# Creates a new test double with a `name` (that will be used in error
# messages only)
def initialize(name=nil, stubs_and_options={})
  __initialize_as_test_double(name, stubs_and_options)
end

以及这里 https://github.com/rspec/rspec-mocks/blob/master/lib/rspec/mocks/test_double.rb#L55-L64

def __initialize_as_test_double(name=nil, stubs_and_options={})
  if name.is_a?(Hash) && stubs_and_options.empty?
    stubs_and_options = name
    @name = nil
  else
    @name = name
  end
  @options = extract_options(stubs_and_options)
  assign_stubs(stubs_and_options)
end

具体只有 inspect 用到 https://github.com/rspec/rspec-mocks/blob/master/lib/rspec/mocks/test_double.rb#L37-L39

def inspect
  "#<#{self.class}:#{sprintf '0x%x', self.object_id} @name=#{@name.inspect}>"
end

说白了,就是给个名字,错误显示里看得清楚点

匿名 #2 2013年01月17日

@kenshin54 太感谢了。

需要 登录 后方可回复, 如果你还没有账号请 注册新账号