puppet 6.13.0 → 6.14.0
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of puppet might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/CONTRIBUTING.md +7 -13
- data/Gemfile.lock +6 -6
- data/README.md +15 -22
- data/lib/puppet.rb +1 -1
- data/lib/puppet/application/agent.rb +9 -11
- data/lib/puppet/application/describe.rb +7 -5
- data/lib/puppet/application/device.rb +2 -2
- data/lib/puppet/application/filebucket.rb +14 -1
- data/lib/puppet/application/ssl.rb +1 -1
- data/lib/puppet/configurer.rb +30 -41
- data/lib/puppet/configurer/plugin_handler.rb +10 -1
- data/lib/puppet/defaults.rb +7 -1
- data/lib/puppet/face/plugin.rb +1 -1
- data/lib/puppet/functions/eyaml_lookup_key.rb +13 -8
- data/lib/puppet/http.rb +1 -0
- data/lib/puppet/http/client.rb +69 -34
- data/lib/puppet/http/resolver/server_list.rb +2 -2
- data/lib/puppet/http/resolver/settings.rb +1 -1
- data/lib/puppet/http/resolver/srv.rb +1 -1
- data/lib/puppet/http/response.rb +6 -1
- data/lib/puppet/http/service.rb +30 -11
- data/lib/puppet/http/service/ca.rb +8 -8
- data/lib/puppet/http/service/compiler.rb +41 -10
- data/lib/puppet/http/service/file_server.rb +40 -20
- data/lib/puppet/http/service/report.rb +12 -15
- data/lib/puppet/http/session.rb +39 -1
- data/lib/puppet/indirector/catalog/rest.rb +33 -0
- data/lib/puppet/indirector/facts/rest.rb +41 -0
- data/lib/puppet/indirector/file_content/rest.rb +30 -0
- data/lib/puppet/indirector/file_metadata/rest.rb +50 -0
- data/lib/puppet/indirector/node/rest.rb +23 -0
- data/lib/puppet/indirector/report/rest.rb +19 -0
- data/lib/puppet/indirector/rest.rb +6 -0
- data/lib/puppet/indirector/status/rest.rb +17 -0
- data/lib/puppet/loaders.rb +6 -0
- data/lib/puppet/network/http/base_pool.rb +1 -1
- data/lib/puppet/network/http/pool.rb +6 -1
- data/lib/puppet/provider/group/groupadd.rb +9 -4
- data/lib/puppet/runtime.rb +8 -1
- data/lib/puppet/settings.rb +2 -0
- data/lib/puppet/settings/http_extra_headers_setting.rb +25 -0
- data/lib/puppet/ssl/state_machine.rb +4 -0
- data/lib/puppet/test/test_helper.rb +3 -1
- data/lib/puppet/type/file.rb +13 -0
- data/lib/puppet/type/file/source.rb +47 -58
- data/lib/puppet/version.rb +1 -1
- data/locales/puppet.pot +167 -160
- data/man/man5/puppet.conf.5 +11 -3
- data/man/man8/puppet-agent.8 +6 -6
- data/man/man8/puppet-apply.8 +1 -1
- data/man/man8/puppet-catalog.8 +1 -1
- data/man/man8/puppet-config.8 +1 -1
- data/man/man8/puppet-describe.8 +1 -1
- data/man/man8/puppet-device.8 +2 -2
- data/man/man8/puppet-doc.8 +1 -1
- data/man/man8/puppet-epp.8 +1 -1
- data/man/man8/puppet-facts.8 +1 -1
- data/man/man8/puppet-filebucket.8 +17 -2
- data/man/man8/puppet-generate.8 +1 -1
- data/man/man8/puppet-help.8 +1 -1
- data/man/man8/puppet-key.8 +1 -1
- data/man/man8/puppet-lookup.8 +1 -1
- data/man/man8/puppet-man.8 +1 -1
- data/man/man8/puppet-module.8 +1 -1
- data/man/man8/puppet-node.8 +1 -1
- data/man/man8/puppet-parser.8 +1 -1
- data/man/man8/puppet-plugin.8 +1 -1
- data/man/man8/puppet-report.8 +1 -1
- data/man/man8/puppet-resource.8 +1 -1
- data/man/man8/puppet-script.8 +1 -1
- data/man/man8/puppet-ssl.8 +2 -2
- data/man/man8/puppet-status.8 +1 -1
- data/man/man8/puppet.8 +2 -2
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_md5/should_fetch_if_not_on_the_local_disk.yml +1 -67
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_md5/should_not_update_if_content_on_disk_is_up-to-date.yml +1 -69
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_md5/should_update_if_content_differs_on_disk.yml +1 -69
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_mtime/should_fetch_if_mtime_is_older_on_disk.yml +1 -67
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_mtime/should_fetch_if_no_header_specified.yml +1 -65
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_mtime/should_fetch_if_not_on_the_local_disk.yml +1 -67
- data/spec/fixtures/vcr/cassettes/Puppet_Type_File/when_sourcing/from_http/using_mtime/should_not_update_if_mtime_is_newer_on_disk.yml +1 -67
- data/spec/integration/faces/plugin_spec.rb +3 -1
- data/spec/integration/http/client_spec.rb +11 -0
- data/spec/integration/network/http_pool_spec.rb +9 -1
- data/spec/unit/application/describe_spec.rb +88 -50
- data/spec/unit/configurer/plugin_handler_spec.rb +36 -19
- data/spec/unit/configurer_spec.rb +16 -14
- data/spec/unit/face/plugin_spec.rb +12 -10
- data/spec/unit/functions/lookup_spec.rb +13 -0
- data/spec/unit/http/client_spec.rb +172 -1
- data/spec/unit/http/resolver_spec.rb +14 -2
- data/spec/unit/http/response_spec.rb +69 -0
- data/spec/unit/http/service/ca_spec.rb +28 -9
- data/spec/unit/http/service/compiler_spec.rb +151 -24
- data/spec/unit/http/service/file_server_spec.rb +65 -8
- data/spec/unit/http/service/report_spec.rb +17 -8
- data/spec/unit/http/service_spec.rb +92 -3
- data/spec/unit/http/session_spec.rb +104 -1
- data/spec/unit/indirector/catalog/rest_spec.rb +59 -2
- data/spec/unit/indirector/facts/rest_spec.rb +79 -24
- data/spec/unit/indirector/file_content/rest_spec.rb +53 -2
- data/spec/unit/indirector/file_metadata/rest_spec.rb +109 -2
- data/spec/unit/indirector/node/rest_spec.rb +57 -2
- data/spec/unit/indirector/report/rest_spec.rb +58 -51
- data/spec/unit/indirector/resource/ral_spec.rb +7 -8
- data/spec/unit/indirector/status/rest_spec.rb +43 -2
- data/spec/unit/network/http/pool_spec.rb +57 -11
- data/spec/unit/provider/group/groupadd_spec.rb +22 -8
- data/spec/unit/settings/autosign_setting_spec.rb +1 -1
- data/spec/unit/settings/http_extra_headers_spec.rb +64 -0
- data/spec/unit/ssl/state_machine_spec.rb +10 -0
- data/spec/unit/transaction_spec.rb +0 -2
- data/spec/unit/type/file/ensure_spec.rb +1 -2
- data/spec/unit/type/file/source_spec.rb +86 -35
- data/spec/unit/util/at_fork_spec.rb +1 -0
- data/spec/unit/util/pidlock_spec.rb +36 -24
- metadata +7 -3
- data/COMMITTERS.md +0 -244
@@ -27,14 +27,6 @@ describe Puppet::HTTP::Service::FileServer do
|
|
27
27
|
|
28
28
|
subject.get_file_content(path: '/:mount/:path', environment: environment) { |data| }
|
29
29
|
end
|
30
|
-
|
31
|
-
it 'includes the X-Puppet-Profiling header when Puppet[:profile] is true' do
|
32
|
-
stub_request(:get, uri).with(headers: {'X-Puppet-Version' => /./, 'User-Agent' => /./, 'X-Puppet-Profiling' => 'true'})
|
33
|
-
|
34
|
-
Puppet[:profile] = true
|
35
|
-
|
36
|
-
subject.get_file_content(path: '/:mount/:path', environment: environment) { |data| }
|
37
|
-
end
|
38
30
|
end
|
39
31
|
|
40
32
|
context 'when routing to the file service' do
|
@@ -54,6 +46,16 @@ describe Puppet::HTTP::Service::FileServer do
|
|
54
46
|
let(:filemetadata) { Puppet::FileServing::Metadata.new(path) }
|
55
47
|
let(:request_path) { "/:mount/#{path}"}
|
56
48
|
|
49
|
+
it 'includes puppet headers set via the :http_extra_headers and :profile settings' do
|
50
|
+
stub_request(:get, url).with(headers: {'Example-Header' => 'real-thing', 'another' => 'thing', 'X-Puppet-Profiling' => 'true'}).
|
51
|
+
to_return(status: 200, body: filemetadata.render, headers: { 'Content-Type' => 'application/json' })
|
52
|
+
|
53
|
+
Puppet[:http_extra_headers] = 'Example-Header:real-thing,another:thing'
|
54
|
+
Puppet[:profile] = true
|
55
|
+
|
56
|
+
subject.get_file_metadata(path: request_path, environment: environment)
|
57
|
+
end
|
58
|
+
|
57
59
|
it 'submits a request for file metadata to the server' do
|
58
60
|
stub_request(:get, url).with(
|
59
61
|
headers: {'Accept'=>'application/json, application/x-msgpack, text/pson',}
|
@@ -117,6 +119,16 @@ describe Puppet::HTTP::Service::FileServer do
|
|
117
119
|
let(:formatter) { Puppet::Network::FormatHandler.format(:json) }
|
118
120
|
let(:request_path) { "/:mount/#{path}"}
|
119
121
|
|
122
|
+
it 'includes puppet headers set via the :http_extra_headers and :profile settings' do
|
123
|
+
stub_request(:get, url).with(headers: {'Example-Header' => 'real-thing', 'another' => 'thing', 'X-Puppet-Profiling' => 'true'}).
|
124
|
+
to_return(status: 200, body: formatter.render_multiple(filemetadatas), headers: { 'Content-Type' => 'application/json' })
|
125
|
+
|
126
|
+
Puppet[:http_extra_headers] = 'Example-Header:real-thing,another:thing'
|
127
|
+
Puppet[:profile] = true
|
128
|
+
|
129
|
+
subject.get_file_metadatas(path: request_path, environment: environment)
|
130
|
+
end
|
131
|
+
|
120
132
|
it 'submits a request for file metadata to the server' do
|
121
133
|
stub_request(:get, url).with(
|
122
134
|
headers: {'Accept'=>'application/json, application/x-msgpack, text/pson',}
|
@@ -188,6 +200,18 @@ describe Puppet::HTTP::Service::FileServer do
|
|
188
200
|
context 'getting file content' do
|
189
201
|
let(:uri) {"https://www.example.com:443/puppet/v3/file_content/:mount/:path?environment=testing"}
|
190
202
|
|
203
|
+
it 'includes puppet headers set via the :http_extra_headers and :profile settings' do
|
204
|
+
stub_request(:get, uri).with(headers: {'Example-Header' => 'real-thing', 'another' => 'thing', 'X-Puppet-Profiling' => 'true'}).
|
205
|
+
to_return(status: 200, body: "and beyond")
|
206
|
+
|
207
|
+
Puppet[:http_extra_headers] = 'Example-Header:real-thing,another:thing'
|
208
|
+
Puppet[:profile] = true
|
209
|
+
|
210
|
+
expect { |b|
|
211
|
+
subject.get_file_content(path: '/:mount/:path', environment: environment, &b)
|
212
|
+
}.to yield_with_args("and beyond")
|
213
|
+
end
|
214
|
+
|
191
215
|
it 'yields file content' do
|
192
216
|
stub_request(:get, uri).with do |request|
|
193
217
|
expect(request.headers).to include({'Accept' => 'application/octet-stream'})
|
@@ -216,4 +240,37 @@ describe Puppet::HTTP::Service::FileServer do
|
|
216
240
|
}.to raise_error(ArgumentError, 'Path must start with a slash')
|
217
241
|
end
|
218
242
|
end
|
243
|
+
|
244
|
+
context 'getting static file content' do
|
245
|
+
let(:code_id) { "0fc72115-adc6-4b1a-aa50-8f31b3ece440" }
|
246
|
+
let(:uri) { "https://www.example.com:443/puppet/v3/static_file_content/:mount/:path?environment=testing&code_id=#{code_id}"}
|
247
|
+
|
248
|
+
it 'yields file content' do
|
249
|
+
stub_request(:get, uri).with do |request|
|
250
|
+
expect(request.headers).to include({'Accept' => 'application/octet-stream'})
|
251
|
+
end.to_return(status: 200, body: "and beyond")
|
252
|
+
|
253
|
+
expect { |b|
|
254
|
+
subject.get_static_file_content(path: '/:mount/:path', environment: environment, code_id: code_id, &b)
|
255
|
+
}.to yield_with_args("and beyond")
|
256
|
+
end
|
257
|
+
|
258
|
+
it 'raises response error if unsuccessful' do
|
259
|
+
stub_request(:get, uri).to_return(status: [400, 'Bad Request'])
|
260
|
+
|
261
|
+
expect {
|
262
|
+
subject.get_static_file_content(path: '/:mount/:path', environment: environment, code_id: code_id) { |data| }
|
263
|
+
}.to raise_error do |err|
|
264
|
+
expect(err).to be_an_instance_of(Puppet::HTTP::ResponseError)
|
265
|
+
expect(err.message).to eq('Bad Request')
|
266
|
+
expect(err.response.code).to eq(400)
|
267
|
+
end
|
268
|
+
end
|
269
|
+
|
270
|
+
it 'raises response error if path is relative' do
|
271
|
+
expect {
|
272
|
+
subject.get_static_file_content(path: 'relative_path', environment: environment, code_id: code_id) { |data| }
|
273
|
+
}.to raise_error(ArgumentError, 'Path must start with a slash')
|
274
|
+
end
|
275
|
+
end
|
219
276
|
end
|
@@ -25,14 +25,6 @@ describe Puppet::HTTP::Service::Report do
|
|
25
25
|
|
26
26
|
subject.put_report('report', report, environment: environment)
|
27
27
|
end
|
28
|
-
|
29
|
-
it 'includes the X-Puppet-Profiling header when Puppet[:profile] is true' do
|
30
|
-
stub_request(:put, uri).with(headers: {'X-Puppet-Version' => /./, 'User-Agent' => /./, 'X-Puppet-Profiling' => 'true'})
|
31
|
-
|
32
|
-
Puppet[:profile] = true
|
33
|
-
|
34
|
-
subject.put_report('report', report, environment: environment)
|
35
|
-
end
|
36
28
|
end
|
37
29
|
|
38
30
|
context 'when routing to the report service' do
|
@@ -60,6 +52,15 @@ describe Puppet::HTTP::Service::Report do
|
|
60
52
|
context 'when submitting a report' do
|
61
53
|
let(:url) { "https://www.example.com/puppet/v3/report/infinity?environment=testing" }
|
62
54
|
|
55
|
+
it 'includes puppet headers set via the :http_extra_headers and :profile settings' do
|
56
|
+
stub_request(:put, url).with(headers: {'Example-Header' => 'real-thing', 'another' => 'thing', 'X-Puppet-Profiling' => 'true'})
|
57
|
+
|
58
|
+
Puppet[:http_extra_headers] = 'Example-Header:real-thing,another:thing'
|
59
|
+
Puppet[:profile] = true
|
60
|
+
|
61
|
+
subject.put_report('infinity', report, environment: environment)
|
62
|
+
end
|
63
|
+
|
63
64
|
it 'submits a report to the "report" endpoint' do
|
64
65
|
stub_request(:put, url)
|
65
66
|
.with(
|
@@ -79,6 +80,14 @@ describe Puppet::HTTP::Service::Report do
|
|
79
80
|
subject.put_report('node name', report, environment: environment)
|
80
81
|
end
|
81
82
|
|
83
|
+
it 'returns the response whose body contains the list of report processors' do
|
84
|
+
body = "[\"store\":\"http\"]"
|
85
|
+
stub_request(:put, url)
|
86
|
+
.to_return(status: 200, body: body, headers: {'Content-Type' => 'application/json'})
|
87
|
+
|
88
|
+
expect(subject.put_report('infinity', report, environment: environment).body).to eq(body)
|
89
|
+
end
|
90
|
+
|
82
91
|
it 'raises response error if unsuccessful' do
|
83
92
|
stub_request(:put, url).to_return(status: [400, 'Bad Request'], headers: {'X-Puppet-Version' => '6.1.8' })
|
84
93
|
|
@@ -1,19 +1,79 @@
|
|
1
1
|
require 'spec_helper'
|
2
2
|
require 'webmock/rspec'
|
3
3
|
require 'puppet/http'
|
4
|
+
require 'puppet/file_serving'
|
5
|
+
require 'puppet/file_serving/content'
|
6
|
+
require 'puppet/file_serving/metadata'
|
4
7
|
|
5
8
|
describe Puppet::HTTP::Service do
|
6
9
|
let(:ssl_context) { Puppet::SSL::SSLContext.new }
|
7
10
|
let(:client) { Puppet::HTTP::Client.new(ssl_context: ssl_context) }
|
11
|
+
let(:session) { Puppet::HTTP::Session.new(client, []) }
|
8
12
|
let(:url) { URI.parse('https://www.example.com') }
|
9
|
-
let(:service) { described_class.new(client, url) }
|
13
|
+
let(:service) { described_class.new(client, session, url) }
|
14
|
+
|
15
|
+
class TestService < Puppet::HTTP::Service
|
16
|
+
def get_test(ssl_context)
|
17
|
+
@client.get(
|
18
|
+
url,
|
19
|
+
headers: add_puppet_headers({'Default-Header' => 'default-value'}),
|
20
|
+
ssl_context: ssl_context
|
21
|
+
)
|
22
|
+
end
|
23
|
+
|
24
|
+
def mime_types(model)
|
25
|
+
get_mime_types(model)
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
context 'when modifying headers for an http request' do
|
30
|
+
let(:service) { TestService.new(client, session, url) }
|
31
|
+
|
32
|
+
it 'adds custom user-specified headers' do
|
33
|
+
stub_request(:get, "https://www.example.com/").
|
34
|
+
with( headers: { 'Default-Header'=>'default-value', 'Header2'=>'newvalue' })
|
35
|
+
|
36
|
+
Puppet[:http_extra_headers] = 'header2:newvalue'
|
37
|
+
|
38
|
+
service.get_test(ssl_context)
|
39
|
+
end
|
40
|
+
|
41
|
+
it 'adds X-Puppet-Profiling header if set' do
|
42
|
+
stub_request(:get, "https://www.example.com/").
|
43
|
+
with( headers: { 'Default-Header'=>'default-value', 'X-Puppet-Profiling'=>'true' })
|
44
|
+
|
45
|
+
Puppet[:profile] = true
|
46
|
+
|
47
|
+
service.get_test(ssl_context)
|
48
|
+
end
|
49
|
+
|
50
|
+
it 'ignores a custom header does not have a value' do
|
51
|
+
stub_request(:get, "https://www.example.com/").with do |request|
|
52
|
+
expect(request.headers).to include({'Default-Header' => 'default-value'})
|
53
|
+
expect(request.headers).to_not include('header-with-no-value')
|
54
|
+
end
|
55
|
+
|
56
|
+
Puppet[:http_extra_headers] = 'header-with-no-value:'
|
57
|
+
|
58
|
+
service.get_test(ssl_context)
|
59
|
+
end
|
60
|
+
|
61
|
+
it 'ignores a custom header that already exists (case insensitive) in the header hash' do
|
62
|
+
stub_request(:get, "https://www.example.com/").
|
63
|
+
with( headers: { 'Default-Header'=>'default-value' })
|
64
|
+
|
65
|
+
Puppet[:http_extra_headers] = 'default-header:wrongvalue'
|
66
|
+
|
67
|
+
service.get_test(ssl_context)
|
68
|
+
end
|
69
|
+
end
|
10
70
|
|
11
71
|
it "returns a URI containing the base URL and path" do
|
12
72
|
expect(service.with_base_url('/puppet/v3')).to eq(URI.parse("https://www.example.com/puppet/v3"))
|
13
73
|
end
|
14
74
|
|
15
75
|
it "doesn't modify frozen the base URL" do
|
16
|
-
service = described_class.new(client, url.freeze)
|
76
|
+
service = described_class.new(client, session, url.freeze)
|
17
77
|
service.with_base_url('/puppet/v3')
|
18
78
|
end
|
19
79
|
|
@@ -36,7 +96,7 @@ describe Puppet::HTTP::Service do
|
|
36
96
|
|
37
97
|
it 'raises for unknown service names' do
|
38
98
|
expect {
|
39
|
-
described_class.create_service(client, :westbound)
|
99
|
+
described_class.create_service(client, session, :westbound)
|
40
100
|
}.to raise_error(ArgumentError, "Unknown service westbound")
|
41
101
|
end
|
42
102
|
|
@@ -53,4 +113,33 @@ describe Puppet::HTTP::Service do
|
|
53
113
|
it "returns false for unknown service names" do
|
54
114
|
expect(described_class.valid_name?(:westbound)).to eq(false)
|
55
115
|
end
|
116
|
+
|
117
|
+
it 'returns different mime types for different models' do
|
118
|
+
mimes = if Puppet.features.msgpack?
|
119
|
+
%w[application/json application/x-msgpack text/pson]
|
120
|
+
else
|
121
|
+
%w[application/json text/pson]
|
122
|
+
end
|
123
|
+
|
124
|
+
service = TestService.new(client, session, url)
|
125
|
+
[
|
126
|
+
Puppet::Node,
|
127
|
+
Puppet::Node::Facts,
|
128
|
+
Puppet::Transaction::Report,
|
129
|
+
Puppet::FileServing::Metadata,
|
130
|
+
Puppet::Status
|
131
|
+
].each do |model|
|
132
|
+
expect(service.mime_types(model)).to eq(mimes)
|
133
|
+
end
|
134
|
+
|
135
|
+
# These are special
|
136
|
+
expect(service.mime_types(Puppet::FileServing::Content)).to eq(%w[application/octet-stream])
|
137
|
+
|
138
|
+
catalog_mimes = if Puppet.features.msgpack?
|
139
|
+
%w[application/vnd.puppet.rich+json application/json application/vnd.puppet.rich+msgpack application/x-msgpack text/pson]
|
140
|
+
else
|
141
|
+
%w[application/vnd.puppet.rich+json application/json application/vnd.puppet.rich+msgpack text/pson]
|
142
|
+
end
|
143
|
+
expect(service.mime_types(Puppet::Resource::Catalog)).to eq(catalog_mimes)
|
144
|
+
end
|
56
145
|
end
|
@@ -155,7 +155,6 @@ describe Puppet::HTTP::Session do
|
|
155
155
|
}.to raise_error(Puppet::Error, "Could not select a functional puppet master from server_list: 'foo.example.com,bar.example.com'")
|
156
156
|
end
|
157
157
|
|
158
|
-
|
159
158
|
it "raises when there are no more routes" do
|
160
159
|
allow_any_instance_of(Net::HTTP).to receive(:start).and_raise(Errno::EHOSTUNREACH)
|
161
160
|
session = client.create_session
|
@@ -164,5 +163,109 @@ describe Puppet::HTTP::Session do
|
|
164
163
|
session.route_to(:ca)
|
165
164
|
}.to raise_error(Puppet::HTTP::RouteError, 'No more routes to ca')
|
166
165
|
end
|
166
|
+
|
167
|
+
Puppet::HTTP::Service::SERVICE_NAMES.each do |name|
|
168
|
+
it "resolves #{name} using server_list" do
|
169
|
+
stub_request(:get, "https://ca.example.com:8141/status/v1/simple/master").to_return(status: 200)
|
170
|
+
|
171
|
+
session.route_to(name)
|
172
|
+
end
|
173
|
+
end
|
174
|
+
|
175
|
+
it 'does not use server_list to resolve the ca service when ca_server is explicitly set' do
|
176
|
+
Puppet[:ca_server] = 'banana.example.com'
|
177
|
+
|
178
|
+
expect(session.route_to(:ca).url.to_s).to eq("https://banana.example.com:8140/puppet-ca/v1")
|
179
|
+
end
|
180
|
+
|
181
|
+
it 'does not use server_list to resolve the report service when the report_server is explicitly set' do
|
182
|
+
Puppet[:report_server] = 'cherry.example.com'
|
183
|
+
|
184
|
+
expect(session.route_to(:report).url.to_s).to eq("https://cherry.example.com:8140/puppet/v3")
|
185
|
+
end
|
186
|
+
end
|
187
|
+
|
188
|
+
context 'when retrieving capabilities' do
|
189
|
+
let(:session) do
|
190
|
+
resolver = DummyResolver.new(good_service)
|
191
|
+
described_class.new(client, [resolver])
|
192
|
+
end
|
193
|
+
|
194
|
+
it 'raises for unknown service names' do
|
195
|
+
expect {
|
196
|
+
session = described_class.new(client, [])
|
197
|
+
session.supports?(:westbound, 'a capability')
|
198
|
+
}.to raise_error(ArgumentError, "Unknown service westbound")
|
199
|
+
end
|
200
|
+
|
201
|
+
context 'locales' do
|
202
|
+
it 'does not support locales if the cached service has not been resolved' do
|
203
|
+
session = described_class.new(client, [])
|
204
|
+
|
205
|
+
expect(session).to_not be_supports(:puppet, 'locales')
|
206
|
+
end
|
207
|
+
|
208
|
+
it "supports locales if the cached service's version is 5.3.4 or greater" do
|
209
|
+
response = Puppet::HTTP::Response.new({'X-Puppet-Version' => '5.3.4'}, uri)
|
210
|
+
|
211
|
+
session.route_to(:puppet)
|
212
|
+
session.process_response(response)
|
213
|
+
|
214
|
+
expect(session).to be_supports(:puppet, 'locales')
|
215
|
+
end
|
216
|
+
|
217
|
+
it "does not support locales if the cached service's version is 5.3.3" do
|
218
|
+
response = Puppet::HTTP::Response.new({'X-Puppet-Version' => '5.3.3'}, uri)
|
219
|
+
|
220
|
+
session.route_to(:puppet)
|
221
|
+
session.process_response(response)
|
222
|
+
|
223
|
+
expect(session).to_not be_supports(:puppet, 'locales')
|
224
|
+
end
|
225
|
+
|
226
|
+
it "does not support locales if the cached service's version is missing" do
|
227
|
+
response = Puppet::HTTP::Response.new({}, uri)
|
228
|
+
|
229
|
+
session.route_to(:puppet)
|
230
|
+
session.process_response(response)
|
231
|
+
|
232
|
+
expect(session).to_not be_supports(:puppet, 'locales')
|
233
|
+
end
|
234
|
+
end
|
235
|
+
|
236
|
+
context 'json' do
|
237
|
+
it 'does not support json if the cached service has not been resolved' do
|
238
|
+
session = described_class.new(client, [])
|
239
|
+
|
240
|
+
expect(session).to_not be_supports(:puppet, 'json')
|
241
|
+
end
|
242
|
+
|
243
|
+
it "supports json if the cached service's version is 5 or greater" do
|
244
|
+
response = Puppet::HTTP::Response.new({'X-Puppet-Version' => '5.5.12'}, uri)
|
245
|
+
|
246
|
+
session.route_to(:puppet)
|
247
|
+
session.process_response(response)
|
248
|
+
|
249
|
+
expect(session).to be_supports(:puppet, 'json')
|
250
|
+
end
|
251
|
+
|
252
|
+
it "does not support json if the cached service's version is less than 5.0" do
|
253
|
+
response = Puppet::HTTP::Response.new({'X-Puppet-Version' => '4.10.1'}, uri)
|
254
|
+
|
255
|
+
session.route_to(:puppet)
|
256
|
+
session.process_response(response)
|
257
|
+
|
258
|
+
expect(session).to_not be_supports(:puppet, 'json')
|
259
|
+
end
|
260
|
+
|
261
|
+
it "supports json if the cached service's version is missing" do
|
262
|
+
response = Puppet::HTTP::Response.new({}, uri)
|
263
|
+
|
264
|
+
session.route_to(:puppet)
|
265
|
+
session.process_response(response)
|
266
|
+
|
267
|
+
expect(session).to be_supports(:puppet, 'json')
|
268
|
+
end
|
269
|
+
end
|
167
270
|
end
|
168
271
|
end
|
@@ -3,7 +3,64 @@ require 'spec_helper'
|
|
3
3
|
require 'puppet/indirector/catalog/rest'
|
4
4
|
|
5
5
|
describe Puppet::Resource::Catalog::Rest do
|
6
|
-
|
7
|
-
|
6
|
+
let(:certname) { 'ziggy' }
|
7
|
+
let(:uri) { %r{/puppet/v3/catalog/ziggy} }
|
8
|
+
let(:formatter) { Puppet::Network::FormatHandler.format(:json) }
|
9
|
+
let(:catalog) { Puppet::Resource::Catalog.new(certname) }
|
10
|
+
|
11
|
+
before :each do
|
12
|
+
Puppet[:server] = 'compiler.example.com'
|
13
|
+
Puppet[:masterport] = 8140
|
14
|
+
|
15
|
+
described_class.indirection.terminus_class = :rest
|
16
|
+
end
|
17
|
+
|
18
|
+
def catalog_response(catalog)
|
19
|
+
{ body: formatter.render(catalog), headers: {'Content-Type' => formatter.mime } }
|
20
|
+
end
|
21
|
+
|
22
|
+
it 'finds a catalog' do
|
23
|
+
stub_request(:post, uri).to_return(**catalog_response(catalog))
|
24
|
+
|
25
|
+
expect(described_class.indirection.find(certname)).to be_a(Puppet::Resource::Catalog)
|
26
|
+
end
|
27
|
+
|
28
|
+
it "serializes the environment" do
|
29
|
+
stub_request(:post, uri)
|
30
|
+
.with(query: hash_including('environment' => 'outerspace'))
|
31
|
+
.to_return(**catalog_response(catalog))
|
32
|
+
|
33
|
+
described_class.indirection.find(certname, environment: Puppet::Node::Environment.remote('outerspace'))
|
34
|
+
end
|
35
|
+
|
36
|
+
it 'constructs a catalog environment_instance' do
|
37
|
+
env = Puppet::Node::Environment.remote('outerspace')
|
38
|
+
catalog = Puppet::Resource::Catalog.new(certname, env)
|
39
|
+
|
40
|
+
stub_request(:post, uri).to_return(**catalog_response(catalog))
|
41
|
+
|
42
|
+
expect(described_class.indirection.find(certname).environment_instance).to eq(env)
|
43
|
+
end
|
44
|
+
|
45
|
+
it 'returns nil if the node does not exist' do
|
46
|
+
stub_request(:post, uri).to_return(status: 404, headers: { 'Content-Type' => 'application/json' }, body: "{}")
|
47
|
+
|
48
|
+
expect(described_class.indirection.find(certname)).to be_nil
|
49
|
+
end
|
50
|
+
|
51
|
+
it 'raises if fail_on_404 is specified' do
|
52
|
+
stub_request(:post, uri).to_return(status: 404, headers: { 'Content-Type' => 'application/json' }, body: "{}")
|
53
|
+
|
54
|
+
expect{
|
55
|
+
described_class.indirection.find(certname, fail_on_404: true)
|
56
|
+
}.to raise_error(Puppet::Error, %r{Find /puppet/v3/catalog/ziggy resulted in 404 with the message: {}})
|
57
|
+
end
|
58
|
+
|
59
|
+
it 'raises Net::HTTPError on 500' do
|
60
|
+
stub_request(:post, uri).to_return(status: 500)
|
61
|
+
|
62
|
+
expect{
|
63
|
+
described_class.indirection.find(certname)
|
64
|
+
}.to raise_error(Net::HTTPError, %r{Error 500 on SERVER: })
|
8
65
|
end
|
9
66
|
end
|