tfwrapper 0.2.0.beta1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.gitignore +54 -0
- data/.rubocop.yml +22 -0
- data/ChangeLog.md +3 -0
- data/Gemfile +4 -0
- data/Guardfile +21 -0
- data/LICENSE +21 -0
- data/README.md +320 -0
- data/Rakefile +60 -0
- data/circle.yml +24 -0
- data/lib/tfwrapper/helpers.rb +81 -0
- data/lib/tfwrapper/raketasks.rb +357 -0
- data/lib/tfwrapper/version.rb +6 -0
- data/lib/tfwrapper.rb +8 -0
- data/spec/acceptance/acceptance_helpers.rb +99 -0
- data/spec/acceptance/acceptance_spec.rb +461 -0
- data/spec/acceptance/consulserver.rb +34 -0
- data/spec/fixtures/Rakefile +7 -0
- data/spec/fixtures/testOne.tf +22 -0
- data/spec/fixtures/testThree/Rakefile +32 -0
- data/spec/fixtures/testThree/bar/testThreeBar.tf +28 -0
- data/spec/fixtures/testThree/baz/testThreeBaz.tf +22 -0
- data/spec/fixtures/testThree/foo/testThreeFoo.tf +27 -0
- data/spec/fixtures/testTwo/Rakefile +9 -0
- data/spec/fixtures/testTwo/foo/bar/testTwo.tf +28 -0
- data/spec/spec_helper.rb +58 -0
- data/spec/unit/helpers_spec.rb +143 -0
- data/spec/unit/raketasks_spec.rb +851 -0
- data/tfwrapper.gemspec +61 -0
- metadata +419 -0
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,58 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'simplecov'
|
4
|
+
require 'simplecov-console'
|
5
|
+
require 'rspec_junit_formatter'
|
6
|
+
|
7
|
+
ENV['CONSUL_ADDR'] ||= '127.0.0.1:8500'
|
8
|
+
ENV['CONSUL_URL'] ||= "http://#{ENV['CONSUL_ADDR']}"
|
9
|
+
|
10
|
+
# for naming coverage and test results in CircleCI by ruby version tested
|
11
|
+
dir_suffix = ''
|
12
|
+
if ENV['GEM_HOME']
|
13
|
+
ver = File.basename(ENV['GEM_HOME'])
|
14
|
+
dir_suffix = "-#{ver}"
|
15
|
+
end
|
16
|
+
|
17
|
+
# for storing artifacts in the right place for CircleCI
|
18
|
+
if ENV['CIRCLE_ARTIFACTS']
|
19
|
+
dir = File.join(ENV['CIRCLE_ARTIFACTS'], "coverage#{dir_suffix}")
|
20
|
+
SimpleCov.coverage_dir(dir)
|
21
|
+
end
|
22
|
+
|
23
|
+
SimpleCov.formatter = SimpleCov::Formatter::MultiFormatter.new(
|
24
|
+
[SimpleCov::Formatter::HTMLFormatter, SimpleCov::Formatter::Console]
|
25
|
+
)
|
26
|
+
|
27
|
+
SimpleCov.start do
|
28
|
+
add_filter '/vendor/'
|
29
|
+
add_filter '/spec/'
|
30
|
+
end
|
31
|
+
|
32
|
+
$LOAD_PATH.unshift File.expand_path('../lib', __FILE__)
|
33
|
+
|
34
|
+
RSpec.configure do |config|
|
35
|
+
# moved from .rspec to interpolate $CIRCLE_ARTIFACTS as output directory
|
36
|
+
# see: https://circleci.com/docs/build-artifacts and
|
37
|
+
# http://blog.circleci.com/build-artifacts/
|
38
|
+
# and also use CircleCI Junit parsing:
|
39
|
+
# http://blog.circleci.com/announcing-detailed-test-failure-reporting/
|
40
|
+
if ENV.key?('CIRCLE_ARTIFACTS')
|
41
|
+
junit_results_path = "#{ENV['CIRCLE_TEST_REPORTS']}/rspec/results"\
|
42
|
+
"#{dir_suffix}.xml"
|
43
|
+
html_results_path = "#{ENV['CIRCLE_TEST_REPORTS']}/rspec/results"\
|
44
|
+
"#{dir_suffix}.html"
|
45
|
+
else
|
46
|
+
junit_results_path = 'results/results.xml'
|
47
|
+
html_results_path = 'results/results.html'
|
48
|
+
end
|
49
|
+
config.color = true
|
50
|
+
config.order = :random
|
51
|
+
# documentation format
|
52
|
+
config.add_formatter(:documentation)
|
53
|
+
# HTML format
|
54
|
+
# @see https://github.com/rspec/rspec-core/blob/v2.14.8/lib/rspec/core/configuration.rb#L1086
|
55
|
+
config.add_formatter(:html, html_results_path)
|
56
|
+
# JUnit results
|
57
|
+
config.add_formatter('RspecJunitFormatter', junit_results_path)
|
58
|
+
end
|
@@ -0,0 +1,143 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'spec_helper'
|
4
|
+
require 'tfwrapper/helpers'
|
5
|
+
|
6
|
+
describe TFWrapper::Helpers do
|
7
|
+
describe '#run_cmd' do
|
8
|
+
it 'doesnt raise if command exits 0' do
|
9
|
+
res = `echo -n 'myout'; exit 0`
|
10
|
+
allow(TFWrapper::Helpers).to receive(:`).and_return(res)
|
11
|
+
|
12
|
+
expect(STDOUT).to receive(:puts).once.with('Running command: foo bar')
|
13
|
+
expect(TFWrapper::Helpers).to receive(:`).once.with('foo bar')
|
14
|
+
TFWrapper::Helpers.run_cmd('foo bar')
|
15
|
+
end
|
16
|
+
it 'raises if command exits non-0' do
|
17
|
+
res = `echo -n 'myout'; exit 23`
|
18
|
+
allow(TFWrapper::Helpers).to receive(:`).and_return(res)
|
19
|
+
|
20
|
+
expect(STDOUT).to receive(:puts).once.with('Running command: foo bar')
|
21
|
+
expect(TFWrapper::Helpers).to receive(:`).once.with('foo bar')
|
22
|
+
expect(STDOUT).to receive(:puts).once.with('Command exited 23:')
|
23
|
+
expect(STDOUT).to receive(:puts).once.with('myout')
|
24
|
+
expect { TFWrapper::Helpers.run_cmd('foo bar') }
|
25
|
+
.to raise_error StandardError, 'ERROR: Command failed: foo bar'
|
26
|
+
end
|
27
|
+
end
|
28
|
+
describe '#run_cmd_stream_output' do
|
29
|
+
# test logic for this was inspired by:
|
30
|
+
# http://rxr.whitequark.org/rubinius/source/spec/ruby/core/io/select_spec.rb
|
31
|
+
before :each do
|
32
|
+
@outerrpipe_r, @outerrpipe_w = IO.pipe
|
33
|
+
@inpipe_r, @inpipe_w = IO.pipe
|
34
|
+
end
|
35
|
+
after :each do
|
36
|
+
@outerrpipe_r.close unless @outerrpipe_r.closed?
|
37
|
+
@outerrpipe_w.close unless @outerrpipe_w.closed?
|
38
|
+
@inpipe_r.close unless @inpipe_r.closed?
|
39
|
+
@inpipe_w.close unless @inpipe_w.closed?
|
40
|
+
end
|
41
|
+
context 'success' do
|
42
|
+
it 'prints and returns output' do
|
43
|
+
dbl_wait_thread = double(Thread)
|
44
|
+
@outerrpipe_w.write('mystdout')
|
45
|
+
@outerrpipe_w.close
|
46
|
+
es = double('exitstatus', exitstatus: 0)
|
47
|
+
allow(dbl_wait_thread).to receive(:value).and_return(es)
|
48
|
+
allow($stdout).to receive(:sync).and_return(false)
|
49
|
+
allow($stdout).to receive(:sync=).with(true)
|
50
|
+
allow(Open3).to receive(:popen2e).and_yield(
|
51
|
+
@inpipe_w, @outerrpipe_r, dbl_wait_thread
|
52
|
+
)
|
53
|
+
|
54
|
+
expect(Open3).to receive(:popen2e)
|
55
|
+
.once.with('foo bar', chdir: '/foo')
|
56
|
+
expect(STDOUT).to receive(:puts).once.with('mystdout')
|
57
|
+
expect($stdout).to receive(:sync=).once.with(true)
|
58
|
+
expect($stdout).to receive(:sync=).once.with(false)
|
59
|
+
expect(TFWrapper::Helpers.run_cmd_stream_output('foo bar', '/foo'))
|
60
|
+
.to eq(['mystdout', 0])
|
61
|
+
end
|
62
|
+
end
|
63
|
+
context 'IOError' do
|
64
|
+
it 'handles IOErrors gracefully' do
|
65
|
+
dbl_wait_thread = double(Thread)
|
66
|
+
@outerrpipe_w.close
|
67
|
+
@outerrpipe_r.close
|
68
|
+
es = double('exitstatus', exitstatus: 0)
|
69
|
+
allow(dbl_wait_thread).to receive(:value).and_return(es)
|
70
|
+
allow($stdout).to receive(:sync).and_return(false)
|
71
|
+
allow($stdout).to receive(:sync=).with(true)
|
72
|
+
allow(Open3).to receive(:popen2e).and_yield(
|
73
|
+
@inpipe_w, @outerrpipe_r, dbl_wait_thread
|
74
|
+
)
|
75
|
+
|
76
|
+
expect(Open3).to receive(:popen2e)
|
77
|
+
.once.with('foo bar', chdir: '/foo')
|
78
|
+
expect(STDERR).to receive(:puts).once.with('IOError: closed stream')
|
79
|
+
expect($stdout).to receive(:sync=).once.with(true)
|
80
|
+
expect($stdout).to receive(:sync=).once.with(false)
|
81
|
+
expect(TFWrapper::Helpers.run_cmd_stream_output('foo bar', '/foo'))
|
82
|
+
.to eq(['', 0])
|
83
|
+
end
|
84
|
+
end
|
85
|
+
context 'failure' do
|
86
|
+
it 'returns the non-zero exit code' do
|
87
|
+
dbl_wait_thread = double(Thread)
|
88
|
+
@outerrpipe_w.write("mystdout\n")
|
89
|
+
@outerrpipe_w.write("STDERR\n")
|
90
|
+
@outerrpipe_w.close
|
91
|
+
es = double('exitstatus', exitstatus: 23)
|
92
|
+
allow(dbl_wait_thread).to receive(:value).and_return(es)
|
93
|
+
allow($stdout).to receive(:sync).and_return(false)
|
94
|
+
allow($stdout).to receive(:sync=).with(true)
|
95
|
+
allow(Open3).to receive(:popen2e).and_yield(
|
96
|
+
@inpipe_w, @outerrpipe_r, dbl_wait_thread
|
97
|
+
)
|
98
|
+
|
99
|
+
expect(Open3).to receive(:popen2e)
|
100
|
+
.once.with('foo bar', chdir: '/foo')
|
101
|
+
expect(STDOUT).to receive(:puts).once.with("mystdout\n")
|
102
|
+
expect(STDOUT).to receive(:puts).once.with("STDERR\n")
|
103
|
+
expect($stdout).to receive(:sync=).once.with(true)
|
104
|
+
expect($stdout).to receive(:sync=).once.with(false)
|
105
|
+
expect(TFWrapper::Helpers.run_cmd_stream_output('foo bar', '/foo'))
|
106
|
+
.to eq(["mystdout\nSTDERR\n", 23])
|
107
|
+
end
|
108
|
+
end
|
109
|
+
end
|
110
|
+
describe '#check_env_vars' do
|
111
|
+
it 'returns nil if vars present' do
|
112
|
+
ENV['foo'] = 'fooval'
|
113
|
+
ENV['bar'] = 'barval'
|
114
|
+
expect(TFWrapper::Helpers.check_env_vars(%w[foo bar])).to be_nil
|
115
|
+
ENV.delete('foo')
|
116
|
+
ENV.delete('bar')
|
117
|
+
end
|
118
|
+
it 'exits if not present' do
|
119
|
+
ENV.delete('foo')
|
120
|
+
ENV.delete('bar')
|
121
|
+
expect(STDOUT).to receive(:puts)
|
122
|
+
.with('ERROR: Environment variable \'foo\' must be set.')
|
123
|
+
expect(STDOUT).to receive(:puts)
|
124
|
+
.with('ERROR: Environment variable \'bar\' must be set.')
|
125
|
+
expect { TFWrapper::Helpers.check_env_vars(%w[foo bar]) }
|
126
|
+
.to raise_error StandardError, 'Missing or empty environment ' \
|
127
|
+
'variables: ["foo", "bar"]'
|
128
|
+
end
|
129
|
+
it 'exits if empty' do
|
130
|
+
ENV['foo'] = ''
|
131
|
+
ENV['bar'] = ' '
|
132
|
+
expect(STDOUT).to receive(:puts)
|
133
|
+
.with("ERROR: Environment variable 'foo' must not be empty.")
|
134
|
+
expect(STDOUT).to receive(:puts)
|
135
|
+
.with("ERROR: Environment variable 'bar' must not be empty.")
|
136
|
+
expect { TFWrapper::Helpers.check_env_vars(%w[foo bar]) }
|
137
|
+
.to raise_error StandardError, 'Missing or empty environment ' \
|
138
|
+
'variables: ["foo", "bar"]'
|
139
|
+
ENV.delete('foo')
|
140
|
+
ENV.delete('bar')
|
141
|
+
end
|
142
|
+
end
|
143
|
+
end
|