puppet 6.21.0-x86-mingw32 → 6.24.0-x86-mingw32
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 +5 -5
- data/Gemfile +1 -1
- data/Gemfile.lock +29 -23
- data/README.md +4 -4
- data/ext/osx/puppet.plist +2 -0
- data/ext/project_data.yaml +3 -2
- data/lib/puppet.rb +3 -3
- data/lib/puppet/application/agent.rb +12 -5
- data/lib/puppet/application/apply.rb +2 -1
- data/lib/puppet/application/device.rb +2 -1
- data/lib/puppet/application/filebucket.rb +1 -0
- data/lib/puppet/application/resource.rb +17 -3
- data/lib/puppet/application/script.rb +2 -1
- data/lib/puppet/application/ssl.rb +12 -0
- data/lib/puppet/configurer/downloader.rb +2 -1
- data/lib/puppet/defaults.rb +27 -5
- data/lib/puppet/environments.rb +26 -1
- data/lib/puppet/face/facts.rb +128 -30
- data/lib/puppet/face/help/action.erb +1 -0
- data/lib/puppet/face/help/face.erb +1 -0
- data/lib/puppet/face/node/clean.rb +11 -0
- data/lib/puppet/file_serving/fileset.rb +14 -2
- data/lib/puppet/file_system/file_impl.rb +1 -1
- data/lib/puppet/file_system/memory_file.rb +8 -1
- data/lib/puppet/file_system/windows.rb +4 -2
- data/lib/puppet/forge.rb +3 -3
- data/lib/puppet/functions/all.rb +1 -1
- data/lib/puppet/functions/camelcase.rb +1 -1
- data/lib/puppet/functions/capitalize.rb +2 -2
- data/lib/puppet/functions/downcase.rb +2 -2
- data/lib/puppet/functions/empty.rb +8 -0
- data/lib/puppet/functions/get.rb +5 -5
- data/lib/puppet/functions/group_by.rb +13 -5
- data/lib/puppet/functions/lest.rb +1 -1
- data/lib/puppet/functions/new.rb +100 -100
- data/lib/puppet/functions/partition.rb +12 -4
- data/lib/puppet/functions/require.rb +5 -5
- data/lib/puppet/functions/sort.rb +3 -3
- data/lib/puppet/functions/strftime.rb +1 -0
- data/lib/puppet/functions/tree_each.rb +7 -9
- data/lib/puppet/functions/type.rb +4 -4
- data/lib/puppet/functions/unwrap.rb +17 -2
- data/lib/puppet/functions/upcase.rb +2 -2
- data/lib/puppet/http/resolver/server_list.rb +15 -4
- data/lib/puppet/http/service/compiler.rb +69 -0
- data/lib/puppet/http/service/file_server.rb +2 -1
- data/lib/puppet/indirector/catalog/compiler.rb +1 -0
- data/lib/puppet/indirector/facts/facter.rb +24 -3
- data/lib/puppet/indirector/file_metadata/rest.rb +1 -0
- data/lib/puppet/indirector/resource/ral.rb +6 -1
- data/lib/puppet/interface/documentation.rb +1 -0
- data/lib/puppet/module_tool/applications/installer.rb +4 -0
- data/lib/puppet/module_tool/errors/shared.rb +17 -0
- data/lib/puppet/network/formats.rb +67 -0
- data/lib/puppet/network/http/factory.rb +4 -0
- data/lib/puppet/parser/functions/fqdn_rand.rb +14 -6
- data/lib/puppet/pops/types/p_sem_ver_type.rb +8 -2
- data/lib/puppet/pops/types/p_sensitive_type.rb +10 -0
- data/lib/puppet/pops/types/type_mismatch_describer.rb +1 -1
- data/lib/puppet/provider/exec/posix.rb +16 -4
- data/lib/puppet/provider/package/dnfmodule.rb +1 -1
- data/lib/puppet/provider/package/nim.rb +11 -6
- data/lib/puppet/provider/package/pip.rb +15 -3
- data/lib/puppet/provider/parsedfile.rb +3 -0
- data/lib/puppet/provider/service/systemd.rb +14 -4
- data/lib/puppet/provider/service/windows.rb +38 -0
- data/lib/puppet/provider/user/directoryservice.rb +25 -12
- data/lib/puppet/provider/user/useradd.rb +9 -2
- data/lib/puppet/reference/configuration.rb +1 -1
- data/lib/puppet/settings.rb +30 -7
- data/lib/puppet/settings/environment_conf.rb +1 -0
- data/lib/puppet/transaction/additional_resource_generator.rb +1 -1
- data/lib/puppet/type/exec.rb +16 -3
- data/lib/puppet/type/file.rb +19 -1
- data/lib/puppet/type/file/mode.rb +6 -0
- data/lib/puppet/type/file/selcontext.rb +1 -1
- data/lib/puppet/type/service.rb +18 -38
- data/lib/puppet/type/tidy.rb +22 -3
- data/lib/puppet/type/user.rb +38 -20
- data/lib/puppet/util/fact_dif.rb +36 -17
- data/lib/puppet/util/monkey_patches.rb +7 -0
- data/lib/puppet/util/selinux.rb +30 -4
- data/lib/puppet/util/symbolic_file_mode.rb +29 -17
- data/lib/puppet/util/windows/adsi.rb +46 -0
- data/lib/puppet/util/windows/api_types.rb +1 -1
- data/lib/puppet/util/windows/principal.rb +9 -2
- data/lib/puppet/util/windows/sid.rb +6 -2
- data/lib/puppet/version.rb +1 -1
- data/locales/puppet.pot +360 -280
- data/man/man5/puppet.conf.5 +279 -251
- data/man/man8/puppet-agent.8 +1 -1
- data/man/man8/puppet-apply.8 +1 -1
- data/man/man8/puppet-catalog.8 +9 -9
- data/man/man8/puppet-config.8 +1 -1
- data/man/man8/puppet-describe.8 +1 -1
- data/man/man8/puppet-device.8 +1 -1
- data/man/man8/puppet-doc.8 +1 -1
- data/man/man8/puppet-epp.8 +1 -1
- data/man/man8/puppet-facts.8 +65 -7
- data/man/man8/puppet-filebucket.8 +1 -1
- data/man/man8/puppet-generate.8 +1 -1
- data/man/man8/puppet-help.8 +1 -1
- data/man/man8/puppet-key.8 +7 -7
- 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 +5 -5
- data/man/man8/puppet-parser.8 +1 -1
- data/man/man8/puppet-plugin.8 +1 -1
- data/man/man8/puppet-report.8 +5 -5
- data/man/man8/puppet-resource.8 +1 -1
- data/man/man8/puppet-script.8 +1 -1
- data/man/man8/puppet-ssl.8 +5 -1
- data/man/man8/puppet-status.8 +4 -4
- data/man/man8/puppet.8 +2 -2
- data/spec/fixtures/ssl/127.0.0.1-key.pem +107 -57
- data/spec/fixtures/ssl/127.0.0.1.pem +52 -31
- data/spec/fixtures/ssl/bad-basic-constraints.pem +57 -35
- data/spec/fixtures/ssl/bad-int-basic-constraints.pem +57 -35
- data/spec/fixtures/ssl/ca.pem +57 -35
- data/spec/fixtures/ssl/crl.pem +28 -18
- data/spec/fixtures/ssl/ec-key.pem +11 -11
- data/spec/fixtures/ssl/ec.pem +33 -24
- data/spec/fixtures/ssl/encrypted-ec-key.pem +12 -12
- data/spec/fixtures/ssl/encrypted-key.pem +108 -58
- data/spec/fixtures/ssl/intermediate-agent-crl.pem +28 -19
- data/spec/fixtures/ssl/intermediate-agent.pem +57 -36
- data/spec/fixtures/ssl/intermediate-crl.pem +31 -21
- data/spec/fixtures/ssl/intermediate.pem +57 -36
- data/spec/fixtures/ssl/oid-key.pem +117 -0
- data/spec/fixtures/ssl/oid.pem +69 -0
- data/spec/fixtures/ssl/pluto-key.pem +107 -57
- data/spec/fixtures/ssl/pluto.pem +52 -30
- data/spec/fixtures/ssl/request-key.pem +107 -57
- data/spec/fixtures/ssl/request.pem +47 -26
- data/spec/fixtures/ssl/revoked-key.pem +107 -57
- data/spec/fixtures/ssl/revoked.pem +52 -30
- data/spec/fixtures/ssl/signed-key.pem +107 -57
- data/spec/fixtures/ssl/signed.pem +52 -30
- data/spec/fixtures/ssl/tampered-cert.pem +52 -30
- data/spec/fixtures/ssl/tampered-csr.pem +47 -26
- data/spec/fixtures/ssl/trusted_oid_mapping.yaml +5 -0
- data/spec/fixtures/ssl/unknown-127.0.0.1-key.pem +107 -57
- data/spec/fixtures/ssl/unknown-127.0.0.1.pem +50 -29
- data/spec/fixtures/ssl/unknown-ca-key.pem +107 -57
- data/spec/fixtures/ssl/unknown-ca.pem +55 -33
- data/spec/fixtures/unit/provider/service/systemd/list_unit_files_services_vendor_preset +9 -0
- data/spec/integration/application/filebucket_spec.rb +11 -0
- data/spec/integration/application/module_spec.rb +21 -0
- data/spec/integration/application/plugin_spec.rb +1 -1
- data/spec/integration/application/resource_spec.rb +64 -0
- data/spec/integration/application/ssl_spec.rb +20 -0
- data/spec/integration/environments/settings_interpolation_spec.rb +0 -4
- data/spec/integration/http/client_spec.rb +12 -0
- data/spec/integration/indirector/direct_file_server_spec.rb +1 -3
- data/spec/integration/indirector/facts/facter_spec.rb +90 -36
- data/spec/integration/type/exec_spec.rb +70 -45
- data/spec/integration/util/windows/adsi_spec.rb +18 -0
- data/spec/integration/util/windows/principal_spec.rb +21 -0
- data/spec/integration/util/windows/registry_spec.rb +6 -0
- data/spec/lib/puppet/test_ca.rb +7 -2
- data/spec/lib/puppet_spec/settings.rb +1 -0
- data/spec/spec_helper.rb +11 -1
- data/spec/unit/application/agent_spec.rb +7 -2
- data/spec/unit/application/facts_spec.rb +482 -3
- data/spec/unit/application/ssl_spec.rb +23 -0
- data/spec/unit/configurer/downloader_spec.rb +6 -0
- data/spec/unit/configurer_spec.rb +23 -0
- data/spec/unit/defaults_spec.rb +16 -0
- data/spec/unit/environments_spec.rb +199 -88
- data/spec/unit/face/facts_spec.rb +4 -0
- data/spec/unit/file_serving/fileset_spec.rb +60 -0
- data/spec/unit/file_system_spec.rb +15 -0
- data/spec/unit/functions/assert_type_spec.rb +1 -1
- data/spec/unit/functions/empty_spec.rb +10 -0
- data/spec/unit/functions/unwrap_spec.rb +8 -0
- data/spec/unit/functions4_spec.rb +2 -2
- data/spec/unit/gettext/config_spec.rb +12 -0
- data/spec/unit/http/service/compiler_spec.rb +123 -0
- data/spec/unit/indirector/catalog/compiler_spec.rb +14 -10
- data/spec/unit/indirector/facts/facter_spec.rb +95 -0
- data/spec/unit/indirector/resource/ral_spec.rb +40 -75
- data/spec/unit/module_tool/applications/installer_spec.rb +12 -0
- data/spec/unit/network/formats_spec.rb +41 -0
- data/spec/unit/network/http/factory_spec.rb +19 -0
- data/spec/unit/parser/functions/fqdn_rand_spec.rb +15 -1
- data/spec/unit/parser/templatewrapper_spec.rb +12 -2
- data/spec/unit/pops/types/p_sem_ver_type_spec.rb +18 -0
- data/spec/unit/pops/types/p_sensitive_type_spec.rb +18 -0
- data/spec/unit/provider/package/dnfmodule_spec.rb +10 -1
- data/spec/unit/provider/package/nim_spec.rb +42 -0
- data/spec/unit/provider/package/pip_spec.rb +37 -0
- data/spec/unit/provider/parsedfile_spec.rb +10 -0
- data/spec/unit/provider/service/init_spec.rb +1 -0
- data/spec/unit/provider/service/openwrt_spec.rb +3 -1
- data/spec/unit/provider/service/systemd_spec.rb +53 -8
- data/spec/unit/provider/service/windows_spec.rb +202 -0
- data/spec/unit/provider/user/directoryservice_spec.rb +67 -35
- data/spec/unit/provider/user/useradd_spec.rb +21 -6
- data/spec/unit/resource/catalog_spec.rb +1 -1
- data/spec/unit/settings_spec.rb +97 -56
- data/spec/unit/ssl/state_machine_spec.rb +19 -5
- data/spec/unit/transaction/additional_resource_generator_spec.rb +0 -2
- data/spec/unit/transaction_spec.rb +18 -20
- data/spec/unit/type/exec_spec.rb +76 -29
- data/spec/unit/type/file/selinux_spec.rb +3 -3
- data/spec/unit/type/file/source_spec.rb +4 -4
- data/spec/unit/type/service_spec.rb +59 -188
- data/spec/unit/type/tidy_spec.rb +24 -7
- data/spec/unit/type/user_spec.rb +45 -0
- data/spec/unit/util/selinux_spec.rb +87 -16
- data/spec/unit/util/windows/sid_spec.rb +41 -0
- data/tasks/generate_cert_fixtures.rake +12 -3
- metadata +24 -9
- data/spec/lib/matchers/include.rb +0 -27
- data/spec/lib/matchers/include_spec.rb +0 -32
@@ -46,6 +46,13 @@ describe Puppet::FileServing::Fileset do
|
|
46
46
|
expect(set.recurselimit).to eq(3)
|
47
47
|
end
|
48
48
|
|
49
|
+
it "accepts a 'max_files' option" do
|
50
|
+
expect(Puppet::FileSystem).to receive(:lstat).with(somefile).and_return(double('stat'))
|
51
|
+
set = Puppet::FileServing::Fileset.new(somefile, :recurselimit => 3, :max_files => 100)
|
52
|
+
expect(set.recurselimit).to eq(3)
|
53
|
+
expect(set.max_files).to eq(100)
|
54
|
+
end
|
55
|
+
|
49
56
|
it "accepts an 'ignore' option" do
|
50
57
|
expect(Puppet::FileSystem).to receive(:lstat).with(somefile).and_return(double('stat'))
|
51
58
|
set = Puppet::FileServing::Fileset.new(somefile, :ignore => ".svn")
|
@@ -160,6 +167,29 @@ describe Puppet::FileServing::Fileset do
|
|
160
167
|
end
|
161
168
|
end
|
162
169
|
|
170
|
+
def mock_big_dir_structure(path, stat_method = :lstat)
|
171
|
+
allow(Puppet::FileSystem).to receive(stat_method).with(path).and_return(@dirstat)
|
172
|
+
|
173
|
+
# Keep track of the files we're stubbing.
|
174
|
+
@files = %w{.}
|
175
|
+
|
176
|
+
top_names = (1..10).map {|i| "dir_#{i}" }
|
177
|
+
sub_names = (1..100).map {|i| "file__#{i}" }
|
178
|
+
|
179
|
+
allow(Dir).to receive(:entries).with(path, encoding: Encoding::UTF_8).and_return(top_names)
|
180
|
+
top_names.each do |subdir|
|
181
|
+
@files << subdir # relative path
|
182
|
+
subpath = File.join(path, subdir)
|
183
|
+
allow(Puppet::FileSystem).to receive(stat_method).with(subpath).and_return(@dirstat)
|
184
|
+
allow(Dir).to receive(:entries).with(subpath, encoding: Encoding::UTF_8).and_return(sub_names)
|
185
|
+
sub_names.each do |file|
|
186
|
+
@files << File.join(subdir, file) # relative path
|
187
|
+
subfile_path = File.join(subpath, file)
|
188
|
+
allow(Puppet::FileSystem).to receive(stat_method).with(subfile_path).and_return(@filestat)
|
189
|
+
end
|
190
|
+
end
|
191
|
+
end
|
192
|
+
|
163
193
|
def setup_mocks_for_dir(mock_dir, base_path)
|
164
194
|
path = File.join(base_path, mock_dir.name)
|
165
195
|
allow(Puppet::FileSystem).to receive(:lstat).with(path).and_return(MockStat.new(path, true))
|
@@ -258,6 +288,36 @@ describe Puppet::FileServing::Fileset do
|
|
258
288
|
expect(@fileset.files.find { |file| file.include?("0") }).to be_nil
|
259
289
|
end
|
260
290
|
|
291
|
+
it "raises exception if number of files is greater than :max_files" do
|
292
|
+
mock_dir_structure(@path)
|
293
|
+
@fileset.recurse = true
|
294
|
+
@fileset.max_files = 22
|
295
|
+
expect { @fileset.files }.to raise_error(Puppet::Error, "The directory '#{@path}' contains 28 entries, which exceeds the limit of 22 specified by the max_files parameter for this resource. The limit may be increased, but be aware that large number of file resources can result in excessive resource consumption and degraded performance. Consider using an alternate method to manage large directory trees")
|
296
|
+
end
|
297
|
+
|
298
|
+
it "logs a warning if number of files is greater than soft max_files limit of 1000" do
|
299
|
+
mock_big_dir_structure(@path)
|
300
|
+
@fileset.recurse = true
|
301
|
+
expect(Puppet).to receive(:warning).with("The directory '#{@path}' contains 1010 entries, which exceeds the default soft limit 1000 and may cause excessive resource consumption and degraded performance. To remove this warning set a value for `max_files` parameter or consider using an alternate method to manage large directory trees")
|
302
|
+
expect { @fileset.files }.to_not raise_error
|
303
|
+
end
|
304
|
+
|
305
|
+
it "does not emit a warning if max_files is -1" do
|
306
|
+
mock_big_dir_structure(@path)
|
307
|
+
@fileset.recurse = true
|
308
|
+
@fileset.max_files = -1
|
309
|
+
expect(Puppet).to receive(:warning).never
|
310
|
+
@fileset.files
|
311
|
+
end
|
312
|
+
|
313
|
+
it "does not emit a warning if max_files is `-1`(string)" do
|
314
|
+
mock_big_dir_structure(@path)
|
315
|
+
@fileset.recurse = true
|
316
|
+
@fileset.max_files = '-1'
|
317
|
+
expect(Puppet).to receive(:warning).never
|
318
|
+
@fileset.files
|
319
|
+
end
|
320
|
+
|
261
321
|
it "ignores files that match a pattern given as a boolean" do
|
262
322
|
mock_dir_structure(@path)
|
263
323
|
@fileset.recurse = true
|
@@ -290,6 +290,12 @@ describe "Puppet::FileSystem" do
|
|
290
290
|
expect(Puppet::FileSystem.read_preserve_line_endings(file)).to eq("file content \r\nsecond line \n")
|
291
291
|
end
|
292
292
|
end
|
293
|
+
|
294
|
+
it "should ignore leading BOM" do
|
295
|
+
with_file_content("\uFEFFfile content \n") do |file|
|
296
|
+
expect(Puppet::FileSystem.read_preserve_line_endings(file)).to eq("file content \n")
|
297
|
+
end
|
298
|
+
end
|
293
299
|
end
|
294
300
|
|
295
301
|
context "read without an encoding specified" do
|
@@ -999,6 +1005,15 @@ describe "Puppet::FileSystem" do
|
|
999
1005
|
Puppet::FileSystem.replace_file(dest, 0755) { |_| }
|
1000
1006
|
}.to raise_error(ArgumentError, /Only modes 0644, 0640, 0660, and 0440 are allowed/)
|
1001
1007
|
end
|
1008
|
+
|
1009
|
+
it 'falls back to fully qualified user name when sid retrieval fails' do
|
1010
|
+
current_user_sid = Puppet::Util::Windows::SID.name_to_sid(Puppet::Util::Windows::ADSI::User.current_user_name)
|
1011
|
+
allow(Puppet::Util::Windows::SID).to receive(:name_to_sid).with(Puppet::Util::Windows::ADSI::User.current_user_name).and_return(nil, current_user_sid)
|
1012
|
+
allow(Puppet::Util::Windows::SID).to receive(:name_to_sid).with(Puppet::Util::Windows::ADSI::User.current_sam_compatible_user_name).and_call_original
|
1013
|
+
|
1014
|
+
Puppet::FileSystem.replace_file(dest, 0644) { |f| f.write(content) }
|
1015
|
+
expects_public_file(dest)
|
1016
|
+
end
|
1002
1017
|
end
|
1003
1018
|
end
|
1004
1019
|
|
@@ -28,7 +28,7 @@ describe 'the assert_type function' do
|
|
28
28
|
it 'checks that first argument is a type' do
|
29
29
|
expect do
|
30
30
|
func.call({}, 10, 10)
|
31
|
-
end.to raise_error(ArgumentError, "'assert_type' expects one of:
|
31
|
+
end.to raise_error(ArgumentError, "The function 'assert_type' was called with arguments it does not accept. It expects one of:
|
32
32
|
(Type type, Any value, Callable[Type, Type] block?)
|
33
33
|
rejected: parameter 'type' expects a Type value, got Integer
|
34
34
|
(String type_string, Any value, Callable[Type, Type] block?)
|
@@ -56,6 +56,16 @@ describe 'the empty function' do
|
|
56
56
|
end
|
57
57
|
end
|
58
58
|
|
59
|
+
context 'for a sensitive string it' do
|
60
|
+
it 'returns true when empty' do
|
61
|
+
expect(compile_to_catalog("notify { String(empty(Sensitive(''))): }")).to have_resource('Notify[true]')
|
62
|
+
end
|
63
|
+
|
64
|
+
it 'returns false when not empty' do
|
65
|
+
expect(compile_to_catalog("notify { String(empty(Sensitive(' '))): }")).to have_resource('Notify[false]')
|
66
|
+
end
|
67
|
+
end
|
68
|
+
|
59
69
|
context 'for a binary it' do
|
60
70
|
it 'returns true when empty' do
|
61
71
|
expect(compile_to_catalog("notify { String(empty(Binary(''))): }")).to have_resource('Notify[true]')
|
@@ -15,6 +15,14 @@ describe 'the unwrap function' do
|
|
15
15
|
expect(eval_and_collect_notices(code)).to eq(['unwrapped value is 12345'])
|
16
16
|
end
|
17
17
|
|
18
|
+
it 'just returns a non-sensitive value' do
|
19
|
+
code = <<-CODE
|
20
|
+
$non_sensitive = "12345"
|
21
|
+
notice("value is still ${non_sensitive.unwrap}")
|
22
|
+
CODE
|
23
|
+
expect(eval_and_collect_notices(code)).to eq(['value is still 12345'])
|
24
|
+
end
|
25
|
+
|
18
26
|
it 'unwraps a sensitive value when given a code block' do
|
19
27
|
code = <<-CODE
|
20
28
|
$sensitive = Sensitive.new("12345")
|
@@ -160,7 +160,7 @@ describe 'the 4x function api' do
|
|
160
160
|
expect(func.is_a?(Puppet::Functions::Function)).to be_truthy
|
161
161
|
expect do
|
162
162
|
func.call({}, 3, 10, 3, "4")
|
163
|
-
end.to raise_error(ArgumentError, "'min' expects one of:
|
163
|
+
end.to raise_error(ArgumentError, "The function 'min' was called with arguments it does not accept. It expects one of:
|
164
164
|
(Numeric x, Numeric y, Numeric a?, Numeric b?, Numeric c*)
|
165
165
|
rejected: parameter 'b' expects a Numeric value, got String
|
166
166
|
(String x, String y, String a+)
|
@@ -231,7 +231,7 @@ describe 'the 4x function api' do
|
|
231
231
|
expect(func.is_a?(Puppet::Functions::Function)).to be_truthy
|
232
232
|
expect do
|
233
233
|
func.call({}, 10, '20')
|
234
|
-
end.to raise_error(ArgumentError, "'min' expects one of:
|
234
|
+
end.to raise_error(ArgumentError, "The function 'min' was called with arguments it does not accept. It expects one of:
|
235
235
|
(Numeric a, Numeric b)
|
236
236
|
rejected: parameter 'b' expects a Numeric value, got String
|
237
237
|
(String s1, String s2)
|
@@ -27,6 +27,18 @@ describe Puppet::GettextConfig do
|
|
27
27
|
Puppet::GettextConfig.delete_all_text_domains
|
28
28
|
end
|
29
29
|
|
30
|
+
# These tests assume gettext is enabled, but it will be disabled when the
|
31
|
+
# first time the `Puppet[:disable_i18n]` setting is resolved
|
32
|
+
around(:each) do |example|
|
33
|
+
disabled = Puppet::GettextConfig.instance_variable_get(:@gettext_disabled)
|
34
|
+
Puppet::GettextConfig.instance_variable_set(:@gettext_disabled, false)
|
35
|
+
begin
|
36
|
+
example.run
|
37
|
+
ensure
|
38
|
+
Puppet::GettextConfig.instance_variable_set(:@gettext_disabled, disabled)
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
30
42
|
describe 'setting and getting the locale' do
|
31
43
|
it 'should return "en" when gettext is unavailable' do
|
32
44
|
allow(Puppet::GettextConfig).to receive(:gettext_loaded?).and_return(false)
|
@@ -1,3 +1,4 @@
|
|
1
|
+
|
1
2
|
# coding: utf-8
|
2
3
|
require 'spec_helper'
|
3
4
|
require 'puppet/http'
|
@@ -258,6 +259,128 @@ describe Puppet::HTTP::Service::Compiler do
|
|
258
259
|
end
|
259
260
|
end
|
260
261
|
|
262
|
+
context 'when posting for a v4 catalog' do
|
263
|
+
let(:uri) {"https://compiler.example.com:8140/puppet/v4/catalog"}
|
264
|
+
let(:persistence) {{ facts: true, catalog: true }}
|
265
|
+
let(:facts) {{ 'foo' => 'bar' }}
|
266
|
+
let(:trusted_facts) {{}}
|
267
|
+
let(:uuid) { "ec3d2844-b236-4287-b0ad-632fbb4d1ff0" }
|
268
|
+
let(:job_id) { "1" }
|
269
|
+
let(:payload) {{
|
270
|
+
environment: environment,
|
271
|
+
persistence: persistence,
|
272
|
+
facts: facts,
|
273
|
+
trusted_facts: trusted_facts,
|
274
|
+
transaction_uuid: uuid,
|
275
|
+
job_id: job_id,
|
276
|
+
options: {
|
277
|
+
prefer_requested_environment: false,
|
278
|
+
capture_logs: false
|
279
|
+
}
|
280
|
+
}}
|
281
|
+
let(:serialized_catalog) {{ 'catalog' => catalog.to_data_hash }.to_json}
|
282
|
+
let(:catalog_response) {{ body: serialized_catalog, headers: {'Content-Type' => formatter.mime }}}
|
283
|
+
|
284
|
+
it 'includes default HTTP headers' do
|
285
|
+
stub_request(:post, uri).with do |request|
|
286
|
+
expect(request.headers).to include({'X-Puppet-Version' => /./, 'User-Agent' => /./})
|
287
|
+
expect(request.headers).to_not include('X-Puppet-Profiling')
|
288
|
+
end.to_return(**catalog_response)
|
289
|
+
|
290
|
+
subject.post_catalog4(certname, **payload)
|
291
|
+
end
|
292
|
+
|
293
|
+
it 'defaults the server and port based on settings' do
|
294
|
+
Puppet[:server] = 'compiler2.example.com'
|
295
|
+
Puppet[:serverport] = 8141
|
296
|
+
|
297
|
+
stub_request(:post, "https://compiler2.example.com:8141/puppet/v4/catalog")
|
298
|
+
.to_return(**catalog_response)
|
299
|
+
|
300
|
+
subject.post_catalog4(certname, **payload)
|
301
|
+
end
|
302
|
+
|
303
|
+
it 'includes puppet headers set via the :http_extra_headers and :profile settings' do
|
304
|
+
stub_request(:post, uri).with(headers: {'Example-Header' => 'real-thing', 'another' => 'thing', 'X-Puppet-Profiling' => 'true'}).
|
305
|
+
to_return(**catalog_response)
|
306
|
+
|
307
|
+
Puppet[:http_extra_headers] = 'Example-Header:real-thing,another:thing'
|
308
|
+
Puppet[:profile] = true
|
309
|
+
|
310
|
+
subject.post_catalog4(certname, **payload)
|
311
|
+
end
|
312
|
+
|
313
|
+
it 'returns a deserialized catalog' do
|
314
|
+
stub_request(:post, uri)
|
315
|
+
.to_return(**catalog_response)
|
316
|
+
|
317
|
+
_, cat, _ = subject.post_catalog4(certname, **payload)
|
318
|
+
expect(cat).to be_a(Puppet::Resource::Catalog)
|
319
|
+
expect(cat.name).to eq(certname)
|
320
|
+
end
|
321
|
+
|
322
|
+
it 'returns the request response' do
|
323
|
+
stub_request(:post, uri)
|
324
|
+
.to_return(**catalog_response)
|
325
|
+
|
326
|
+
resp, _, _ = subject.post_catalog4(certname, **payload)
|
327
|
+
expect(resp).to be_a(Puppet::HTTP::Response)
|
328
|
+
end
|
329
|
+
|
330
|
+
it 'raises a response error if unsuccessful' do
|
331
|
+
stub_request(:post, uri)
|
332
|
+
.to_return(status: [500, "Server Error"])
|
333
|
+
|
334
|
+
expect {
|
335
|
+
subject.post_catalog4(certname, **payload)
|
336
|
+
}.to raise_error do |err|
|
337
|
+
expect(err).to be_an_instance_of(Puppet::HTTP::ResponseError)
|
338
|
+
expect(err.message).to eq('Server Error')
|
339
|
+
expect(err.response.code).to eq(500)
|
340
|
+
end
|
341
|
+
end
|
342
|
+
|
343
|
+
it 'raises a response error when server response is not JSON' do
|
344
|
+
stub_request(:post, uri)
|
345
|
+
.to_return(body: "this isn't valid JSON", headers: {'Content-Type' => 'application/json'})
|
346
|
+
|
347
|
+
expect {
|
348
|
+
subject.post_catalog4(certname, **payload)
|
349
|
+
}.to raise_error do |err|
|
350
|
+
expect(err).to be_an_instance_of(Puppet::HTTP::SerializationError)
|
351
|
+
expect(err.message).to match(/Failed to deserialize catalog from puppetserver response/)
|
352
|
+
end
|
353
|
+
end
|
354
|
+
|
355
|
+
it 'raises a response error when server response a JSON serialized catalog' do
|
356
|
+
stub_request(:post, uri)
|
357
|
+
.to_return(body: {oops: 'bad response data'}.to_json, headers: {'Content-Type' => 'application/json'})
|
358
|
+
|
359
|
+
expect {
|
360
|
+
subject.post_catalog4(certname, **payload)
|
361
|
+
}.to raise_error do |err|
|
362
|
+
expect(err).to be_an_instance_of(Puppet::HTTP::SerializationError)
|
363
|
+
expect(err.message).to match(/Failed to deserialize catalog from puppetserver response/)
|
364
|
+
end
|
365
|
+
end
|
366
|
+
|
367
|
+
it 'raises ArgumentError when the `persistence` hash does not contain required keys' do
|
368
|
+
payload[:persistence].delete(:facts)
|
369
|
+
expect { subject.post_catalog4(certname, **payload) }.to raise_error do |err|
|
370
|
+
expect(err).to be_an_instance_of(ArgumentError)
|
371
|
+
expect(err.message).to match(/The 'persistence' hash is missing the keys: facts/)
|
372
|
+
end
|
373
|
+
end
|
374
|
+
|
375
|
+
it 'raises ArgumentError when `facts` are not a Hash' do
|
376
|
+
payload[:facts] = Puppet::Node::Facts.new(certname)
|
377
|
+
expect { subject.post_catalog4(certname, **payload) }.to raise_error do |err|
|
378
|
+
expect(err).to be_an_instance_of(ArgumentError)
|
379
|
+
expect(err.message).to match(/Facts must be a Hash not a Puppet::Node::Facts/)
|
380
|
+
end
|
381
|
+
end
|
382
|
+
end
|
383
|
+
|
261
384
|
context 'when getting a node' do
|
262
385
|
let(:uri) { %r{/puppet/v3/node/ziggy} }
|
263
386
|
let(:node_response) { { body: formatter.render(node), headers: {'Content-Type' => formatter.mime } } }
|
@@ -909,9 +909,10 @@ describe Puppet::Resource::Catalog::Compiler do
|
|
909
909
|
it "inlines child metadata" do
|
910
910
|
catalog = compile_to_catalog(<<-MANIFEST, node)
|
911
911
|
file { '#{path}':
|
912
|
-
ensure
|
913
|
-
recurse
|
914
|
-
source
|
912
|
+
ensure => directory,
|
913
|
+
recurse => true,
|
914
|
+
source => '#{source_dir}',
|
915
|
+
max_files => 1234,
|
915
916
|
}
|
916
917
|
MANIFEST
|
917
918
|
|
@@ -925,6 +926,7 @@ describe Puppet::Resource::Catalog::Compiler do
|
|
925
926
|
:source_permissions => :ignore,
|
926
927
|
:recurse => true,
|
927
928
|
:recurselimit => nil,
|
929
|
+
:max_files => 1234,
|
928
930
|
:ignore => nil,
|
929
931
|
}
|
930
932
|
expect(Puppet::FileServing::Metadata.indirection).to receive(:search).with(source_dir, options).and_return([metadata, child_metadata])
|
@@ -938,14 +940,15 @@ describe Puppet::Resource::Catalog::Compiler do
|
|
938
940
|
it "uses resource parameters when inlining metadata" do
|
939
941
|
catalog = compile_to_catalog(<<-MANIFEST, node)
|
940
942
|
file { '#{path}':
|
941
|
-
ensure
|
942
|
-
recurse
|
943
|
-
source
|
944
|
-
checksum
|
943
|
+
ensure => directory,
|
944
|
+
recurse => true,
|
945
|
+
source => '#{source_dir}',
|
946
|
+
checksum => sha256,
|
945
947
|
source_permissions => use_when_creating,
|
946
|
-
recurselimit
|
947
|
-
|
948
|
-
|
948
|
+
recurselimit => 2,
|
949
|
+
max_files => 4321,
|
950
|
+
ignore => 'foo.+',
|
951
|
+
links => follow,
|
949
952
|
}
|
950
953
|
MANIFEST
|
951
954
|
|
@@ -956,6 +959,7 @@ describe Puppet::Resource::Catalog::Compiler do
|
|
956
959
|
:source_permissions => :use_when_creating,
|
957
960
|
:recurse => true,
|
958
961
|
:recurselimit => 2,
|
962
|
+
:max_files => 4321,
|
959
963
|
:ignore => 'foo.+',
|
960
964
|
}
|
961
965
|
expect(Puppet::FileServing::Metadata.indirection).to receive(:search).with(source_dir, options).and_return([metadata, child_metadata])
|
@@ -28,6 +28,7 @@ describe Puppet::Node::Facts::Facter do
|
|
28
28
|
@request = double('request', :key => @name)
|
29
29
|
@environment = double('environment')
|
30
30
|
allow(@request).to receive(:environment).and_return(@environment)
|
31
|
+
allow(@request).to receive(:options).and_return({})
|
31
32
|
allow(@request.environment).to receive(:modules).and_return([])
|
32
33
|
allow(@request.environment).to receive(:modulepath).and_return([])
|
33
34
|
end
|
@@ -104,6 +105,7 @@ describe Puppet::Node::Facts::Facter do
|
|
104
105
|
expect(FileTest).to receive(:directory?).with(factpath1).and_return(true)
|
105
106
|
expect(FileTest).to receive(:directory?).with(factpath2).and_return(true)
|
106
107
|
allow(@request.environment).to receive(:modulepath).and_return([modulepath])
|
108
|
+
allow(@request).to receive(:options).and_return({})
|
107
109
|
expect(Dir).to receive(:glob).with("#{modulepath}/*/lib/facter").and_return([modulelibfacter])
|
108
110
|
expect(Dir).to receive(:glob).with("#{modulepath}/*/plugins/facter").and_return([modulepluginsfacter])
|
109
111
|
|
@@ -149,4 +151,97 @@ describe Puppet::Node::Facts::Facter do
|
|
149
151
|
Puppet::Node::Facts::Facter.setup_external_search_paths @request
|
150
152
|
end
|
151
153
|
end
|
154
|
+
|
155
|
+
describe 'when :resolve_options is true' do
|
156
|
+
let(:options) { { resolve_options: true, user_query: ["os", "timezone"], show_legacy: true } }
|
157
|
+
let(:facts) { Puppet::Node::Facts.new("foo") }
|
158
|
+
|
159
|
+
before :each do
|
160
|
+
allow(@request).to receive(:options).and_return(options)
|
161
|
+
allow(Puppet::Node::Facts).to receive(:new).and_return(facts)
|
162
|
+
allow(facts).to receive(:add_local_facts)
|
163
|
+
end
|
164
|
+
|
165
|
+
it 'should call Facter.resolve method' do
|
166
|
+
expect(Facter).to receive(:resolve).with("os timezone --show-legacy")
|
167
|
+
@facter.find(@request)
|
168
|
+
end
|
169
|
+
|
170
|
+
it 'should NOT add local facts' do
|
171
|
+
expect(facts).not_to receive(:add_local_facts)
|
172
|
+
|
173
|
+
@facter.find(@request)
|
174
|
+
end
|
175
|
+
|
176
|
+
describe 'when Facter version is lower than 4.0.40' do
|
177
|
+
before :each do
|
178
|
+
allow(Facter).to receive(:respond_to?).and_return(false)
|
179
|
+
allow(Facter).to receive(:respond_to?).with(:resolve).and_return(false)
|
180
|
+
end
|
181
|
+
|
182
|
+
it 'raises an error' do
|
183
|
+
expect { @facter.find(@request) }.to raise_error(Puppet::Error, "puppet facts show requires version 4.0.40 or greater of Facter.")
|
184
|
+
end
|
185
|
+
end
|
186
|
+
|
187
|
+
describe 'when setting up external search paths' do
|
188
|
+
let(:options) { { resolve_options: true, user_query: ["os", "timezone"], external_dir: 'some/dir' } }
|
189
|
+
let(:pluginfactdest) { File.expand_path 'plugin/dest' }
|
190
|
+
let(:modulepath) { File.expand_path 'module/foo' }
|
191
|
+
let(:modulefactsd) { File.expand_path 'module/foo/facts.d' }
|
192
|
+
|
193
|
+
before :each do
|
194
|
+
expect(FileTest).to receive(:directory?).with(pluginfactdest).and_return(true)
|
195
|
+
mod = Puppet::Module.new('foo', modulepath, @request.environment)
|
196
|
+
allow(@request.environment).to receive(:modules).and_return([mod])
|
197
|
+
Puppet[:pluginfactdest] = pluginfactdest
|
198
|
+
end
|
199
|
+
|
200
|
+
it 'should skip files' do
|
201
|
+
expect(File).to receive(:directory?).with(modulefactsd).and_return(false)
|
202
|
+
expect(Facter).to receive(:search_external).with([pluginfactdest, options[:external_dir]])
|
203
|
+
Puppet::Node::Facts::Facter.setup_external_search_paths @request
|
204
|
+
end
|
205
|
+
|
206
|
+
it 'should add directories' do
|
207
|
+
expect(File).to receive(:directory?).with(modulefactsd).and_return(true)
|
208
|
+
expect(Facter).to receive(:search_external).with([modulefactsd, pluginfactdest, options[:external_dir]])
|
209
|
+
Puppet::Node::Facts::Facter.setup_external_search_paths @request
|
210
|
+
end
|
211
|
+
end
|
212
|
+
|
213
|
+
describe 'when setting up search paths' do
|
214
|
+
let(:factpath1) { File.expand_path 'one' }
|
215
|
+
let(:factpath2) { File.expand_path 'two' }
|
216
|
+
let(:factpath) { [factpath1, factpath2].join(File::PATH_SEPARATOR) }
|
217
|
+
let(:modulepath) { File.expand_path 'module/foo' }
|
218
|
+
let(:modulelibfacter) { File.expand_path 'module/foo/lib/facter' }
|
219
|
+
let(:modulepluginsfacter) { File.expand_path 'module/foo/plugins/facter' }
|
220
|
+
let(:options) { { resolve_options: true, custom_dir: 'some/dir' } }
|
221
|
+
|
222
|
+
before :each do
|
223
|
+
expect(FileTest).to receive(:directory?).with(factpath1).and_return(true)
|
224
|
+
expect(FileTest).to receive(:directory?).with(factpath2).and_return(true)
|
225
|
+
allow(@request.environment).to receive(:modulepath).and_return([modulepath])
|
226
|
+
expect(Dir).to receive(:glob).with("#{modulepath}/*/lib/facter").and_return([modulelibfacter])
|
227
|
+
expect(Dir).to receive(:glob).with("#{modulepath}/*/plugins/facter").and_return([modulepluginsfacter])
|
228
|
+
|
229
|
+
Puppet[:factpath] = factpath
|
230
|
+
end
|
231
|
+
|
232
|
+
it 'should skip files' do
|
233
|
+
expect(FileTest).to receive(:directory?).with(modulelibfacter).and_return(false)
|
234
|
+
expect(FileTest).to receive(:directory?).with(modulepluginsfacter).and_return(false)
|
235
|
+
expect(Facter).to receive(:search).with(factpath1, factpath2, options[:custom_dir])
|
236
|
+
Puppet::Node::Facts::Facter.setup_search_paths @request
|
237
|
+
end
|
238
|
+
|
239
|
+
it 'should add directories' do
|
240
|
+
expect(FileTest).to receive(:directory?).with(modulelibfacter).and_return(true)
|
241
|
+
expect(FileTest).to receive(:directory?).with(modulepluginsfacter).and_return(false)
|
242
|
+
expect(Facter).to receive(:search).with(modulelibfacter, factpath1, factpath2, options[:custom_dir])
|
243
|
+
Puppet::Node::Facts::Facter.setup_search_paths @request
|
244
|
+
end
|
245
|
+
end
|
246
|
+
end
|
152
247
|
end
|