diff --git a/Gemfile b/Gemfile index ef78622c..4299c72e 100644 --- a/Gemfile +++ b/Gemfile @@ -13,7 +13,6 @@ gem 'rake', '~> 10.1' gem 'rdoc', '~> 3.11' gem 'redgreen', '~> 1.2' gem 'shoulda', '~> 3.5' -gem 'rr', '~> 1.1' gem 'cucumber', '1.3.18' gem 'maruku', '~> 0.7.0' gem 'rdiscount', '~> 2.0' @@ -28,6 +27,7 @@ gem 'minitest' gem 'minitest-reporters' gem 'minitest-profile' gem 'test-unit' if RUBY_PLATFORM =~ /cygwin/ || RUBY_VERSION.start_with?("2.2") +gem 'rspec-mocks' if ENV['BENCHMARK'] gem 'rbtrace' diff --git a/features/support/env.rb b/features/support/env.rb index 8f33ff63..43d74ab9 100644 --- a/features/support/env.rb +++ b/features/support/env.rb @@ -1,6 +1,5 @@ require 'fileutils' require 'posix-spawn' -require 'rr' require 'minitest/assertions' require 'time' diff --git a/test/helper.rb b/test/helper.rb index e4a50db0..9c5a1eb0 100644 --- a/test/helper.rb +++ b/test/helper.rb @@ -11,6 +11,7 @@ require 'ostruct' require 'minitest/autorun' require 'minitest/reporters' require 'minitest/profile' +require 'rspec/mocks' require 'jekyll' @@ -19,7 +20,6 @@ require 'kramdown' require 'redcarpet' require 'shoulda' -require 'rr' include Jekyll @@ -30,6 +30,20 @@ STDERR.reopen(test(?e, '/dev/null') ? '/dev/null' : 'NUL:') Minitest::Reporters.use! [Minitest::Reporters::DefaultReporter.new(:color => true)] class JekyllUnitTest < Minitest::Test + include ::RSpec::Mocks::ExampleMethods + + def before_setup + ::RSpec::Mocks.setup + super + end + + def after_teardown + super + ::RSpec::Mocks.verify + ensure + ::RSpec::Mocks.teardown + end + def fixture_site(overrides = {}) Jekyll::Site.new(site_configuration(overrides)) end diff --git a/test/test_command.rb b/test/test_command.rb index fb9e247b..f7c3e237 100644 --- a/test/test_command.rb +++ b/test/test_command.rb @@ -4,7 +4,7 @@ class TestCommand < JekyllUnitTest context "when calling .add_build_options" do should "add common options" do cmd = Object.new - mock(cmd).option.with_any_args.at_least(1) + expect(cmd).to receive(:option).at_least(:once) Command.add_build_options(cmd) end end @@ -12,7 +12,7 @@ class TestCommand < JekyllUnitTest context "when fatal error occurs" do should "exit with non-zero error code" do site = Object.new - stub(site).process { raise Jekyll::Errors::FatalException } + def site.process; raise Jekyll::Errors::FatalException; end error = assert_raises(SystemExit) { Command.process_site(site) } refute_equal 0, error.status end diff --git a/test/test_configuration.rb b/test/test_configuration.rb index 8de8ac29..ce54223c 100644 --- a/test/test_configuration.rb +++ b/test/test_configuration.rb @@ -42,12 +42,12 @@ class TestConfiguration < JekyllUnitTest assert_equal [source_dir("_config.yml")], @config.config_files(@no_override) end should "return .yaml if it exists but .yml does not" do - mock(File).exist?(source_dir("_config.yml")) { false } - mock(File).exist?(source_dir("_config.yaml")) { true } + allow(File).to receive(:exist?).with(source_dir("_config.yml")).and_return(false) + allow(File).to receive(:exist?).with(source_dir("_config.yaml")).and_return(true) assert_equal [source_dir("_config.yaml")], @config.config_files(@no_override) end should "return .yml if both .yml and .yaml exist" do - mock(File).exist?(source_dir("_config.yml")) { true } + allow(File).to receive(:exist?).with(source_dir("_config.yml")).and_return(true) assert_equal [source_dir("_config.yml")], @config.config_files(@no_override) end should "return the config if given one config file" do @@ -115,27 +115,27 @@ class TestConfiguration < JekyllUnitTest end should "fire warning with no _config.yml" do - mock(SafeYAML).load_file(@path) { raise SystemCallError, "No such file or directory - #{@path}" } - mock($stderr).puts("Configuration file: none".yellow) + allow(SafeYAML).to receive(:load_file).with(@path) { raise SystemCallError, "No such file or directory - #{@path}" } + allow($stderr).to receive(:puts).with("Configuration file: none".yellow) assert_equal Jekyll::Configuration::DEFAULTS, Jekyll.configuration({}) end should "load configuration as hash" do - mock(SafeYAML).load_file(@path) { Hash.new } - mock($stdout).puts("Configuration file: #{@path}") + allow(SafeYAML).to receive(:load_file).with(@path).and_return(Hash.new) + allow($stdout).to receive(:puts).with("Configuration file: #{@path}") assert_equal Jekyll::Configuration::DEFAULTS, Jekyll.configuration({}) end should "fire warning with bad config" do - mock(SafeYAML).load_file(@path) { Array.new } - mock($stderr).puts(("WARNING: ".rjust(20) + "Error reading configuration. Using defaults (and options).").yellow) - mock($stderr).puts("Configuration file: (INVALID) #{@path}".yellow) + allow(SafeYAML).to receive(:load_file).with(@path).and_return(Array.new) + allow($stderr).to receive(:puts).and_return(("WARNING: ".rjust(20) + "Error reading configuration. Using defaults (and options).").yellow) + allow($stderr).to receive(:puts).and_return("Configuration file: (INVALID) #{@path}".yellow) assert_equal Jekyll::Configuration::DEFAULTS, Jekyll.configuration({}) end should "fire warning when user-specified config file isn't there" do - mock(SafeYAML).load_file(@user_config) { raise SystemCallError, "No such file or directory - #{@user_config}" } - mock($stderr).puts(("Fatal: ".rjust(20) + "The configuration file '#{@user_config}' could not be found.").red) + allow(SafeYAML).to receive(:load_file).with(@user_config) { raise SystemCallError, "No such file or directory - #{@user_config}" } + allow($stderr).to receive(:puts).with(("Fatal: ".rjust(20) + "The configuration file '#{@user_config}' could not be found.").red) assert_raises LoadError do Jekyll.configuration({'config' => [@user_config]}) end @@ -157,20 +157,20 @@ class TestConfiguration < JekyllUnitTest end should "load default config if no config_file is set" do - mock(SafeYAML).load_file(@paths[:default]) { Hash.new } - mock($stdout).puts("Configuration file: #{@paths[:default]}") + allow(SafeYAML).to receive(:load_file).with(@paths[:default]).and_return({}) + allow($stdout).to receive(:puts).with("Configuration file: #{@paths[:default]}") assert_equal Jekyll::Configuration::DEFAULTS, Jekyll.configuration({}) end should "load different config if specified" do - mock(SafeYAML).load_file(@paths[:other]) { {"baseurl" => "http://wahoo.dev"} } - mock($stdout).puts("Configuration file: #{@paths[:other]}") + allow(SafeYAML).to receive(:load_file).with(@paths[:other]).and_return({"baseurl" => "http://wahoo.dev"}) + allow($stdout).to receive(:puts).with("Configuration file: #{@paths[:other]}") assert_equal Utils.deep_merge_hashes(Jekyll::Configuration::DEFAULTS, { "baseurl" => "http://wahoo.dev" }), Jekyll.configuration({ "config" => @paths[:other] }) end should "load default config if path passed is empty" do - mock(SafeYAML).load_file(@paths[:default]) { Hash.new } - mock($stdout).puts("Configuration file: #{@paths[:default]}") + allow(SafeYAML).to receive(:load_file).with(@paths[:default]).and_return({}) + allow($stdout).to receive(:puts).with("Configuration file: #{@paths[:default]}") assert_equal Jekyll::Configuration::DEFAULTS, Jekyll.configuration({ "config" => @paths[:empty] }) end @@ -183,20 +183,20 @@ class TestConfiguration < JekyllUnitTest should "load multiple config files" do External.require_with_graceful_fail('toml') - mock(SafeYAML).load_file(@paths[:default]) { Hash.new } - mock(SafeYAML).load_file(@paths[:other]) { Hash.new } - mock(TOML).load_file(@paths[:toml]) { Hash.new } - mock($stdout).puts("Configuration file: #{@paths[:default]}") - mock($stdout).puts("Configuration file: #{@paths[:other]}") - mock($stdout).puts("Configuration file: #{@paths[:toml]}") + allow(SafeYAML).to receive(:load_file).with(@paths[:default]).and_return(Hash.new) + allow(SafeYAML).to receive(:load_file).with(@paths[:other]).and_return(Hash.new) + allow(TOML).to receive(:load_file).with(@paths[:toml]).and_return(Hash.new) + allow($stdout).to receive(:puts).with("Configuration file: #{@paths[:default]}") + allow($stdout).to receive(:puts).with("Configuration file: #{@paths[:other]}") + allow($stdout).to receive(:puts).with("Configuration file: #{@paths[:toml]}") assert_equal Jekyll::Configuration::DEFAULTS, Jekyll.configuration({ "config" => [@paths[:default], @paths[:other], @paths[:toml]] }) end should "load multiple config files and last config should win" do - mock(SafeYAML).load_file(@paths[:default]) { {"baseurl" => "http://example.dev"} } - mock(SafeYAML).load_file(@paths[:other]) { {"baseurl" => "http://wahoo.dev"} } - mock($stdout).puts("Configuration file: #{@paths[:default]}") - mock($stdout).puts("Configuration file: #{@paths[:other]}") + allow(SafeYAML).to receive(:load_file).with(@paths[:default]).and_return({"baseurl" => "http://example.dev"}) + allow(SafeYAML).to receive(:load_file).with(@paths[:other]).and_return({"baseurl" => "http://wahoo.dev"}) + allow($stdout).to receive(:puts).with("Configuration file: #{@paths[:default]}") + allow($stdout).to receive(:puts).with("Configuration file: #{@paths[:other]}") assert_equal Utils.deep_merge_hashes(Jekyll::Configuration::DEFAULTS, { "baseurl" => "http://wahoo.dev" }), Jekyll.configuration({ "config" => [@paths[:default], @paths[:other]] }) end end diff --git a/test/test_entry_filter.rb b/test/test_entry_filter.rb index e3a7e8c0..e5a5dc66 100644 --- a/test/test_entry_filter.rb +++ b/test/test_entry_filter.rb @@ -48,13 +48,13 @@ class TestEntryFilter < JekyllUnitTest should "filter symlink entries when safe mode enabled" do site = Site.new(site_configuration('safe' => true)) - stub(File).symlink?('symlink.js') {true} + allow(File).to receive(:symlink?).with('symlink.js').and_return(true) files = %w[symlink.js] assert_equal [], site.filter_entries(files) end should "not filter symlink entries when safe mode disabled" do - stub(File).symlink?('symlink.js') {true} + allow(File).to receive(:symlink?).with('symlink.js').and_return(true) files = %w[symlink.js] assert_equal files, @site.filter_entries(files) end diff --git a/test/test_generated_site.rb b/test/test_generated_site.rb index 519b8f3a..b3fe811f 100644 --- a/test/test_generated_site.rb +++ b/test/test_generated_site.rb @@ -4,11 +4,9 @@ class TestGeneratedSite < JekyllUnitTest context "generated sites" do setup do clear_dest - stub(Jekyll).configuration do - Jekyll::Configuration::DEFAULTS.merge({'source' => source_dir, 'destination' => dest_dir}) - end + config = Jekyll::Configuration::DEFAULTS.merge({'source' => source_dir, 'destination' => dest_dir}) - @site = Site.new(Jekyll.configuration) + @site = fixture_site config @site.process @index = File.read(dest_dir('index.html')) end @@ -59,11 +57,8 @@ OUTPUT context "generating limited posts" do setup do clear_dest - stub(Jekyll).configuration do - Jekyll::Configuration::DEFAULTS.merge({'source' => source_dir, 'destination' => dest_dir, 'limit_posts' => 5}) - end - - @site = Site.new(Jekyll.configuration) + config = Jekyll::Configuration::DEFAULTS.merge({'source' => source_dir, 'destination' => dest_dir, 'limit_posts' => 5}) + @site = fixture_site config @site.process @index = File.read(dest_dir('index.html')) end @@ -75,21 +70,17 @@ OUTPUT should "ensure limit posts is 0 or more" do assert_raises ArgumentError do clear_dest - stub(Jekyll).configuration do - Jekyll::Configuration::DEFAULTS.merge({'source' => source_dir, 'destination' => dest_dir, 'limit_posts' => -1}) - end + config = Jekyll::Configuration::DEFAULTS.merge({'source' => source_dir, 'destination' => dest_dir, 'limit_posts' => -1}) - @site = Site.new(Jekyll.configuration) + @site = fixture_site config end end should "acceptable limit post is 0" do clear_dest - stub(Jekyll).configuration do - Jekyll::Configuration::DEFAULTS.merge({'source' => source_dir, 'destination' => dest_dir, 'limit_posts' => 0}) - end + config = Jekyll::Configuration::DEFAULTS.merge({'source' => source_dir, 'destination' => dest_dir, 'limit_posts' => 0}) - assert Site.new(Jekyll.configuration), "Couldn't create a site with the given limit_posts." + assert Site.new(config), "Couldn't create a site with the given limit_posts." end end end diff --git a/test/test_layout_reader.rb b/test/test_layout_reader.rb index fc2f1fc3..88f35220 100644 --- a/test/test_layout_reader.rb +++ b/test/test_layout_reader.rb @@ -3,10 +3,8 @@ require 'helper' class TestLayoutReader < JekyllUnitTest context "reading layouts" do setup do - stub(Jekyll).configuration do - Jekyll::Configuration::DEFAULTS.merge({'source' => source_dir, 'destination' => dest_dir}) - end - @site = Site.new(Jekyll.configuration) + config = Jekyll::Configuration::DEFAULTS.merge({'source' => source_dir, 'destination' => dest_dir}) + @site = fixture_site config end should "read layouts" do @@ -22,8 +20,8 @@ class TestLayoutReader < JekyllUnitTest context "when a _layouts directory exists in CWD" do setup do - stub(File).directory? { true } - stub(Dir).pwd { source_dir("blah") } + allow(File).to receive(:directory?).and_return(true) + allow(Dir).to receive(:pwd).and_return(source_dir("blah")) end should "know to use the layout directory relative to CWD" do diff --git a/test/test_log_adapter.rb b/test/test_log_adapter.rb index 99b243bc..dee5df3e 100644 --- a/test/test_log_adapter.rb +++ b/test/test_log_adapter.rb @@ -22,7 +22,7 @@ class TestLogAdapter < JekyllUnitTest should "call #debug on writer return true" do writer = LoggerDouble.new logger = Jekyll::LogAdapter.new(writer) - stub(writer).debug('topic '.rjust(20) + 'log message') { true } + allow(writer).to receive(:debug).with('topic '.rjust(20) + 'log message').and_return(true) assert logger.debug('topic', 'log message') end end @@ -31,7 +31,7 @@ class TestLogAdapter < JekyllUnitTest should "call #info on writer return true" do writer = LoggerDouble.new logger = Jekyll::LogAdapter.new(writer) - stub(writer).info('topic '.rjust(20) + 'log message') { true } + allow(writer).to receive(:info).with('topic '.rjust(20) + 'log message').and_return(true) assert logger.info('topic', 'log message') end end @@ -40,7 +40,7 @@ class TestLogAdapter < JekyllUnitTest should "call #warn on writer return true" do writer = LoggerDouble.new logger = Jekyll::LogAdapter.new(writer) - stub(writer).warn('topic '.rjust(20) + 'log message') { true } + allow(writer).to receive(:warn).with('topic '.rjust(20) + 'log message').and_return(true) assert logger.warn('topic', 'log message') end end @@ -49,7 +49,7 @@ class TestLogAdapter < JekyllUnitTest should "call #error on writer return true" do writer = LoggerDouble.new logger = Jekyll::LogAdapter.new(writer) - stub(writer).error('topic '.rjust(20) + 'log message') { true } + allow(writer).to receive(:error).with('topic '.rjust(20) + 'log message').and_return(true) assert logger.error('topic', 'log message') end end @@ -57,7 +57,7 @@ class TestLogAdapter < JekyllUnitTest context "#abort_with" do should "call #error and abort" do logger = Jekyll::LogAdapter.new(LoggerDouble.new) - stub(logger).error('topic', 'log message') { true } + allow(logger).to receive(:error).with('topic', 'log message').and_return(true) assert_raises(SystemExit) { logger.abort_with('topic', 'log message') } end end diff --git a/test/test_new_command.rb b/test/test_new_command.rb index 2e0fd45c..7321b462 100644 --- a/test/test_new_command.rb +++ b/test/test_new_command.rb @@ -55,7 +55,7 @@ class TestNewCommand < JekyllUnitTest end stubbed_date = '2013-01-01' - stub.instance_of(Time).strftime { stubbed_date } + allow_any_instance_of(Time).to receive(:strftime) { stubbed_date } erb_template_files.each do |f| f.chomp! '.erb' diff --git a/test/test_path_sanitization.rb b/test/test_path_sanitization.rb index 2a3182e3..b04a2bad 100644 --- a/test/test_path_sanitization.rb +++ b/test/test_path_sanitization.rb @@ -5,7 +5,7 @@ class TestPathSanitization < JekyllUnitTest setup do @source = "C:/Users/xmr/Desktop/mpc-hc.org" @dest = "./_site/" - stub(Dir).pwd { "C:/Users/xmr/Desktop/mpc-hc.org" } + allow(Dir).to receive(:pwd).and_return("C:/Users/xmr/Desktop/mpc-hc.org") end should "strip drive name from path" do assert_equal "C:/Users/xmr/Desktop/mpc-hc.org/_site", Jekyll.sanitized_path(@source, @dest) diff --git a/test/test_related_posts.rb b/test/test_related_posts.rb index 645f2bfb..42c58279 100644 --- a/test/test_related_posts.rb +++ b/test/test_related_posts.rb @@ -3,11 +3,7 @@ require 'helper' class TestRelatedPosts < JekyllUnitTest context "building related posts without lsi" do setup do - stub(Jekyll).configuration do - Jekyll::Configuration::DEFAULTS.merge({'source' => source_dir, - 'destination' => dest_dir}) - end - @site = Site.new(Jekyll.configuration) + @site = fixture_site end should "use the most recent posts for related posts" do @@ -24,23 +20,17 @@ class TestRelatedPosts < JekyllUnitTest context "building related posts with lsi" do setup do - stub(Jekyll).configuration do - Jekyll::Configuration::DEFAULTS.merge({'source' => source_dir, - 'destination' => dest_dir, - 'lsi' => true}) - end - any_instance_of(Jekyll::RelatedPosts) { |i| stub(i).display } - @site = Site.new(Jekyll.configuration) + allow_any_instance_of(Jekyll::RelatedPosts).to receive(:display) + @site = fixture_site({"lsi" => true}) end should "use lsi for the related posts" do @site.reset @site.read require 'classifier-reborn' - any_instance_of(::ClassifierReborn::LSI) do |c| - stub(c).find_related { @site.posts[-1..-9] } - stub(c).build_index - end + allow_any_instance_of(::ClassifierReborn::LSI).to receive(:find_related).and_return(@site.posts[-1..-9]) + allow_any_instance_of(::ClassifierReborn::LSI).to receive(:build_index) + assert_equal @site.posts[-1..-9], Jekyll::RelatedPosts.new(@site.posts.last).build end end diff --git a/test/test_site.rb b/test/test_site.rb index 76ce9ce1..4bc7ddb2 100644 --- a/test/test_site.rb +++ b/test/test_site.rb @@ -162,7 +162,8 @@ class TestSite < JekyllUnitTest end should "sort pages alphabetically" do - stub.proxy(Dir).entries { |entries| entries.reverse } + method = Dir.method(:entries) + allow(Dir).to receive(:entries) { |*args, &block| method.call(*args, &block).reverse } @site.process # files in symlinked directories may appear twice sorted_pages = %w( diff --git a/test/test_tags.rb b/test/test_tags.rb index 4db4ab85..0460f3f6 100644 --- a/test/test_tags.rb +++ b/test/test_tags.rb @@ -5,12 +5,7 @@ require 'helper' class TestTags < JekyllUnitTest def create_post(content, override = {}, converter_class = Jekyll::Converters::Markdown) - stub(Jekyll).configuration do - site_configuration({ - "highlighter" => "rouge" - }.merge(override)) - end - site = Site.new(Jekyll.configuration) + site = fixture_site({"highlighter" => "rouge"}.merge(override)) if override['read_posts'] site.read_posts('') @@ -645,11 +640,7 @@ CONTENT context "include tag with variable and liquid filters" do setup do - stub(Jekyll).configuration do - site_configuration({'pygments' => true}) - end - - site = Site.new(Jekyll.configuration) + site = fixture_site({'pygments' => true}) post = Post.new(site, source_dir, '', "2013-12-17-include-variable-filters.markdown") layouts = { "default" => Layout.new(site, source_dir('_layouts'), "simple.html")} post.render(layouts, {"site" => {"posts" => []}}) @@ -681,11 +672,7 @@ CONTENT context "relative include tag with variable and liquid filters" do setup do - stub(Jekyll).configuration do - site_configuration({'pygments' => true}) - end - - site = Site.new(Jekyll.configuration) + site = fixture_site('pygments' => true) post = Post.new(site, source_dir, '', "2014-09-02-relative-includes.markdown") layouts = { "default" => Layout.new(site, source_dir('_layouts'), "simple.html")} post.render(layouts, {"site" => {"posts" => []}})