puppet 5.5.20 → 5.5.21

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 (92) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile.lock +19 -19
  3. data/lib/puppet/agent.rb +3 -3
  4. data/lib/puppet/application/agent.rb +3 -1
  5. data/lib/puppet/daemon.rb +1 -1
  6. data/lib/puppet/defaults.rb +2 -2
  7. data/lib/puppet/file_system/uniquefile.rb +4 -0
  8. data/lib/puppet/network/http/api/indirected_routes.rb +1 -1
  9. data/lib/puppet/network/http/api/master/v3/environment.rb +3 -0
  10. data/lib/puppet/parser/compiler/catalog_validator/env_relationship_validator.rb +2 -0
  11. data/lib/puppet/parser/compiler/catalog_validator/site_validator.rb +2 -0
  12. data/lib/puppet/parser/environment_compiler.rb +3 -0
  13. data/lib/puppet/parser/resource.rb +3 -2
  14. data/lib/puppet/parser/resource/param.rb +6 -0
  15. data/lib/puppet/pops/issues.rb +5 -0
  16. data/lib/puppet/pops/resource/resource_type_impl.rb +2 -0
  17. data/lib/puppet/pops/validation/checker4_0.rb +10 -0
  18. data/lib/puppet/pops/validation/validator_factory_4_0.rb +1 -0
  19. data/lib/puppet/provider/package/dnfmodule.rb +24 -4
  20. data/lib/puppet/provider/package/pip.rb +6 -4
  21. data/lib/puppet/provider/package/zypper.rb +1 -0
  22. data/lib/puppet/provider/service/systemd.rb +22 -4
  23. data/lib/puppet/provider/user/useradd.rb +16 -5
  24. data/lib/puppet/resource/type.rb +8 -0
  25. data/lib/puppet/test/test_helper.rb +8 -10
  26. data/lib/puppet/type.rb +6 -0
  27. data/lib/puppet/type/package.rb +16 -1
  28. data/lib/puppet/type/service.rb +1 -7
  29. data/lib/puppet/type/user.rb +1 -7
  30. data/lib/puppet/util.rb +12 -13
  31. data/lib/puppet/util/log/destinations.rb +1 -10
  32. data/lib/puppet/util/windows/api_types.rb +45 -32
  33. data/lib/puppet/util/windows/eventlog.rb +1 -6
  34. data/lib/puppet/util/windows/principal.rb +8 -6
  35. data/lib/puppet/util/windows/registry.rb +11 -11
  36. data/lib/puppet/version.rb +1 -1
  37. data/locales/puppet.pot +97 -93
  38. data/man/man5/puppet.conf.5 +2 -2
  39. data/man/man8/puppet-agent.8 +2 -2
  40. data/man/man8/puppet-apply.8 +1 -1
  41. data/man/man8/puppet-ca.8 +1 -1
  42. data/man/man8/puppet-catalog.8 +1 -1
  43. data/man/man8/puppet-cert.8 +1 -1
  44. data/man/man8/puppet-certificate.8 +1 -1
  45. data/man/man8/puppet-certificate_request.8 +1 -1
  46. data/man/man8/puppet-certificate_revocation_list.8 +1 -1
  47. data/man/man8/puppet-config.8 +1 -1
  48. data/man/man8/puppet-describe.8 +1 -1
  49. data/man/man8/puppet-device.8 +1 -1
  50. data/man/man8/puppet-doc.8 +1 -1
  51. data/man/man8/puppet-epp.8 +1 -1
  52. data/man/man8/puppet-facts.8 +1 -1
  53. data/man/man8/puppet-filebucket.8 +1 -1
  54. data/man/man8/puppet-generate.8 +1 -1
  55. data/man/man8/puppet-help.8 +1 -1
  56. data/man/man8/puppet-key.8 +1 -1
  57. data/man/man8/puppet-lookup.8 +1 -1
  58. data/man/man8/puppet-man.8 +1 -1
  59. data/man/man8/puppet-master.8 +1 -1
  60. data/man/man8/puppet-module.8 +1 -1
  61. data/man/man8/puppet-node.8 +1 -1
  62. data/man/man8/puppet-parser.8 +1 -1
  63. data/man/man8/puppet-plugin.8 +1 -1
  64. data/man/man8/puppet-report.8 +1 -1
  65. data/man/man8/puppet-resource.8 +1 -1
  66. data/man/man8/puppet-script.8 +1 -1
  67. data/man/man8/puppet-status.8 +1 -1
  68. data/man/man8/puppet.8 +2 -2
  69. data/spec/fixtures/unit/provider/package/dnfmodule/{dnf-module-list-enabled.txt → dnf-module-list.txt} +6 -0
  70. data/spec/fixtures/unit/provider/service/systemd/list_unit_files_services +9 -0
  71. data/spec/integration/defaults_spec.rb +1 -2
  72. data/spec/integration/parser/compiler_spec.rb +11 -0
  73. data/spec/integration/util/windows/adsi_spec.rb +5 -0
  74. data/spec/integration/util/windows/registry_spec.rb +7 -7
  75. data/spec/unit/agent_spec.rb +1 -1
  76. data/spec/unit/daemon_spec.rb +0 -1
  77. data/spec/unit/file_system/uniquefile_spec.rb +11 -0
  78. data/spec/unit/network/http/api/indirected_routes_spec.rb +2 -1
  79. data/spec/unit/parser/environment_compiler_spec.rb +7 -0
  80. data/spec/unit/provider/package/dnfmodule_spec.rb +25 -5
  81. data/spec/unit/provider/package/pip_spec.rb +42 -16
  82. data/spec/unit/provider/package/zypper_spec.rb +13 -0
  83. data/spec/unit/provider/service/systemd_spec.rb +93 -20
  84. data/spec/unit/provider/user/openbsd_spec.rb +1 -0
  85. data/spec/unit/provider/user/useradd_spec.rb +30 -16
  86. data/spec/unit/test/test_helper_spec.rb +17 -0
  87. data/spec/unit/type/service_spec.rb +9 -8
  88. data/spec/unit/type/user_spec.rb +19 -13
  89. data/spec/unit/util/log/destinations_spec.rb +1 -29
  90. data/spec/unit/util/windows/api_types_spec.rb +104 -40
  91. metadata +7 -7
  92. data/spec/integration/test/test_helper_spec.rb +0 -31
@@ -224,7 +224,6 @@ describe Puppet::Daemon, :unless => Puppet.features.microsoft_windows? do
224
224
  end
225
225
 
226
226
  it "should reexec itself if the agent is not running" do
227
- expect(agent).to receive(:running?).and_return(false)
228
227
  daemon.agent = agent
229
228
  expect(daemon).to receive(:reexec)
230
229
 
@@ -1,6 +1,8 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe Puppet::FileSystem::Uniquefile do
4
+ include PuppetSpec::Files
5
+
4
6
  it "makes the name of the file available" do
5
7
  Puppet::FileSystem::Uniquefile.open_tmp('foo') do |file|
6
8
  expect(file.path).to match(/foo/)
@@ -67,6 +69,15 @@ describe Puppet::FileSystem::Uniquefile do
67
69
  Puppet::FileSystem::Uniquefile.open_tmp('foo') { |tmp| }
68
70
  end
69
71
 
72
+ it "reports when a parent directory does not exist" do
73
+ dir = tmpdir('uniquefile')
74
+ lock = File.join(dir, 'path', 'to', 'lock')
75
+
76
+ expect {
77
+ Puppet::FileSystem::Uniquefile.open_tmp(lock) { |tmp| }
78
+ }.to raise_error(Errno::ENOENT, %r{No such file or directory - A directory component in .* does not exist or is a dangling symbolic link})
79
+ end
80
+
70
81
  context "Ruby 1.9.3 Tempfile tests" do
71
82
  # the remaining tests in this file are ported directly from the ruby 1.9.3 source,
72
83
  # since most of this file was ported from there
@@ -343,7 +343,8 @@ describe Puppet::Network::HTTP::API::IndirectedRoutes do
343
343
 
344
344
  expect {
345
345
  handler.call(request, response)
346
- }.to raise_error(Puppet::Network::HTTP::Error::HTTPNotAcceptableError, /No supported formats are acceptable/)
346
+ }.to raise_error(Puppet::Network::HTTP::Error::HTTPNotAcceptableError,
347
+ %r{No supported formats are acceptable \(Accept: application/json, text/pson\)})
347
348
  end
348
349
 
349
350
  it "should return [] when searching returns an empty array" do
@@ -367,6 +367,13 @@ EOS
367
367
  }.to raise_error(/'Cap\[cap\]' is exported by both 'Prod\[one\]' and 'Prod\[two\]'/)
368
368
  end
369
369
 
370
+ it "issues deprecation warnings" do
371
+ expect {compile_collect_log(MANIFEST_WO_NODE)}.not_to raise_error
372
+ expect(warnings).to include(/Capability Mapping is deprecated/) # there are two of these
373
+ expect(warnings).to include(/Application is deprecated/)
374
+ expect(warnings).to include(/Site Definition is deprecated/)
375
+ end
376
+
370
377
  context "for producing node" do
371
378
  let(:compiled_node) { Puppet::Node.new('first', :environment => env) }
372
379
  let(:compiled_catalog) { compile_to_catalog(MANIFEST, compiled_node)}
@@ -18,7 +18,7 @@ describe Puppet::Type.type(:package).provider(:dnfmodule) do
18
18
  {:failonfail => true, :combine => true, :custom_environment => {}}
19
19
  end
20
20
 
21
- let(:packages) { File.read(my_fixture("dnf-module-list-enabled.txt")) }
21
+ let(:packages) { File.read(my_fixture("dnf-module-list.txt")) }
22
22
  let(:dnf_path) { '/usr/bin/dnf' }
23
23
 
24
24
  before(:each) { allow(Puppet::Util).to receive(:which).with('/usr/bin/dnf').and_return(dnf_path) }
@@ -81,7 +81,7 @@ describe Puppet::Type.type(:package).provider(:dnfmodule) do
81
81
  end
82
82
  end
83
83
 
84
- describe "when installing a module" do
84
+ describe "when ensuring a module" do
85
85
  let(:name) { 'baz' }
86
86
 
87
87
  let(:resource) do
@@ -200,14 +200,32 @@ describe Puppet::Type.type(:package).provider(:dnfmodule) do
200
200
  expect(provider.flavor).to eq('minimal')
201
201
  end
202
202
  end
203
+
204
+ context "when disabling a module" do
205
+
206
+ it "executed the disable command" do
207
+ resource[:ensure] = :disabled
208
+ expect(provider).to receive(:execute).with(array_including('disable'))
209
+ provider.disable
210
+ end
211
+
212
+ it "does not try to disable if package is already disabled" do
213
+ allow(described_class).to receive(:command).with(:dnf).and_return(dnf_path)
214
+ allow(Puppet::Util::Execution).to receive(:execute)
215
+ .with("/usr/bin/dnf module list -d 0 -e 1")
216
+ .and_return("baz 1.2 [d][x] common [d], complete Package Description")
217
+ resource[:ensure] = :disabled
218
+ expect(provider).to be_insync(:disabled)
219
+ end
220
+ end
203
221
  end
204
222
 
205
- context "parsing the output of module list --enabled" do
223
+ context "parsing the output of module list" do
206
224
  before { allow(described_class).to receive(:command).with(:dnf).and_return(dnf_path) }
207
225
 
208
226
  it "returns an array of enabled modules" do
209
227
  allow(Puppet::Util::Execution).to receive(:execute)
210
- .with("/usr/bin/dnf module list --enabled -d 0 -e 1")
228
+ .with("/usr/bin/dnf module list -d 0 -e 1")
211
229
  .and_return(packages)
212
230
 
213
231
  enabled_packages = described_class.instances.map { |package| package.properties }
@@ -219,7 +237,9 @@ describe Puppet::Type.type(:package).provider(:dnfmodule) do
219
237
  {name: "postgresql", ensure: "10", flavor: "server", provider: :dnfmodule},
220
238
  {name: "ruby", ensure: "2.5", flavor: :absent, provider: :dnfmodule},
221
239
  {name: "rust-toolset", ensure: "rhel8", flavor: "common", provider: :dnfmodule},
222
- {name: "subversion", ensure: "1.10", flavor: "server", provider: :dnfmodule}]
240
+ {name: "subversion", ensure: "1.10", flavor: "server", provider: :dnfmodule},
241
+ {name: "swig", ensure: :disabled, flavor: :absent, provider: :dnfmodule},
242
+ {name: "virt", ensure: :disabled, flavor: :absent, provider: :dnfmodule}]
223
243
 
224
244
  expect(enabled_packages).to eql(expected_packages)
225
245
  end
@@ -1,6 +1,7 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  osfamilies = { 'windows' => ['pip.exe'], 'other' => ['pip', 'pip-python', 'pip2', 'pip-2'] }
4
+ pip_path_with_spaces = 'C:\Program Files (x86)\Python\Scripts\pip.exe'
4
5
 
5
6
  describe Puppet::Type.type(:package).provider(:pip) do
6
7
 
@@ -93,6 +94,16 @@ describe Puppet::Type.type(:package).provider(:pip) do
93
94
  expect(described_class.instances).to eq([])
94
95
  end
95
96
  end
97
+
98
+ context "when pip path location contains spaces" do
99
+ it "should quote the command before doing execpipe" do
100
+ allow(described_class).to receive(:which).and_return(pip_path_with_spaces)
101
+ allow(described_class).to receive(:pip_version).with(pip_path_with_spaces).and_return('8.0.1')
102
+
103
+ expect(described_class).to receive(:execpipe).with(["\"#{pip_path_with_spaces}\"", ["freeze"]])
104
+ described_class.instances
105
+ end
106
+ end
96
107
  end
97
108
 
98
109
  context "query" do
@@ -143,15 +154,18 @@ describe Puppet::Type.type(:package).provider(:pip) do
143
154
  end
144
155
 
145
156
  context "latest" do
157
+ before do
158
+ allow(described_class).to receive(:pip_version).with(pip_path).and_return(pip_version)
159
+ allow(described_class).to receive(:which).with('pip').and_return(pip_path)
160
+ allow(described_class).to receive(:which).with('pip-python').and_return(pip_path)
161
+ allow(described_class).to receive(:which).with('pip.exe').and_return(pip_path)
162
+ allow(described_class).to receive(:provider_command).and_return(pip_path)
163
+ allow(described_class).to receive(:validate_command).with(pip_path)
164
+ end
165
+
146
166
  context "with pip version < 1.5.4" do
147
- before :each do
148
- allow(described_class).to receive(:pip_version).with("/fake/bin/pip").and_return('1.0.1')
149
- allow(described_class).to receive(:which).with('pip').and_return("/fake/bin/pip")
150
- allow(described_class).to receive(:which).with('pip-python').and_return("/fake/bin/pip")
151
- allow(described_class).to receive(:which).with('pip.exe').and_return("/fake/bin/pip")
152
- allow(described_class).to receive(:provider_command).and_return('/fake/bin/pip')
153
- allow(described_class).to receive(:validate_command).with('/fake/bin/pip')
154
- end
167
+ let(:pip_version) { '1.0.1' }
168
+ let(:pip_path) { '/fake/bin/pip' }
155
169
 
156
170
  it "should find a version number for new_pip_package" do
157
171
  p = StringIO.new(
@@ -204,19 +218,22 @@ describe Puppet::Type.type(:package).provider(:pip) do
204
218
  @resource[:install_options] = ['--index' => 'https://fake.example.com']
205
219
  expect(@provider.latest).to eq(nil)
206
220
  end
221
+
222
+ context "when pip path location contains spaces" do
223
+ let(:pip_path) { pip_path_with_spaces }
224
+
225
+ it "should quote the command before doing execpipe" do
226
+ expect(Puppet::Util::Execution).to receive(:execpipe).with(array_including("\"#{pip_path}\""))
227
+ @provider.latest
228
+ end
229
+ end
207
230
  end
208
231
 
209
232
  context "with pip version >= 1.5.4" do
210
233
  # For Pip 1.5.4 and above, you can get a version list from CLI - which allows for native pip behavior
211
234
  # with regards to custom repositories, proxies and the like
212
- before :each do
213
- allow(described_class).to receive(:pip_version).with("/fake/bin/pip").and_return('1.5.4')
214
- allow(described_class).to receive(:which).with('pip').and_return("/fake/bin/pip")
215
- allow(described_class).to receive(:which).with('pip-python').and_return("/fake/bin/pip")
216
- allow(described_class).to receive(:which).with('pip.exe').and_return("/fake/bin/pip")
217
- allow(described_class).to receive(:provider_command).and_return('/fake/bin/pip')
218
- allow(described_class).to receive(:validate_command).with('/fake/bin/pip')
219
- end
235
+ let(:pip_version) { '1.5.4' }
236
+ let(:pip_path) { '/fake/bin/pip' }
220
237
 
221
238
  it "should find a version number for real_package" do
222
239
  p = StringIO.new(
@@ -265,6 +282,15 @@ describe Puppet::Type.type(:package).provider(:pip) do
265
282
  @resource[:install_options] = ['--index' => 'https://fake.example.com']
266
283
  expect(@provider.latest).to eq(nil)
267
284
  end
285
+
286
+ context "when pip path location contains spaces" do
287
+ let(:pip_path) { pip_path_with_spaces }
288
+
289
+ it "should quote the command before doing execpipe" do
290
+ expect(Puppet::Util::Execution).to receive(:execpipe).with(array_including("\"#{pip_path}\""))
291
+ @provider.latest
292
+ end
293
+ end
268
294
  end
269
295
  end
270
296
 
@@ -176,6 +176,19 @@ describe Puppet::Type.type(:package).provider(:zypper) do
176
176
  @provider.install
177
177
  end
178
178
 
179
+ it "should install the package with --no-gpg-checks" do
180
+ allow(@resource).to receive(:[]).with(:name).and_return("php5")
181
+ allow(@resource).to receive(:[]).with(:install_options).and_return(['--no-gpg-checks', {'-p' => '/vagrant/files/localrepo/'}])
182
+ allow(@resource).to receive(:should).with(:ensure).and_return("5.4.10-4.5.6")
183
+ allow(@resource).to receive(:allow_virtual?).and_return(false)
184
+ allow(@provider).to receive(:zypper_version).and_return("1.2.8")
185
+
186
+ expect(@provider).to receive(:zypper).with('--quiet', '--no-gpg-checks', :install,
187
+ '--auto-agree-with-licenses', '--no-confirm', '-p=/vagrant/files/localrepo/', 'php5-5.4.10-4.5.6')
188
+ expect(@provider).to receive(:query).and_return("php5 0 5.4.10 4.5.6 x86_64")
189
+ @provider.install
190
+ end
191
+
179
192
  it "should install package with hash install options" do
180
193
  allow(@resource).to receive(:[]).with(:name).and_return('vim')
181
194
  allow(@resource).to receive(:[]).with(:install_options).and_return([{ '--a' => 'foo', '--b' => '"quoted bar"' }])
@@ -151,9 +151,19 @@ describe Puppet::Type.type(:service).provider(:systemd) do
151
151
  autovt@.service
152
152
  avahi-daemon.service
153
153
  blk-availability.service
154
+ apparmor.service
155
+ umountnfs.service
156
+ urandom.service
157
+ brandbot.service
154
158
  })
155
159
  end
156
- end
160
+
161
+ it "should print a debug message when a service with the state `bad` is found" do
162
+ expect(described_class).to receive(:systemctl).with('list-unit-files', '--type', 'service', '--full', '--all', '--no-pager').and_return(File.read(my_fixture('list_unit_files_services')))
163
+ expect(Puppet).to receive(:debug).with("apparmor.service marked as bad by `systemctl`. It is recommended to be further checked.")
164
+ described_class.instances
165
+ end
166
+ end
157
167
 
158
168
  describe "#start" do
159
169
  it "should use the supplied start command if specified" do
@@ -216,44 +226,46 @@ Jun 14 21:43:23 foo.example.com systemd[1]: sshd.service lacks both ExecStart= a
216
226
  describe "#enabled?" do
217
227
  it "should return :true if the service is enabled" do
218
228
  provider = described_class.new(Puppet::Type.type(:service).new(:name => 'sshd.service'))
219
- expect(provider).to receive(:execute).with(['/bin/systemctl','is-enabled', '--', 'sshd.service'], :failonfail => false).and_return("enabled\n")
220
- allow($CHILD_STATUS).to receive(:exitstatus).and_return(0)
229
+ expect(provider).to receive(:execute).with(['/bin/systemctl','is-enabled', '--', 'sshd.service'], :failonfail => false).
230
+ and_return(Puppet::Util::Execution::ProcessOutput.new("enabled\n", 0))
221
231
  expect(provider.enabled?).to eq(:true)
222
232
  end
223
233
 
224
234
  it "should return :true if the service is static" do
225
235
  provider = described_class.new(Puppet::Type.type(:service).new(:name => 'sshd.service'))
226
- expect(provider).to receive(:execute).with(['/bin/systemctl','is-enabled','--', 'sshd.service'], :failonfail => false).and_return("static\n")
227
- allow($CHILD_STATUS).to receive(:exitstatus).and_return(0)
236
+ expect(provider).to receive(:execute).with(['/bin/systemctl','is-enabled','--', 'sshd.service'], :failonfail => false).
237
+ and_return(Puppet::Util::Execution::ProcessOutput.new("static\n", 0))
228
238
  expect(provider.enabled?).to eq(:true)
229
239
  end
230
240
 
231
241
  it "should return :false if the service is disabled" do
232
242
  provider = described_class.new(Puppet::Type.type(:service).new(:name => 'sshd.service'))
233
- expect(provider).to receive(:execute).with(['/bin/systemctl','is-enabled', '--', 'sshd.service'], :failonfail => false).and_return("disabled\n")
234
- allow($CHILD_STATUS).to receive(:exitstatus).and_return(1)
243
+ expect(provider).to receive(:execute).with(['/bin/systemctl','is-enabled', '--', 'sshd.service'], :failonfail => false).
244
+ and_return(Puppet::Util::Execution::ProcessOutput.new("disabled\n", 1))
235
245
  expect(provider.enabled?).to eq(:false)
236
246
  end
237
247
 
238
248
  it "should return :false if the service is indirect" do
239
249
  provider = described_class.new(Puppet::Type.type(:service).new(:name => 'sshd.service'))
240
- expect(provider).to receive(:execute).with(['/bin/systemctl','is-enabled', '--', 'sshd.service'], :failonfail => false).and_return("indirect\n")
241
- allow($CHILD_STATUS).to receive(:exitstatus).and_return(0)
250
+ expect(provider).to receive(:execute).with(['/bin/systemctl','is-enabled', '--', 'sshd.service'], :failonfail => false).
251
+ and_return(Puppet::Util::Execution::ProcessOutput.new("indirect\n", 0))
242
252
  expect(provider.enabled?).to eq(:false)
243
253
  end
244
254
 
245
- it "should return :false if the service is masked and the resource is attempting to be disabled" do
246
- provider = described_class.new(Puppet::Type.type(:service).new(:name => 'sshd.service', :enable => false))
247
- expect(provider).to receive(:execute).with(['/bin/systemctl','is-enabled', '--', 'sshd.service'], :failonfail => false).and_return("masked\n")
248
- allow($CHILD_STATUS).to receive(:exitstatus).and_return(1)
249
- expect(provider.enabled?).to eq(:false)
250
- end
255
+ context "when masked" do
256
+ it "should return :false if the resource is attempting to be disabled" do
257
+ provider = described_class.new(Puppet::Type.type(:service).new(:name => 'sshd.service', :enable => false))
258
+ expect(provider).to receive(:execute).with(['/bin/systemctl','is-enabled', '--', 'sshd.service'], :failonfail => false).
259
+ and_return(Puppet::Util::Execution::ProcessOutput.new("masked\n", 1))
260
+ expect(provider.enabled?).to eq(:false)
261
+ end
251
262
 
252
- it "should return :mask if the service is masked and the resource is attempting to be masked" do
253
- provider = described_class.new(Puppet::Type.type(:service).new(:name => 'sshd.service', :enable => 'mask'))
254
- expect(provider).to receive(:execute).with(['/bin/systemctl','is-enabled', '--', 'sshd.service'], :failonfail => false).and_return("masked\n")
255
- allow($CHILD_STATUS).to receive(:exitstatus).and_return(1)
256
- expect(provider.enabled?).to eq(:mask)
263
+ it "should return :mask if the resource is attempting to be masked" do
264
+ provider = described_class.new(Puppet::Type.type(:service).new(:name => 'sshd.service', :enable => 'mask'))
265
+ expect(provider).to receive(:execute).with(['/bin/systemctl','is-enabled', '--', 'sshd.service'], :failonfail => false).
266
+ and_return(Puppet::Util::Execution::ProcessOutput.new("masked\n", 1))
267
+ expect(provider.enabled?).to eq(:mask)
268
+ end
257
269
  end
258
270
  end
259
271
 
@@ -372,6 +384,67 @@ Jun 14 21:43:23 foo.example.com systemd[1]: sshd.service lacks both ExecStart= a
372
384
  end
373
385
  end
374
386
 
387
+ describe "#insync_enabled?" do
388
+ let(:provider) do
389
+ described_class.new(Puppet::Type.type(:service).new(:name => 'sshd.service', :enable => false))
390
+ end
391
+
392
+ before do
393
+ allow(provider).to receive(:cached_enabled?).and_return({ output: service_state, exitcode: 0 })
394
+ end
395
+
396
+ context 'when service state is static' do
397
+ let(:service_state) { 'static' }
398
+
399
+ it 'is always enabled_insync even if current value is the same as expected' do
400
+ expect(provider).to be_enabled_insync(:false)
401
+ end
402
+
403
+ it 'is always enabled_insync even if current value is not the same as expected' do
404
+ expect(provider).to be_enabled_insync(:true)
405
+ end
406
+
407
+ it 'logs a debug messsage' do
408
+ expect(Puppet).to receive(:debug).with("Unable to enable or disable static service sshd.service")
409
+ provider.enabled_insync?(:true)
410
+ end
411
+ end
412
+
413
+ context 'when service state is indirect' do
414
+ let(:service_state) { 'indirect' }
415
+
416
+ it 'is always enabled_insync even if current value is the same as expected' do
417
+ expect(provider).to be_enabled_insync(:false)
418
+ end
419
+
420
+ it 'is always enabled_insync even if current value is not the same as expected' do
421
+ expect(provider).to be_enabled_insync(:true)
422
+ end
423
+
424
+ it 'logs a debug messsage' do
425
+ expect(Puppet).to receive(:debug).with("Service sshd.service is in 'indirect' state and cannot be enabled/disabled")
426
+ provider.enabled_insync?(:true)
427
+ end
428
+ end
429
+
430
+ context 'when service state is enabled' do
431
+ let(:service_state) { 'enabled' }
432
+
433
+ it 'is enabled_insync if current value is the same as expected' do
434
+ expect(provider).to be_enabled_insync(:false)
435
+ end
436
+
437
+ it 'is not enabled_insync if current value is not the same as expected' do
438
+ expect(provider).not_to be_enabled_insync(:true)
439
+ end
440
+
441
+ it 'logs no debug messsage' do
442
+ expect(Puppet).not_to receive(:debug)
443
+ provider.enabled_insync?(:true)
444
+ end
445
+ end
446
+ end
447
+
375
448
  describe "#get_start_link_count" do
376
449
  it "should strip the '.service' from the search if present in the resource name" do
377
450
  provider = described_class.new(Puppet::Type.type(:service).new(:name => 'sshd.service'))
@@ -45,6 +45,7 @@ describe Puppet::Type.type(:user).provider(:openbsd) do
45
45
  describe "#addcmd" do
46
46
  it "should return an array with the full command and expiry as MM/DD/YY" do
47
47
  allow(Facter).to receive(:value).with(:osfamily).and_return('OpenBSD')
48
+ allow(Facter).to receive(:value).with(:operatingsystemmajrelease)
48
49
  resource[:expiry] = "1997-06-01"
49
50
  expect(provider.addcmd).to eq(['/usr/sbin/useradd', '-e', 'June 01 1997', 'myuser'])
50
51
  end
@@ -72,20 +72,24 @@ describe Puppet::Type.type(:user).provider(:useradd) do
72
72
  provider.create
73
73
  end
74
74
 
75
- it "should use -G to set groups" do
76
- allow(Facter).to receive(:value).with(:osfamily).and_return('Not RedHat')
77
- resource[:ensure] = :present
78
- resource[:groups] = ['group1', 'group2']
79
- expect(provider).to receive(:execute).with(['/usr/sbin/useradd', '-G', 'group1,group2', 'myuser'], kind_of(Hash))
80
- provider.create
81
- end
75
+ context "when setting groups" do
76
+ it "uses -G to set groups" do
77
+ allow(Facter).to receive(:value).with(:osfamily).and_return('Solaris')
78
+ allow(Facter).to receive(:value).with(:operatingsystemmajrelease)
79
+ resource[:ensure] = :present
80
+ resource[:groups] = ['group1', 'group2']
81
+ expect(provider).to receive(:execute).with(['/usr/sbin/useradd', '-G', 'group1,group2', 'myuser'], kind_of(Hash))
82
+ provider.create
83
+ end
82
84
 
83
- it "should use -G to set groups without -M on RedHat" do
84
- allow(Facter).to receive(:value).with(:osfamily).and_return('RedHat')
85
- resource[:ensure] = :present
86
- resource[:groups] = ['group1', 'group2']
87
- expect(provider).to receive(:execute).with(['/usr/sbin/useradd', '-G', 'group1,group2', '-M', 'myuser'], kind_of(Hash))
88
- provider.create
85
+ it "uses -G to set groups with -M on supported systems" do
86
+ allow(Facter).to receive(:value).with(:osfamily).and_return('RedHat')
87
+ allow(Facter).to receive(:value).with(:operatingsystemmajrelease)
88
+ resource[:ensure] = :present
89
+ resource[:groups] = ['group1', 'group2']
90
+ expect(provider).to receive(:execute).with(['/usr/sbin/useradd', '-G', 'group1,group2', '-M', 'myuser'], kind_of(Hash))
91
+ provider.create
92
+ end
89
93
  end
90
94
 
91
95
  it "should add -o when allowdupe is enabled and the user is being created" do
@@ -315,6 +319,14 @@ describe Puppet::Type.type(:user).provider(:useradd) do
315
319
  expect(provider).to receive(:execute).with(['/usr/sbin/usermod', '-e', '', 'myuser'], hash_including(custom_environment: {}))
316
320
  provider.expiry = :absent
317
321
  end
322
+
323
+ it "should use -e with -1 when the expiry property is removed on SLES11" do
324
+ allow(Facter).to receive(:value).with(:operatingsystem).and_return('SLES')
325
+ allow(Facter).to receive(:value).with(:operatingsystemmajrelease).and_return('11')
326
+ resource[:expiry] = :absent
327
+ expect(provider).to receive(:execute).with(['/usr/sbin/usermod', '-e', -1, 'myuser'], hash_including(custom_environment: {}))
328
+ provider.expiry = :absent
329
+ end
318
330
  end
319
331
 
320
332
  describe "#comment" do
@@ -421,15 +433,17 @@ describe Puppet::Type.type(:user).provider(:useradd) do
421
433
  provider.delete
422
434
  end
423
435
 
424
- it "should use -M flag if home is not managed and on Redhat" do
436
+ it "should use -M flag if home is not managed on a supported system" do
425
437
  allow(Facter).to receive(:value).with(:osfamily).and_return("RedHat")
438
+ allow(Facter).to receive(:value).with(:operatingsystemmajrelease)
426
439
  resource[:managehome] = :false
427
440
  expect(provider).to receive(:execute).with(include('-M'), kind_of(Hash))
428
441
  provider.create
429
442
  end
430
443
 
431
- it "should not use -M flag if home is not managed and not on Redhat" do
432
- allow(Facter).to receive(:value).with(:osfamily).and_return("not RedHat")
444
+ it "should not use -M flag if home is not managed on an unsupported system" do
445
+ allow(Facter).to receive(:value).with(:osfamily).and_return("Suse")
446
+ allow(Facter).to receive(:value).with(:operatingsystemmajrelease).and_return("11")
433
447
  resource[:managehome] = :false
434
448
  expect(provider).to receive(:execute).with(excluding('-M'), kind_of(Hash))
435
449
  provider.create