为什么 RSpec 在 ruby​​ 中运行时会运行两次specs并且重新加载spec文件?

Mic*_*zka 5 ruby rspec jruby guard

我尝试在现有的 ruby​​ 运行时中使用 RSpec,并在每次文件更改时运行规范。这是因为 JRuby 和 JVM 启动时间。为了在每次运行时消除这个问题,我想启动 ruby​​ 一次,然后只重新加载更改的文件并运行规范。我正在使用guard(具有不同的扩展)和watchr,但似乎都遇到了下面描述的问题。

我将问题归结为 RSpec 本身。问题是,当通过RSpec::Core::Runner.run多次运行 RSpec 时,它可以正常工作,直到使用load. 然后 RSpecs 开始运行规范两次。我创建了示例项目来实时显示此问题:https ://github.com/mostr/rspec_double_run_issue

以下是示例输出:

ruby run_spec_in_loop.rb 
Running spec from within ruby runtime
.
Finished in 0.00047 seconds
1 example, 0 failures

loading spec file via 'load' as if it was changed and we wanted changes to be picked up
Running spec from within ruby runtime
..
Finished in 0.001 seconds
2 examples, 0 failures
Run Code Online (Sandbox Code Playgroud)

当从现有的 ruby​​ 运行时运行时,有什么方法可以告诉 RSpec 在后续运行之间清除其上下文吗?我还将此作为 RSpec Core 项目的问题#826提出。

Dre*_*awn 2

在这里总结答案,以便从“未回答”过滤器中删除这个问题......

根据RJHunter的观察,该解释已记录在 GitHub RSpec Core 项目中:

https://github.com/rspec/rspec-core/issues/826#issuecomment-15089030

对于后代(如果上述链接失效),以下是详细信息:

RSpec 运行程序已经在内部调用加载,您的第二个加载是导致双运行问题的原因。

我根据您的示例快速编写了一个脚本,该脚本重新运行单个规范文件,将规范更改为其他内容,然后重新运行它们,无需第二次加载即可正常工作

请参阅: https: //gist.github.com/JonRowe/5192007

上述要点包含:

require 'rspec'
 
spec_file = 'spec/sample_spec.rb'
 
File.open(spec_file, 'w') { |file| file.write 'describe { specify { expect(true).to eq false } }' }
 
1.upto(5) do |i|
  puts "Running spec from within ruby runtime"
  ::RSpec::Core::Runner.run([spec_file], STDERR, STDOUT)
 
  #rewriting the spec file
  File.open(spec_file, 'w') { |file| file.write "describe { specify { expect(#{i}).to eq false } }" }
  
end
Run Code Online (Sandbox Code Playgroud)