Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
34 changes: 34 additions & 0 deletions lib/octocatalog-diff/cli/options/save_catalog.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
# frozen_string_literal: true

# Allow catalogs to be saved to a file before they are diff'd.
# @param parser [OptionParser object] The OptionParser argument
# @param options [Hash] Options hash being constructed; this is modified in this method.
OctocatalogDiff::Cli::Options::Option.newoption(:save_catalog) do
has_weight 155

def parse(parser, options)
OctocatalogDiff::Cli::Options.option_globally_or_per_branch(
parser: parser,
options: options,
cli_name: 'save-catalog',
option_name: 'save_catalog',
desc: 'Save intermediate catalogs into files',
datatype: '',
validator: lambda do |catalog_file|
target_dir = File.dirname(catalog_file)
unless File.directory?(target_dir)
raise Errno::ENOENT, "Cannot save catalog to #{catalog_file} because parent directory does not exist"
end
if File.exist?(catalog_file) && !File.file?(catalog_file)
raise ArgumentError, "Cannot overwrite #{catalog_file} which is not a file"
end
true
end,
post_process: lambda do |opts|
if opts[:to_save_catalog] && opts[:to_save_catalog] == opts[:from_save_catalog]
raise ArgumentError, 'Cannot use the same file for --to-save-catalog and --from-save-catalog'
end
end
)
end
end
5 changes: 5 additions & 0 deletions lib/octocatalog-diff/util/catalogs.rb
Original file line number Diff line number Diff line change
Expand Up @@ -197,6 +197,11 @@ def add_parallel_result(result, parallel_catalog_obj, key_task_tuple)
if catalog.valid?
# The catalog was successfully compiled.
result[key] = parallel_catalog_obj.output

if task.args[:save_catalog]
File.open(task.args[:save_catalog], 'w') { |f| f.write(catalog.catalog_json) }
@logger.debug "Saved catalog to #{task.args[:save_catalog]}"
end
else
# The catalog failed, but a catalog object was returned so that better error reporting
# can take place. In this error reporting, we will replace 'Error:' with '[Puppet Error]'
Expand Down
70 changes: 70 additions & 0 deletions spec/octocatalog-diff/tests/cli/options/save_catalog_spec.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,70 @@
# frozen_string_literal: true

require_relative '../options_helper'

describe OctocatalogDiff::Cli::Options do
describe '#opt_save_catalog' do
it 'should raise error if catalog parent directory does not exist' do
args = [
'--to-save-catalog',
OctocatalogDiff::Spec.fixture_path('non/exists/catalog.json')
]
expect { run_optparse(args) }.to raise_error(Errno::ENOENT, /parent directory does not exist/)
end

it 'should raise error if catalog exists but is not a file' do
args = [
'--to-save-catalog',
OctocatalogDiff::Spec.fixture_path('repos/default')
]
expect { run_optparse(args) }.to raise_error(ArgumentError, /Cannot overwrite/)
end

it 'should not raise error if catalog file already exists' do
args = [
'--to-save-catalog',
OctocatalogDiff::Spec.fixture_path('catalogs/catalog-1.json')
]
result = run_optparse(args)
expect(result[:to_save_catalog]).to eq(OctocatalogDiff::Spec.fixture_path('catalogs/catalog-1.json'))
end

it 'should not raise error if catalog file does not exist' do
args = [
'--to-save-catalog',
OctocatalogDiff::Spec.fixture_path('catalogs/brand-new-catalog-1.json')
]
result = run_optparse(args)
expect(result[:to_save_catalog]).to eq(OctocatalogDiff::Spec.fixture_path('catalogs/brand-new-catalog-1.json'))
end

it 'should raise error if --to-save-catalog == --from-save-catalog' do
args = [
'--to-save-catalog',
OctocatalogDiff::Spec.fixture_path('catalogs/brand-new-catalog-1.json'),
'--from-save-catalog',
OctocatalogDiff::Spec.fixture_path('catalogs/brand-new-catalog-1.json')
]
expect { run_optparse(args) }.to raise_error(ArgumentError, /Cannot use the same file for/)
end

it 'should not raise error if --to-save-catalog and --from-save-catalog are both nil' do
args = []
result = run_optparse(args)
expect(result[:to_save_catalog]).to be_nil
expect(result[:from_save_catalog]).to be_nil
end

it 'should set option correctly' do
args = [
'--to-save-catalog',
OctocatalogDiff::Spec.fixture_path('catalogs/brand-new-catalog-1.json'),
'--from-save-catalog',
OctocatalogDiff::Spec.fixture_path('catalogs/brand-new-catalog-2.json')
]
result = run_optparse(args)
expect(result[:to_save_catalog]).to eq(OctocatalogDiff::Spec.fixture_path('catalogs/brand-new-catalog-1.json'))
expect(result[:from_save_catalog]).to eq(OctocatalogDiff::Spec.fixture_path('catalogs/brand-new-catalog-2.json'))
end
end
end
21 changes: 21 additions & 0 deletions spec/octocatalog-diff/tests/util/catalogs_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -330,6 +330,27 @@ def valid?
expect(result[:from]).to eq('blank')
end

context 'saving the catalog' do
before(:each) { @tmpdir = Dir.mktmpdir }
after(:each) { OctocatalogDiff::Spec.clean_up_tmpdir(@tmpdir) }

it 'should save the catalog when requested' do
filename = File.join(@tmpdir, 'catalog.json')
options = {
to_catalog: OctocatalogDiff::Spec.fixture_path('catalogs/tiny-catalog.json'),
from_catalog: OctocatalogDiff::Spec.fixture_path('catalogs/catalog-test-file.json'),
from_save_catalog: filename
}

logger, logger_str = OctocatalogDiff::Spec.setup_logger
testobj = OctocatalogDiff::Util::Catalogs.new(options, logger)
result = testobj.send(:build_catalog_parallelizer)

expect(logger_str.string).to match(Regexp.escape("Saved catalog to #{filename}"))
expect(File.read(filename)).to eq(result[:from].catalog_json)
end
end

it 'should format error and raise error when a catalog compile fails' do
error_lines = [
'Debug: You do not care about this',
Expand Down