From ca19aa844dd81800d206d7af60ab81fc47e07a64 Mon Sep 17 00:00:00 2001 From: Beth Skurrie Date: Fri, 13 Apr 2018 16:49:29 +1000 Subject: [PATCH] feat: allow --out FILE to be specified for the output from pact verify --- lib/pact/cli.rb | 1 + lib/pact/cli/run_pact_verification.rb | 5 ++- lib/pact/provider/pact_spec_runner.rb | 38 ++++++++++++-------- spec/integration/cli_spec.rb | 50 +++++++++++++++++++++++++-- 4 files changed, 74 insertions(+), 20 deletions(-) diff --git a/lib/pact/cli.rb b/lib/pact/cli.rb index ffa32968..936a5f71 100755 --- a/lib/pact/cli.rb +++ b/lib/pact/cli.rb @@ -17,6 +17,7 @@ class CLI < Thor method_option :description, aliases: "-d", desc: "Interaction description filter" method_option :provider_state, aliases: "-s", desc: "Provider state filter" method_option :format, aliases: "-f", banner: "FORMATTER", desc: "RSpec formatter. Defaults to custom Pact formatter. [j]son may also be used." + method_option :out, aliases: "-o", banner: "FILE", desc: "Write output to a file instead of $stdout." def verify require 'pact/cli/run_pact_verification' diff --git a/lib/pact/cli/run_pact_verification.rb b/lib/pact/cli/run_pact_verification.rb index e794a299..5de5e464 100644 --- a/lib/pact/cli/run_pact_verification.rb +++ b/lib/pact/cli/run_pact_verification.rb @@ -14,7 +14,6 @@ def self.call options new(options).call end - def call initialize_rspec setup_load_path @@ -71,10 +70,10 @@ def pact_spec_options { full_backtrace: options[:backtrace], criteria: SpecCriteria.call(options), - format: options[:format] + format: options[:format], + out: options[:out] } end - end end end diff --git a/lib/pact/provider/pact_spec_runner.rb b/lib/pact/provider/pact_spec_runner.rb index 5c9c4dd0..b219dcbc 100644 --- a/lib/pact/provider/pact_spec_runner.rb +++ b/lib/pact/provider/pact_spec_runner.rb @@ -62,21 +62,7 @@ def configure_rspec config.output_stream = Pact.configuration.output_stream end - Pact::RSpec.with_rspec_3 do - ::RSpec.configuration.add_formatter Pact::Provider::RSpec::PactBrokerFormatter, StringIO.new - end - - if options[:format] - ::RSpec.configuration.add_formatter options[:format] - # Don't want to mess up the JSON parsing with messages to stdout, so send it to stderr - Pact.configuration.output_stream = Pact.configuration.error_stream - else - # Sometimes the formatter set in the cli.rb get set with an output of StringIO.. don't know why - formatter_class = Pact::RSpec.formatter_class - pact_formatter = ::RSpec.configuration.formatters.find {|f| f.class == formatter_class && f.output == ::RSpec.configuration.output_stream} - ::RSpec.configuration.add_formatter formatter_class unless pact_formatter - end - ::RSpec.configuration.full_backtrace = @options[:full_backtrace] + configure_output config.before(:suite) do # Preload app before suite so the classes loaded in memory are consistent for @@ -138,6 +124,28 @@ def initialize_specs end end + def configure_output + Pact::RSpec.with_rspec_3 do + ::RSpec.configuration.add_formatter Pact::Provider::RSpec::PactBrokerFormatter, StringIO.new + end + + output = options[:out] || Pact.configuration.output_stream + if options[:format] + ::RSpec.configuration.add_formatter options[:format], output + if !options[:out] + # Don't want to mess up the JSON parsing with messages to stdout, so send it to stderr + Pact.configuration.output_stream = Pact.configuration.error_stream + end + else + # Sometimes the formatter set in the cli.rb get set with an output of StringIO.. don't know why + formatter_class = Pact::RSpec.formatter_class + pact_formatter = ::RSpec.configuration.formatters.find {|f| f.class == formatter_class && f.output == ::RSpec.configuration.output_stream} + ::RSpec.configuration.add_formatter(formatter_class, output) unless pact_formatter + end + + ::RSpec.configuration.full_backtrace = @options[:full_backtrace] + end + def ordered_pact_json(pact_json) return pact_json if Pact.configuration.interactions_replay_order == :recorded diff --git a/spec/integration/cli_spec.rb b/spec/integration/cli_spec.rb index 454d5d4a..baa27864 100644 --- a/spec/integration/cli_spec.rb +++ b/spec/integration/cli_spec.rb @@ -5,6 +5,8 @@ include Pact::Support::CLI + let(:expected_test_output) { "2 interactions, 0 failures" } + describe "running a failing test with --backtrace" do let(:command) do [ @@ -32,7 +34,29 @@ end end - describe "running with json output" do + describe "running with json output and an output path specified" do + before do + FileUtils.rm_rf 'tmp/foo.json' + end + + let(:command) do + [ + "bundle exec bin/pact verify", + "--pact-uri spec/support/test_app_pass.json", + "--pact-helper spec/support/pact_helper.rb", + "--format json", + "--out tmp/foo.json" + ].join(" ") + end + + it "formats the output as json to the specified file" do + output = `#{command}` + expect(JSON.parse(File.read('tmp/foo.json'))["examples"].size).to be > 1 + expect(output).to_not include expected_test_output + end + end + + describe "running with json output and no output path specified" do let(:command) do [ "bundle exec bin/pact verify", @@ -41,9 +65,31 @@ "--format json" ].join(" ") end - it "formats the output as json" do + + it "formats the output as json to stdout" do output = `#{command}` expect(JSON.parse(output)["examples"].size).to be > 1 end end + + describe "running with an output path specified" do + before do + FileUtils.rm_rf 'tmp/foo.out' + end + + let(:command) do + [ + "bundle exec bin/pact verify", + "--pact-uri spec/support/test_app_pass.json", + "--pact-helper spec/support/pact_helper.rb", + "--out tmp/foo.out" + ].join(" ") + end + + it "writes the output to the specified path and not to stdout" do + output = `#{command}` + expect(File.read('tmp/foo.out')).to include expected_test_output + expect(output).to_not include expected_test_output + end + end end