puppet 6.16.0-x86-mingw32 → 6.17.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.

Files changed (138) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile +4 -2
  3. data/Gemfile.lock +10 -10
  4. data/README.md +2 -2
  5. data/lib/puppet/agent.rb +2 -2
  6. data/lib/puppet/application/agent.rb +14 -3
  7. data/lib/puppet/configurer.rb +20 -12
  8. data/lib/puppet/confine.rb +1 -1
  9. data/lib/puppet/defaults.rb +25 -8
  10. data/lib/puppet/file_serving/http_metadata.rb +13 -1
  11. data/lib/puppet/file_serving/metadata.rb +4 -1
  12. data/lib/puppet/file_serving/terminus_selector.rb +7 -8
  13. data/lib/puppet/file_system/file_impl.rb +1 -1
  14. data/lib/puppet/file_system/uniquefile.rb +8 -16
  15. data/lib/puppet/forge.rb +1 -1
  16. data/lib/puppet/forge/cache.rb +1 -1
  17. data/lib/puppet/forge/repository.rb +3 -7
  18. data/lib/puppet/http/client.rb +5 -0
  19. data/lib/puppet/http/redirector.rb +9 -7
  20. data/lib/puppet/http/response.rb +19 -0
  21. data/lib/puppet/indirector.rb +1 -1
  22. data/lib/puppet/indirector/file_content/rest.rb +1 -1
  23. data/lib/puppet/indirector/file_metadata/http.rb +24 -5
  24. data/lib/puppet/indirector/file_metadata/rest.rb +2 -2
  25. data/lib/puppet/indirector/request.rb +1 -1
  26. data/lib/puppet/network/http/api/indirected_routes.rb +1 -1
  27. data/lib/puppet/network/http/api/master/v3/environment.rb +3 -0
  28. data/lib/puppet/network/http/connection_adapter.rb +6 -4
  29. data/lib/puppet/parser/ast/leaf.rb +5 -5
  30. data/lib/puppet/parser/ast/pops_bridge.rb +0 -4
  31. data/lib/puppet/parser/compiler.rb +1 -1
  32. data/lib/puppet/parser/compiler/catalog_validator/env_relationship_validator.rb +2 -0
  33. data/lib/puppet/parser/compiler/catalog_validator/site_validator.rb +2 -0
  34. data/lib/puppet/parser/environment_compiler.rb +4 -1
  35. data/lib/puppet/parser/resource.rb +3 -2
  36. data/lib/puppet/parser/resource/param.rb +6 -0
  37. data/lib/puppet/pops/evaluator/evaluator_impl.rb +5 -5
  38. data/lib/puppet/pops/issues.rb +5 -0
  39. data/lib/puppet/pops/resource/resource_type_impl.rb +2 -0
  40. data/lib/puppet/pops/validation/checker4_0.rb +10 -0
  41. data/lib/puppet/pops/validation/validator_factory_4_0.rb +1 -0
  42. data/lib/puppet/provider/package/aptitude.rb +1 -1
  43. data/lib/puppet/provider/package/yum.rb +1 -1
  44. data/lib/puppet/provider/service/windows.rb +23 -7
  45. data/lib/puppet/provider/user/useradd.rb +11 -4
  46. data/lib/puppet/reports/http.rb +2 -0
  47. data/lib/puppet/resource.rb +2 -1
  48. data/lib/puppet/resource/type.rb +8 -0
  49. data/lib/puppet/ssl/ssl_context.rb +2 -2
  50. data/lib/puppet/ssl/ssl_provider.rb +20 -1
  51. data/lib/puppet/test/test_helper.rb +8 -10
  52. data/lib/puppet/trusted_external.rb +29 -1
  53. data/lib/puppet/type.rb +12 -5
  54. data/lib/puppet/type/file.rb +38 -13
  55. data/lib/puppet/type/file/checksum.rb +4 -4
  56. data/lib/puppet/type/file/source.rb +4 -4
  57. data/lib/puppet/type/service.rb +49 -0
  58. data/lib/puppet/util.rb +39 -15
  59. data/lib/puppet/util/checksums.rb +19 -4
  60. data/lib/puppet/util/fileparsing.rb +2 -2
  61. data/lib/puppet/util/provider_features.rb +1 -1
  62. data/lib/puppet/util/reference.rb +1 -1
  63. data/lib/puppet/util/windows/api_types.rb +45 -32
  64. data/lib/puppet/util/windows/eventlog.rb +1 -6
  65. data/lib/puppet/util/windows/principal.rb +8 -6
  66. data/lib/puppet/util/windows/registry.rb +11 -11
  67. data/lib/puppet/util/windows/service.rb +43 -26
  68. data/lib/puppet/util/windows/user.rb +23 -8
  69. data/lib/puppet/version.rb +1 -1
  70. data/locales/puppet.pot +249 -221
  71. data/man/man5/puppet.conf.5 +19 -8
  72. data/man/man8/puppet-agent.8 +2 -2
  73. data/man/man8/puppet-apply.8 +1 -1
  74. data/man/man8/puppet-catalog.8 +1 -1
  75. data/man/man8/puppet-config.8 +1 -1
  76. data/man/man8/puppet-describe.8 +1 -1
  77. data/man/man8/puppet-device.8 +1 -1
  78. data/man/man8/puppet-doc.8 +1 -1
  79. data/man/man8/puppet-epp.8 +1 -1
  80. data/man/man8/puppet-facts.8 +1 -1
  81. data/man/man8/puppet-filebucket.8 +1 -1
  82. data/man/man8/puppet-generate.8 +1 -1
  83. data/man/man8/puppet-help.8 +1 -1
  84. data/man/man8/puppet-key.8 +1 -1
  85. data/man/man8/puppet-lookup.8 +1 -1
  86. data/man/man8/puppet-man.8 +1 -1
  87. data/man/man8/puppet-module.8 +1 -1
  88. data/man/man8/puppet-node.8 +1 -1
  89. data/man/man8/puppet-parser.8 +1 -1
  90. data/man/man8/puppet-plugin.8 +1 -1
  91. data/man/man8/puppet-report.8 +1 -1
  92. data/man/man8/puppet-resource.8 +1 -1
  93. data/man/man8/puppet-script.8 +1 -1
  94. data/man/man8/puppet-ssl.8 +1 -1
  95. data/man/man8/puppet-status.8 +1 -1
  96. data/man/man8/puppet.8 +2 -2
  97. data/spec/integration/application/agent_spec.rb +89 -0
  98. data/spec/integration/defaults_spec.rb +1 -2
  99. data/spec/integration/network/http_pool_spec.rb +26 -9
  100. data/spec/integration/parser/compiler_spec.rb +11 -0
  101. data/spec/integration/type/file_spec.rb +1 -1
  102. data/spec/integration/util/windows/registry_spec.rb +7 -7
  103. data/spec/integration/util/windows/user_spec.rb +40 -5
  104. data/spec/unit/configurer/fact_handler_spec.rb +4 -4
  105. data/spec/unit/context/trusted_information_spec.rb +10 -4
  106. data/spec/unit/file_serving/http_metadata_spec.rb +37 -14
  107. data/spec/unit/file_serving/terminus_selector_spec.rb +45 -26
  108. data/spec/unit/http/client_spec.rb +64 -8
  109. data/spec/unit/http/response_spec.rb +6 -0
  110. data/spec/unit/indirector/file_metadata/http_spec.rb +27 -0
  111. data/spec/unit/indirector/request_spec.rb +1 -1
  112. data/spec/unit/interface_spec.rb +3 -3
  113. data/spec/unit/network/http/api/indirected_routes_spec.rb +2 -1
  114. data/spec/unit/network/http/connection_spec.rb +42 -32
  115. data/spec/unit/parser/ast/block_expression_spec.rb +1 -1
  116. data/spec/unit/parser/environment_compiler_spec.rb +7 -0
  117. data/spec/unit/parser/scope_spec.rb +1 -1
  118. data/spec/unit/pops/evaluator/evaluating_parser_spec.rb +15 -1
  119. data/spec/unit/pops/loaders/loaders_spec.rb +1 -1
  120. data/spec/unit/pops/types/type_calculator_spec.rb +1 -11
  121. data/spec/unit/provider/service/windows_spec.rb +22 -14
  122. data/spec/unit/provider/user/openbsd_spec.rb +1 -0
  123. data/spec/unit/provider/user/useradd_spec.rb +22 -16
  124. data/spec/unit/resource_spec.rb +3 -3
  125. data/spec/unit/ssl/ssl_provider_spec.rb +69 -43
  126. data/spec/unit/test/test_helper_spec.rb +17 -0
  127. data/spec/unit/transaction/report_spec.rb +1 -1
  128. data/spec/unit/type/file/source_spec.rb +3 -3
  129. data/spec/unit/type/file_spec.rb +122 -96
  130. data/spec/unit/type/service_spec.rb +176 -0
  131. data/spec/unit/type_spec.rb +50 -0
  132. data/spec/unit/util/checksums_spec.rb +16 -0
  133. data/spec/unit/util/windows/api_types_spec.rb +104 -40
  134. data/spec/unit/util/windows/service_spec.rb +4 -4
  135. data/spec/unit/util_spec.rb +3 -3
  136. data/spec/unit/x509/cert_provider_spec.rb +1 -1
  137. metadata +5 -5
  138. data/spec/integration/test/test_helper_spec.rb +0 -31
@@ -0,0 +1,17 @@
1
+ require 'spec_helper'
2
+
3
+ describe "TestHelper" do
4
+ context "#after_each_test" do
5
+ it "restores the original environment" do
6
+ varname = 'test_helper_spec-test_variable'
7
+ Puppet::Util.set_env(varname, "\u16A0")
8
+
9
+ expect(Puppet::Util.get_env(varname)).to eq("\u16A0")
10
+
11
+ # Prematurely trigger the after_each_test method
12
+ Puppet::Test::TestHelper.after_each_test
13
+
14
+ expect(Puppet::Util::get_env(varname)).to be_nil
15
+ end
16
+ end
17
+ end
@@ -663,7 +663,7 @@ Version:
663
663
  :status => stringifier.convert('success'),
664
664
  }
665
665
 
666
- event = Puppet::Transaction::Event.new(event_hash)
666
+ event = Puppet::Transaction::Event.new(**event_hash)
667
667
 
668
668
  status = Puppet::Resource::Status.new(Puppet::Type.type(:notify).new(:title => "a resource"))
669
669
  status.changed = true
@@ -22,8 +22,8 @@ describe Puppet::Type.type(:file).attrclass(:source), :uses_checksums => true do
22
22
  @foobar = make_absolute("/foo/bar baz")
23
23
  @feebooz = make_absolute("/fee/booz baz")
24
24
 
25
- @foobar_uri = URI.unescape(Puppet::Util.path_to_uri(@foobar).to_s)
26
- @feebooz_uri = URI.unescape(Puppet::Util.path_to_uri(@feebooz).to_s)
25
+ @foobar_uri = Puppet::Util.uri_unescape(Puppet::Util.path_to_uri(@foobar).to_s)
26
+ @feebooz_uri = Puppet::Util.uri_unescape(Puppet::Util.path_to_uri(@feebooz).to_s)
27
27
  end
28
28
 
29
29
  it "should be a subclass of Parameter" do
@@ -82,7 +82,7 @@ describe Puppet::Type.type(:file).attrclass(:source), :uses_checksums => true do
82
82
  describe "#munge" do
83
83
  it "should prefix file scheme to absolute paths" do
84
84
  resource[:source] = filename
85
- expect(resource[:source]).to eq([URI.unescape(Puppet::Util.path_to_uri(filename).to_s)])
85
+ expect(resource[:source]).to eq([Puppet::Util.uri_unescape(Puppet::Util.path_to_uri(filename).to_s)])
86
86
  end
87
87
 
88
88
  %w[file puppet].each do |scheme|
@@ -3,6 +3,34 @@ require 'spec_helper'
3
3
  describe Puppet::Type.type(:file) do
4
4
  include PuppetSpec::Files
5
5
 
6
+ # precomputed checksum values for FILE_CONTENT
7
+ FILE_CONTENT = 'file content'.freeze
8
+ CHECKSUM_VALUES = {
9
+ md5: 'd10b4c3ff123b26dc068d43a8bef2d23',
10
+ md5lite: 'd10b4c3ff123b26dc068d43a8bef2d23',
11
+ sha256: 'e0ac3601005dfa1864f5392aabaf7d898b1b5bab854f1acb4491bcd806b76b0c',
12
+ sha256lite: 'e0ac3601005dfa1864f5392aabaf7d898b1b5bab854f1acb4491bcd806b76b0c',
13
+ sha1: '87758871f598e1a3b4679953589ae2f57a0bb43c',
14
+ sha1lite: '87758871f598e1a3b4679953589ae2f57a0bb43c',
15
+ sha224: '2aefaaa5f4d8f17f82f3e1bb407e190cede9aa1311fa4533ce505531',
16
+ sha384: '61c7783501ebd90233650357fefbe5a141b7618f907b8f043bbaa92c0f610c785a641ddd479fa81d650cd86e29aa6858',
17
+ sha512: '2fb1877301854ac92dd518018f97407a0a88bb696bfef0a51e9efbd39917353500009e15bd72c3f0e4bf690115870bfab926565d5ad97269d922dbbb41261221',
18
+ mtime: 'Jan 26 13:59:49 2016',
19
+ ctime: 'Jan 26 13:59:49 2016'
20
+ }.freeze
21
+
22
+ INVALID_CHECKSUM_VALUES = {
23
+ md5: '00000000000000000000000000000000',
24
+ md5lite: '00000000000000000000000000000000',
25
+ sha256: '0000000000000000000000000000000000000000000000000000000000000000',
26
+ sha256lite: '0000000000000000000000000000000000000000000000000000000000000000',
27
+ sha1: '0000000000000000000000000000000000000000',
28
+ sha1lite: '0000000000000000000000000000000000000000',
29
+ sha224: '00000000000000000000000000000000000000000000000000000000',
30
+ sha384: '000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000',
31
+ sha512: '00000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000'
32
+ }.freeze
33
+
6
34
  let(:path) { tmpfile('file_testing') }
7
35
  let(:file) { described_class.new(:path => path, :catalog => catalog) }
8
36
  let(:provider) { file.provider }
@@ -791,7 +819,7 @@ describe Puppet::Type.type(:file) do
791
819
  let(:sources) do
792
820
  h = {}
793
821
  %w{/a /b /c /d}.each do |key|
794
- h[key] = URI.unescape(Puppet::Util.path_to_uri(File.expand_path(key)).to_s)
822
+ h[key] = Puppet::Util.uri_unescape(Puppet::Util.path_to_uri(File.expand_path(key)).to_s)
795
823
  end
796
824
  h
797
825
  end
@@ -1108,38 +1136,6 @@ describe Puppet::Type.type(:file) do
1108
1136
  end
1109
1137
 
1110
1138
  describe "#write" do
1111
- describe "when validating the checksum" do
1112
- before { allow(file).to receive(:validate_checksum?).and_return(true) }
1113
-
1114
- it "should fail if the checksum parameter and content checksums do not match" do
1115
- checksum = double('checksum_parameter', :sum => 'checksum_b', :sum_file => 'checksum_b')
1116
- allow(file).to receive(:parameter).with(:checksum).and_return(checksum)
1117
- allow(file).to receive(:parameter).with(:source).and_return(nil)
1118
-
1119
-
1120
- property = double('content_property', :actual_content => "something", :length => "something".length, :write => 'checksum_a')
1121
- allow(file).to receive(:property).with(:content).and_return(property)
1122
-
1123
- expect { file.write property }.to raise_error(Puppet::Error) end
1124
- end
1125
-
1126
- describe "when not validating the checksum" do
1127
- before do
1128
- allow(file).to receive(:validate_checksum?).and_return(false)
1129
- end
1130
-
1131
- it "should not fail if the checksum property and content checksums do not match" do
1132
- checksum = double('checksum_parameter', :sum => 'checksum_b')
1133
- allow(file).to receive(:parameter).with(:checksum).and_return(checksum)
1134
- allow(file).to receive(:parameter).with(:source).and_return(nil)
1135
-
1136
- property = double('content_property', :actual_content => "something", :length => "something".length, :write => 'checksum_a')
1137
- allow(file).to receive(:property).with(:content).and_return(property)
1138
-
1139
- expect { file.write property }.to_not raise_error
1140
- end
1141
- end
1142
-
1143
1139
  describe "when resource mode is supplied" do
1144
1140
  before do
1145
1141
  allow(file).to receive(:property_fix)
@@ -1191,7 +1187,7 @@ describe Puppet::Type.type(:file) do
1191
1187
  describe "when resource mode is not supplied" do
1192
1188
  context "and content is supplied" do
1193
1189
  it "should default to 0644 mode" do
1194
- file = described_class.new(:path => path, :content => "file content")
1190
+ file = described_class.new(:path => path, :content => FILE_CONTENT)
1195
1191
 
1196
1192
  file.write file.parameter(:content)
1197
1193
 
@@ -1214,35 +1210,6 @@ describe Puppet::Type.type(:file) do
1214
1210
  end
1215
1211
  end
1216
1212
 
1217
- describe "#fail_if_checksum_is_wrong" do
1218
- it "should fail if the checksum of the file doesn't match the expected one" do
1219
- expect do
1220
- allow(file.parameter(:checksum)).to receive(:sum_file).and_return('wrong!!')
1221
- file.instance_eval do
1222
- fail_if_checksum_is_wrong(self[:path], 'anything!')
1223
- end
1224
- end.to raise_error(Puppet::Error, /File written to disk did not match checksum/)
1225
- end
1226
-
1227
- it "should not fail if the checksum is correct" do
1228
- expect do
1229
- allow(file.parameter(:checksum)).to receive(:sum_file).and_return('anything!')
1230
- file.instance_eval do
1231
- fail_if_checksum_is_wrong(self[:path], 'anything!')
1232
- end
1233
- end.not_to raise_error
1234
- end
1235
-
1236
- it "should not fail if the checksum is absent" do
1237
- expect do
1238
- allow(file.parameter(:checksum)).to receive(:sum_file).and_return(nil)
1239
- file.instance_eval do
1240
- fail_if_checksum_is_wrong(self[:path], 'anything!')
1241
- end
1242
- end.not_to raise_error
1243
- end
1244
- end
1245
-
1246
1213
  describe "#write_temporary_file?" do
1247
1214
  it "should be true if the file has specified content" do
1248
1215
  file[:content] = 'some content'
@@ -1462,7 +1429,7 @@ describe Puppet::Type.type(:file) do
1462
1429
  expect(Puppet::FileServing::Metadata.indirection).to receive(:find).with(source, anything).and_return(metadata)
1463
1430
 
1464
1431
  uri = file.parameters[:source].uri
1465
- expect(URI.unescape(uri.path)).to eq(filename)
1432
+ expect(Puppet::Util.uri_unescape(uri.path)).to eq(filename)
1466
1433
  expect(uri.path.encoding).to eq(Encoding::UTF_8)
1467
1434
  end
1468
1435
 
@@ -1486,29 +1453,16 @@ describe Puppet::Type.type(:file) do
1486
1453
  expect_any_instance_of(Puppet::Indirector::FileMetadata::Rest).to receive(:find).with(request_key(filename[1..-1])).and_return(metadata)
1487
1454
 
1488
1455
  uri = file.parameters[:source].uri
1489
- expect(URI.unescape(uri.path)).to eq(filename)
1456
+ expect(Puppet::Util.uri_unescape(uri.path)).to eq(filename)
1490
1457
  expect(uri.path.encoding).to eq(Encoding::UTF_8)
1491
1458
  end
1492
1459
  end
1493
1460
 
1494
1461
  describe "when using source" do
1462
+ let(:source) { tmpfile('file_source') }
1463
+
1495
1464
  before do
1496
- file[:source] = File.expand_path('/one')
1497
- # Contents of an empty file generate the below hash values
1498
- # in case you need to add support for additional algorithms in future
1499
- @checksum_values = {
1500
- :md5 => 'd41d8cd98f00b204e9800998ecf8427e',
1501
- :md5lite => 'd41d8cd98f00b204e9800998ecf8427e',
1502
- :sha256 => 'e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855',
1503
- :sha256lite => 'e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855',
1504
- :sha1 => 'da39a3ee5e6b4b0d3255bfef95601890afd80709',
1505
- :sha1lite => 'da39a3ee5e6b4b0d3255bfef95601890afd80709',
1506
- :sha224 => 'd14a028c2a3a2bc9476102bb288234c415a2b01f828ea62ac5b3e42f',
1507
- :sha384 => '38b060a751ac96384cd9327eb1b1e36a21fdb71114be07434c0cc7bf63f6e1da274edebfe76f65fbd51ad2f14898b95b',
1508
- :sha512 => 'cf83e1357eefb8bdf1542850d66d8007d620e4050b5715dc83f4a921d36ce9ce47d0d13c5d85f2b0ff8318d2877eec2f63b931bd47417a81a538327af927da3e',
1509
- :mtime => 'Jan 26 13:59:49 2016',
1510
- :ctime => 'Jan 26 13:59:49 2016'
1511
- }
1465
+ file[:source] = source
1512
1466
  end
1513
1467
 
1514
1468
  Puppet::Type::File::ParameterChecksum.value_collection.values.reject {|v| v == :none}.each do |checksum_type|
@@ -1527,9 +1481,51 @@ describe Puppet::Type.type(:file) do
1527
1481
  end
1528
1482
 
1529
1483
  it 'should validate a valid checksum_value' do
1530
- file[:checksum_value] = @checksum_values[checksum_type]
1484
+ file[:checksum_value] = CHECKSUM_VALUES[checksum_type]
1531
1485
  expect { file.validate }.to_not raise_error
1532
1486
  end
1487
+
1488
+ it 'fails if the checksum_value parameter and written file do not match' do
1489
+ skip if checksum_type =~ /^(ctime|mtime)/
1490
+
1491
+ File.write(source, FILE_CONTENT)
1492
+ file[:checksum_value] = INVALID_CHECKSUM_VALUES[checksum_type]
1493
+
1494
+ expect {
1495
+ file.property(:checksum_value).sync
1496
+ }.to raise_error(Puppet::Error, /File written to disk did not match desired checksum/)
1497
+
1498
+ expect(Puppet::FileSystem).to_not be_exist(file[:path])
1499
+ end
1500
+
1501
+ it 'fails if the checksum_value parameter does not match, but the metadata does' do
1502
+ skip if checksum_type =~ /^(ctime|mtime)/
1503
+
1504
+ File.write(source, FILE_CONTENT)
1505
+ file[:checksum_value] = INVALID_CHECKSUM_VALUES[checksum_type]
1506
+ allow(file.parameter(:source).metadata).to receive(:checksum).and_return(file[:checksum_value])
1507
+
1508
+ expect {
1509
+ file.property(:checksum_value).sync
1510
+ }.to raise_error(Puppet::Error, /File written to disk did not match desired checksum/)
1511
+
1512
+ expect(Puppet::FileSystem).to_not be_exist(file[:path])
1513
+ end
1514
+
1515
+ it 'replaces a file from a source when the checksum matches' do
1516
+ File.write(source, FILE_CONTENT)
1517
+ file[:checksum_value] = CHECKSUM_VALUES[checksum_type]
1518
+
1519
+ file.property(:checksum_value).sync
1520
+ checksum = file.parameter(:checksum).sum_file(file[:path])
1521
+
1522
+ if checksum_type =~ /^(ctime|mtime)/
1523
+ # file on disk ctime/mtime will be later than expected time
1524
+ expect(checksum).to match(/{#{checksum_type}}/)
1525
+ else
1526
+ expect(checksum).to eq("{#{checksum_type}}#{file[:checksum_value]}")
1527
+ end
1528
+ end
1533
1529
  end
1534
1530
  end
1535
1531
 
@@ -1591,19 +1587,8 @@ describe Puppet::Type.type(:file) do
1591
1587
  end
1592
1588
 
1593
1589
  describe "when using content" do
1594
- before do
1595
- file[:content] = 'file contents'
1596
- @checksum_values = {
1597
- :md5 => 'd41d8cd98f00b204e9800998ecf8427e',
1598
- :md5lite => 'd41d8cd98f00b204e9800998ecf8427e',
1599
- :sha256 => 'e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855',
1600
- :sha256lite => 'e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855',
1601
- :sha1 => 'da39a3ee5e6b4b0d3255bfef95601890afd80709',
1602
- :sha1lite => 'da39a3ee5e6b4b0d3255bfef95601890afd80709',
1603
- :sha224 => 'd14a028c2a3a2bc9476102bb288234c415a2b01f828ea62ac5b3e42f',
1604
- :sha384 => '38b060a751ac96384cd9327eb1b1e36a21fdb71114be07434c0cc7bf63f6e1da274edebfe76f65fbd51ad2f14898b95b',
1605
- :sha512 => 'cf83e1357eefb8bdf1542850d66d8007d620e4050b5715dc83f4a921d36ce9ce47d0d13c5d85f2b0ff8318d2877eec2f63b931bd47417a81a538327af927da3e',
1606
- }
1590
+ before :each do
1591
+ file[:content] = FILE_CONTENT
1607
1592
  end
1608
1593
 
1609
1594
  (Puppet::Type::File::ParameterChecksum.value_collection.values - SOURCE_ONLY_CHECKSUMS).each do |checksum_type|
@@ -1622,9 +1607,43 @@ describe Puppet::Type.type(:file) do
1622
1607
  end
1623
1608
 
1624
1609
  it 'should validate a valid checksum_value' do
1625
- file[:checksum_value] = @checksum_values[checksum_type]
1610
+ file[:checksum_value] = CHECKSUM_VALUES[checksum_type]
1626
1611
  expect { file.validate }.to_not raise_error
1627
1612
  end
1613
+
1614
+ it 'fails if the checksum_value parameter and written file do not match' do
1615
+ file[:checksum_value] = INVALID_CHECKSUM_VALUES[checksum_type]
1616
+
1617
+ expect {
1618
+ file.property(:content).sync
1619
+ }.to raise_error(Puppet::Error, /File written to disk did not match desired checksum/)
1620
+
1621
+ expect(Puppet::FileSystem).to_not be_exist(file[:path])
1622
+ end
1623
+
1624
+ it 'fails if the calculated checksum for the content and written file do not match' do
1625
+ allow(file.parameter(:checksum)).to receive(:sum).and_return(INVALID_CHECKSUM_VALUES[checksum_type])
1626
+
1627
+ expect {
1628
+ file.property(:content).sync
1629
+ }.to raise_error(Puppet::Error, /File written to disk did not match desired checksum/)
1630
+
1631
+ expect(Puppet::FileSystem).to_not be_exist(file[:path])
1632
+ end
1633
+
1634
+ it 'replaces a file from content when the checksum matches' do
1635
+ file[:checksum_value] = CHECKSUM_VALUES[checksum_type]
1636
+
1637
+ file.property(:content).sync
1638
+ checksum = file.parameter(:checksum).sum_file(file[:path])
1639
+
1640
+ if checksum_type =~ /^(ctime|mtime)/
1641
+ # file on disk ctime/mtime will be later than expected time
1642
+ expect(checksum).to match(/{#{checksum_type}}/)
1643
+ else
1644
+ expect(checksum).to eq("{#{checksum_type}}#{file[:checksum_value]}")
1645
+ end
1646
+ end
1628
1647
  end
1629
1648
  end
1630
1649
 
@@ -1657,6 +1676,13 @@ describe Puppet::Type.type(:file) do
1657
1676
  file[:checksum_value] = ''
1658
1677
  expect { file.validate }.to_not raise_error
1659
1678
  end
1679
+
1680
+ it 'writes a file' do
1681
+ file[:ensure] = :file
1682
+ file.property(:ensure).sync
1683
+
1684
+ expect(file.parameter(:checksum).sum_file(file[:path])).to eq('{none}')
1685
+ end
1660
1686
  end
1661
1687
 
1662
1688
  describe "when auditing" do
@@ -145,6 +145,166 @@ describe test_title, "when validating attribute values" do
145
145
  end
146
146
  end
147
147
 
148
+ describe "the service logon credentials" do
149
+ before do
150
+ provider_class_with_logon_credentials = Puppet::Type.type(:service).provide(:simple) do
151
+ has_features :manages_logon_credentials
152
+ def logonpassword=(value) end
153
+ end
154
+ allow(Puppet::Type.type(:service)).to receive(:defaultprovider).and_return(provider_class_with_logon_credentials)
155
+ end
156
+
157
+ describe "the 'logonaccount' property" do
158
+ it "should not be munged nor checked when not on Windows" do
159
+ allow(Puppet::Util::Platform).to receive(:windows?).and_return(false)
160
+ service = Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'NonWindowsUser')
161
+
162
+ expect { service }.not_to raise_error
163
+ expect(service[:logonaccount]).to eq('NonWindowsUser')
164
+ end
165
+
166
+ context "when on Windows", :if => Puppet::Util::Platform.windows? do
167
+ before do
168
+ allow(Puppet::Util::Windows::ADSI).to receive(:computer_name).and_return("myPC")
169
+ allow(Puppet::Util::Windows::User).to receive(:default_system_account?).and_return(true)
170
+ end
171
+
172
+ ['LocalSystem', '.\LocalSystem', 'myPC\LocalSystem', 'lOcALsysTem'].each do |user_input|
173
+ it "should succesfully munge #{user_input} to 'LocalSystem'" do
174
+ service = Puppet::Type.type(:service).new(:name => "yay", :logonaccount => user_input)
175
+
176
+ expect { service }.not_to raise_error
177
+ expect(service[:logonaccount]).to eq('LocalSystem')
178
+ end
179
+ end
180
+
181
+ it "should succesfully munge local account" do
182
+ allow(Puppet::Util::Windows::SID).to receive(:name_to_principal).and_return(Puppet::Util::Windows::SID::Principal.new("myUser", nil, nil, "myPC", :SidTypeUser))
183
+ service = Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'myUser')
184
+
185
+ expect { service }.not_to raise_error
186
+ expect(service[:logonaccount]).to eq('.\myUser')
187
+ end
188
+
189
+ it "should succesfully munge domain account" do
190
+ allow(Puppet::Util::Windows::SID).to receive(:name_to_principal).and_return(Puppet::Util::Windows::SID::Principal.new("DomainUser", nil, nil, "myDomain", :SidTypeUser))
191
+ service = Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'DomainUser')
192
+
193
+ expect { service }.not_to raise_error
194
+ expect(service[:logonaccount]).to eq('myDomain\DomainUser')
195
+ end
196
+
197
+ it "should succesfully munge well known user" do
198
+ allow(Puppet::Util::Windows::SID).to receive(:name_to_principal).and_return(Puppet::Util::Windows::SID::Principal.new("LOCAL SERVICE", nil, nil, "NT AUTHORITY", :SidTypeWellKnownGroup))
199
+ service = Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'LocalService')
200
+
201
+ expect { service }.not_to raise_error
202
+ expect(service[:logonaccount]).to eq('NT AUTHORITY\LOCAL SERVICE')
203
+ end
204
+
205
+ it "should succesfully munge a SID" do
206
+ allow(Puppet::Util::Windows::SID).to receive(:name_to_principal).and_return(Puppet::Util::Windows::SID::Principal.new("NETWORK SERVICE", nil, nil, "NT AUTHORITY", :SidTypeUser))
207
+ service = Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'S-1-5-20')
208
+
209
+ expect { service }.not_to raise_error
210
+ expect(service[:logonaccount]).to eq('NT AUTHORITY\NETWORK SERVICE')
211
+ end
212
+
213
+ it "should fail when account is invalid" do
214
+ allow(Puppet::Util::Windows::SID).to receive(:name_to_principal).and_return(nil)
215
+ expect { Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'InvalidUser') }.to raise_error(Puppet::Error, /\"InvalidUser\" is not a valid account/)
216
+ end
217
+
218
+ it "should fail when sid type is not user or well known user" do
219
+ allow(Puppet::Util::Windows::SID).to receive(:name_to_principal).and_return(Puppet::Util::Windows::SID::Principal.new("Administrators", nil, nil, "BUILTIN", :SidTypeAlias))
220
+ expect { Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'Administrators') }.to raise_error(Puppet::Error, /\"Administrators\" is not a valid account/)
221
+ end
222
+ end
223
+ end
224
+
225
+ describe "the logonpassword parameter" do
226
+ it "should fail when logonaccount is not being managed as well" do
227
+ expect { Puppet::Type.type(:service).new(:name => "yay", :logonpassword => 'myPass') }.to raise_error(Puppet::Error, /The 'logonaccount' parameter is mandatory when setting 'logonpassword'./)
228
+ end
229
+
230
+ it "should default to empty string when only logonaccount is being managed" do
231
+ allow(Puppet::Util::Platform).to receive(:windows?).and_return(false)
232
+ service = Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'myUser')
233
+
234
+ expect { service }.not_to raise_error
235
+ expect(service[:logonpassword]).to eq("")
236
+ end
237
+
238
+ it "should default to nil when not even logonaccount is being managed" do
239
+ service = Puppet::Type.type(:service).new(:name => "yay")
240
+ expect(service[:logonpassword]).to eq(nil)
241
+ end
242
+
243
+ it "should fail when logonpassword includes the ':' character" do
244
+ allow(Puppet::Util::Platform).to receive(:windows?).and_return(false)
245
+ expect { Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'myUser', :logonpassword => 'my:Pass') }.to raise_error(Puppet::Error, /Passwords cannot include ':'/)
246
+ end
247
+
248
+ it "should not further check the password against given account when not on Windows" do
249
+ allow(Puppet::Util::Platform).to receive(:windows?).and_return(false)
250
+ expect { Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'myUser', :logonpassword => 'myPass') }.not_to raise_error
251
+ end
252
+
253
+ context "when on Windows", :if => Puppet::Util::Platform.windows? do
254
+ before do
255
+ allow(Puppet::Util::Windows::ADSI).to receive(:computer_name).and_return("myPC")
256
+ allow(Puppet::Util::Windows::SID).to receive(:name_to_principal).and_return(name_to_principal_result)
257
+ end
258
+
259
+ it "should pass validation when given account is 'LocalSystem'" do
260
+ allow(Puppet::Util::Windows::User).to receive(:localsystem?).with('LocalSystem').and_return(true)
261
+ allow(Puppet::Util::Windows::User).to receive(:default_system_account?).with('LocalSystem').and_return(false)
262
+
263
+ expect(Puppet::Util::Windows::SID).not_to receive(:name_to_principal)
264
+ expect(Puppet::Util::Windows::User).not_to receive(:password_is?)
265
+ expect { Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'LocalSystem') }.not_to raise_error
266
+ end
267
+
268
+ ['LOCAL SERVICE', 'NETWORK SERVICE', 'SYSTEM'].each do |predefined_local_account|
269
+ describe "when given account is #{predefined_local_account}" do
270
+ let(:name_to_principal_result) do
271
+ Puppet::Util::Windows::SID::Principal.new(predefined_local_account, nil, nil, "NT AUTHORITY", :SidTypeUser)
272
+ end
273
+
274
+ it "should pass validation" do
275
+ allow(Puppet::Util::Windows::User).to receive(:localsystem?).with(predefined_local_account).and_return(false)
276
+ expect(Puppet::Util::Windows::User).to receive(:default_system_account?).with("NT AUTHORITY\\#{predefined_local_account}").and_return(true)
277
+
278
+ expect(Puppet::Util::Windows::User).not_to receive(:password_is?)
279
+ expect { Puppet::Type.type(:service).new(:name => "yay", :logonaccount => predefined_local_account) }.not_to raise_error
280
+ end
281
+ end
282
+ end
283
+
284
+ let(:name_to_principal_result) do
285
+ Puppet::Util::Windows::SID::Principal.new("myUser", nil, nil, "myPC", :SidTypeUser)
286
+ end
287
+
288
+ describe "when given logonaccount is not a predefined local account" do
289
+ before do
290
+ allow(Puppet::Util::Windows::User).to receive(:localsystem?).with('myUser').and_return(false)
291
+ allow(Puppet::Util::Windows::User).to receive(:default_system_account?).with('.\\myUser').and_return(false)
292
+ end
293
+
294
+ it "should pass validation if password is proven correct" do
295
+ allow(Puppet::Util::Windows::User).to receive(:password_is?).with('myUser', 'myPass', '.').and_return(true)
296
+ expect { Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'myUser', :logonpassword => 'myPass') }.not_to raise_error
297
+ end
298
+
299
+ it "should not pass validation if password check fails" do
300
+ allow(Puppet::Util::Windows::User).to receive(:password_is?).with('myUser', 'myWrongPass', '.').and_return(false)
301
+ expect { Puppet::Type.type(:service).new(:name => "yay", :logonaccount => 'myUser', :logonpassword => 'myWrongPass') }.to raise_error(Puppet::Error, /The given password is invalid for user '.\\myUser'/)
302
+ end
303
+ end
304
+ end
305
+ end
306
+ end
307
+
148
308
  it "should support :true as a value to :hasstatus" do
149
309
  srv = Puppet::Type.type(:service).new(:name => "yay", :hasstatus => :true)
150
310
  expect(srv[:hasstatus]).to eq(:true)
@@ -314,6 +474,22 @@ describe test_title, "when changing the host" do
314
474
 
315
475
  @service.property(:ensure).sync
316
476
  end
477
+
478
+ it "should sync the service's logonaccount state when changing the state of :ensure if :logonaccount is being managed" do
479
+ allow(@service.provider.class).to receive(:supports_parameter?).and_return(true)
480
+ allow(Puppet::Util::Platform).to receive(:windows?).and_return(false)
481
+
482
+ @service[:ensure] = :stopped
483
+ @service[:logonaccount] = 'LocalSystem'
484
+
485
+ expect(@service.property(:logonaccount)).to receive(:retrieve).and_return("MyUser")
486
+ expect(@service.property(:logonaccount)).to receive(:insync?).and_return(false)
487
+ expect(@service.property(:logonaccount)).to receive(:sync)
488
+
489
+ allow(@service.provider).to receive(:stop)
490
+
491
+ @service.property(:ensure).sync
492
+ end
317
493
  end
318
494
 
319
495
  describe test_title, "when refreshing the service" do