RSpec 2.14 发布!

Myron Marston

2013 年 7 月 8 日

我们刚刚发布了 RSpec 2.14。它将是最后一个 2.x 版本的特性发布,建议所有用户升级。我们已经开始着手 RSpec 3。下周我会在博客上发布有关 RSpec 3 计划的文章,敬请关注:)。

感谢所有为此次 RSpec 发布做出贡献的贡献者。

值得注意的新特性

核心:剖析器现在也可以剖析示例组

RSpec 长期以来一直拥有 --profile 选项,用于在结束时转储前 N 个最慢的示例。在 RSpec 2.14 中,此功能得到了增强,因此它会打印平均示例时间最长的组。例如,以下是使用 --profile 5 对 rspec-core 的套件进行剖析后输出的结果

Top 5 slowest examples (0.38945 seconds, 10.8% of total time):
  RSpec::Core::Formatters::TextMateFormatter produces HTML identical to the one we designed manually
    0.10471 seconds ./spec/rspec/core/formatters/text_mate_formatter_spec.rb:64
  ::DRbCommandLine --drb-port without RSPEC_DRB environment variable set sets the DRb port
    0.07461 seconds ./spec/rspec/core/drb_command_line_spec.rb:39
  RSpec::Core::Runner#run with --drb or -X and a DRb server is running builds a DRbCommandLine and runs the specs
    0.0744 seconds ./spec/rspec/core/runner_spec.rb:47
  command line when a custom order is configured orders the groups and examples by the provided strategy
    0.06924 seconds ./spec/command_line/order_spec.rb:169
  RSpec::Core::ConfigurationOptions#configure sends pattern before files_or_directories_to_run
    0.06649 seconds ./spec/rspec/core/configuration_options_spec.rb:48

Top 5 slowest example groups:
  RSpec::Core::Formatters::HtmlFormatter
    0.05861 seconds average (0.05861 seconds / 1 example) ./spec/rspec/core/formatters/html_formatter_spec.rb:9
  RSpec::Core::Formatters::TextMateFormatter
    0.05713 seconds average (0.1714 seconds / 3 examples) ./spec/rspec/core/formatters/text_mate_formatter_spec.rb:9
  command line
    0.05218 seconds average (0.31307 seconds / 6 examples) ./spec/command_line/order_spec.rb:3
  ::DRbCommandLine
    0.02016 seconds average (0.16127 seconds / 8 examples) ./spec/rspec/core/drb_command_line_spec.rb:4
  RSpec::Core::Runner
    0.01822 seconds average (0.10931 seconds / 6 examples) ./spec/rspec/core/runner_spec.rb:5

核心:新的 --warnings 标志用于启用 Ruby 的警告模式

现在,您可以传递 --warnings-w 标志来启用 ruby 的警告模式。

核心:共享示例组的范围限定为定义它们的上下文

在 2.14 之前,共享示例组存储在一个全局哈希表中,可以在任何上下文中定义,也可以从任何上下文中使用。在 2.14 中,这种情况发生了改变:共享示例组的范围现在限定为定义它们的上下文。这意味着您现在可以执行以下操作

describe MySinatraApp1 do
  shared_examples_for "error handling" do
    # some examples would go here
  end

  context 'GET to /foo' do
    include_examples "error handling"
  end

  context 'GET to /bar' do
    include_examples "error handling"
  end
end
describe MySinatraApp2 do
  shared_examples_for "error handling" do
    # some different examples would go here
  end

  context 'GET to /foo' do
    include_examples "error handling"
  end

  context 'GET to /bar' do
    include_examples "error handling"
  end
end

这里有两个不同的 "error handling" 共享示例组,每个示例组的范围限定为(并从)不同的示例组。如这里所示,共享示例组可从定义它们的上下文或从任何嵌套上下文访问。在 2.14 中,在兄弟上下文中声明的共享示例组仍然可供使用以保持向后兼容性,但会打印弃用警告。在 3.0 中,您将无法使用在兄弟上下文中定义的共享示例组。

核心:弃用输出现在可配置

RSpec 2.14 已经弃用了一些内容,以便在 3.0 中删除。为了帮助减少由于弃用数量增加而导致的噪音,出现了一个新的选项,可以将弃用警告定向到文件

# spec_helper.rb
RSpec.configure do |rspec|
  rspec.deprecation_stream = 'log/deprecations.log'
  # or
  rspec.deprecation_stream = File.open("/path/to/file", "w")
end

通常,弃用警告会被打印到 stderr。当您配置此选项时,它会将弃用警告发送到已配置的文件,并在规格运行结束时打印类似以下的信息

2 deprecations logged to log/deprecations.log

模拟:新的消息期望语法

在 RSpec 2.11 中,我们在 rspec-expectations 中添加了新的语法,该语法不再依赖于猴子补丁,从而避免了与代理对象相关的某些问题。在 RSpec 2.14 中,我们将相同的语法扩展到了 rspec-mocks

mailer = double("Mailer")

# old syntax:
mailer.stub(:deliver_welcome_email)
mailer.should_receive(:deliver_welcome_email).with(an_instance_of(User))

# new syntax
allow(mailer).to receive(:deliver_welcome_email)
expect(mailer).to receive(:deliver_welcome_email).with(an_instance_of(User))

有关更多详细信息,请阅读 Sam Phippen 在 2.14.0.rc1 版本发布时发布的 公告博客文章

模拟:间谍

来自 Thoughtbot 的 Joe Ferris 实施了此新特性。传统上,rspec-mocks 要求您在收到消息之前设置消息期望

mailer = double("Mailer")
expect(mailer).to receive(:deliver_welcome_email).with(an_instance_of(User))
UserCreationService.new(mailer).create_user(params)

在某些情况下,此顺序感觉反了(特别是如果您尝试使用安排/操作/断言模式组织测试)。间谍允许您在事后断言消息已收到

mailer = double("Mailer", deliver_welcome_email: nil)
UserCreationService.new(mailer).create_user(params)
expect(mailer).to have_received(:deliver_welcome_email).with(an_instance_of(User))

请注意,您首先必须对您稍后将期望的消息进行存根,以便 rspec-mocks 可以监视它。(对于 rspec-mocks 来说,没有可行的高效方法可以自动监视发送到所有对象的任何方法调用)。或者,您可以创建一个测试双重作为空对象(使用 double().as_null_object),这将对发送到该对象的所有消息进行自动间谍

mailer = double("Mailer").as_null_object
UserCreationService.new(mailer).create_user(params)
expect(mailer).to have_received(:deliver_welcome_email).with(an_instance_of(User))

文档

RDoc

Cucumber 特性

发行说明

rspec-core 2.14.0

完整变更日志

增强功能

错误修复

弃用

rspec-expectations 2.14.0

完整变更日志

增强功能

错误修复

弃用

rspec-mocks 2.14.0

完整变更日志

增强功能

错误修复

弃用

rspec-rails 2.14.0

增强功能

错误修复