chef 17.6.18 → 17.7.22

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (63) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile +5 -0
  3. data/chef.gemspec +1 -0
  4. data/lib/chef/chef_fs/file_pattern.rb +1 -1
  5. data/lib/chef/chef_fs/path_utils.rb +1 -1
  6. data/lib/chef/data_collector/run_end_message.rb +1 -1
  7. data/lib/chef/dsl/reboot_pending.rb +1 -1
  8. data/lib/chef/exceptions.rb +10 -0
  9. data/lib/chef/provider/cron.rb +4 -1
  10. data/lib/chef/provider/git.rb +1 -1
  11. data/lib/chef/provider/ifconfig/debian.rb +1 -1
  12. data/lib/chef/provider/subversion.rb +5 -5
  13. data/lib/chef/resource/chocolatey_config.rb +1 -1
  14. data/lib/chef/resource/chocolatey_feature.rb +1 -1
  15. data/lib/chef/resource/chocolatey_source.rb +24 -2
  16. data/lib/chef/resource/directory.rb +1 -1
  17. data/lib/chef/resource/habitat_install.rb +3 -3
  18. data/lib/chef/resource/inspec_waiver.rb +1 -1
  19. data/lib/chef/resource/inspec_waiver_file_entry.rb +1 -1
  20. data/lib/chef/resource/kernel_module.rb +27 -2
  21. data/lib/chef/resource/macos_userdefaults.rb +43 -128
  22. data/lib/chef/resource/windows_auto_run.rb +1 -1
  23. data/lib/chef/resource/windows_dfs_namespace.rb +2 -2
  24. data/lib/chef/resource/windows_update_settings.rb +3 -3
  25. data/lib/chef/resource.rb +1 -1
  26. data/lib/chef/resource_reporter.rb +1 -1
  27. data/lib/chef/secret_fetcher/azure_key_vault.rb +62 -8
  28. data/lib/chef/secret_fetcher.rb +0 -1
  29. data/lib/chef/version.rb +1 -1
  30. data/spec/functional/dsl/reboot_pending_spec.rb +3 -3
  31. data/spec/functional/dsl/registry_helper_spec.rb +1 -1
  32. data/spec/functional/resource/dsc_script_spec.rb +2 -2
  33. data/spec/functional/resource/macos_userdefaults_spec.rb +119 -0
  34. data/spec/functional/resource/registry_spec.rb +81 -81
  35. data/spec/functional/win32/registry_spec.rb +8 -8
  36. data/spec/unit/data_collector_spec.rb +24 -1
  37. data/spec/unit/dsl/reboot_pending_spec.rb +1 -1
  38. data/spec/unit/mixin/default_paths_spec.rb +1 -1
  39. data/spec/unit/mixin/securable_spec.rb +3 -3
  40. data/spec/unit/provider/cron_spec.rb +45 -0
  41. data/spec/unit/provider/package/rubygems_spec.rb +5 -5
  42. data/spec/unit/provider/package/windows_spec.rb +1 -1
  43. data/spec/unit/provider/registry_key_spec.rb +4 -4
  44. data/spec/unit/provider/service/windows_spec.rb +5 -5
  45. data/spec/unit/provider/subversion_spec.rb +4 -4
  46. data/spec/unit/provider/windows_env_spec.rb +1 -1
  47. data/spec/unit/provider/zypper_repository_spec.rb +1 -1
  48. data/spec/unit/resource/chocolatey_config_spec.rb +1 -1
  49. data/spec/unit/resource/chocolatey_feature_spec.rb +1 -1
  50. data/spec/unit/resource/chocolatey_source_spec.rb +1 -1
  51. data/spec/unit/resource/kernel_module_spec.rb +2 -1
  52. data/spec/unit/resource/macos_user_defaults_spec.rb +36 -96
  53. data/spec/unit/resource/registry_key_spec.rb +10 -10
  54. data/spec/unit/resource/windows_auto_run_spec.rb +1 -1
  55. data/spec/unit/resource/windows_feature_powershell_spec.rb +1 -1
  56. data/spec/unit/resource/windows_firewall_rule_spec.rb +2 -2
  57. data/spec/unit/resource/windows_task_spec.rb +3 -3
  58. data/spec/unit/resource_reporter_spec.rb +2 -2
  59. data/spec/unit/resource_spec.rb +5 -0
  60. data/spec/unit/secret_fetcher/azure_key_vault_spec.rb +99 -20
  61. data/spec/unit/util/backup_spec.rb +1 -1
  62. data/spec/unit/win32/registry_spec.rb +3 -3
  63. metadata +21 -6
@@ -20,51 +20,130 @@
20
20
  require_relative "../../spec_helper"
21
21
  require "chef/secret_fetcher"
22
22
  require "chef/secret_fetcher/azure_key_vault"
23
+ require "net/http/responses"
23
24
 
24
25
  describe Chef::SecretFetcher::AzureKeyVault do
25
- let(:config) { { vault: "my_vault" } }
26
+ let(:config) { { vault: "my-vault" } }
26
27
  let(:fetcher) { Chef::SecretFetcher::AzureKeyVault.new(config, nil) }
28
+ let(:secrets_response_body) { '{ "value" : "my secret value" }' }
29
+ let(:secrets_response_mock) do
30
+ rm = Net::HTTPSuccess.new("1.0", "400", "OK")
31
+ allow(rm).to receive(:body).and_return(secrets_response_body)
32
+ rm
33
+ end
34
+ let(:token_response_body) { %Q({"access_token":"#{access_token}","client_id":"#{client_id}","expires_in":"86294","expires_on":"1627761860","ext_expires_in":"86399","not_before":"1627675160","resource":"https://vault.azure.net","token_type":"Bearer"}) }
35
+ let(:access_token) { "eyJ0eXAiOiJKV1QiLCJhbGciOiJSUzI1NiIsIng1dCI6Im5PbzNaRHJPRFhFSzFqS1doWHNsSFJfS1hFZyIsImtpZCI6Im5PbzNaRHJPRFhFSzFqS1doWHNsSFJfS1hFZyJ9.eyJhdWQiOiJodHRwczovL3ZhdWx0LmF6dXJlLm5ldCIsImlzcyI6Imh0dHBzOi8vc3RzLndpbmRvd3MubmV0L2E5ZTY2ZDhkLTA1ZTAtNGMwMC1iOWRkLWM0Yjc3M2U5MWNhNi8iLCJpYXQiOjE2Mjc2NzUxNjAsIm5iZiI6MTYyNzY3NTE2MCwiZXhwIjoxNjI3NzYxODYwLCJhaW8iOiJFMlpnWUhCWGplaTdWS214eEh6bjdoSWpNZFlMQUE9PSIsImFwcGlkIjoiNjU2Mjc1MjEtMzYzYi00ZDk2LTkyMTctMjcIsIm9pZCI6IjNiZjI1NjVhLWY4NWQtNDBiNy1hZWJkLTNlZDA1ZDA0N2FmNiIsInJoIjoiMC5BUk1BalczbXFlQUZBRXk1M2NTM2Mta2NwaUYxWW1VN05wWk5raGNuRGpuZEwxb1RBQUEuIiwic3ViIjoiM2JmMjU2NWEtZjg1ZC00MGI3LWFlYmQtM2VkMDVkMDQ3YWY2IiwidGlkIjoiYTllNjZkOGQtMDVlMC00YzAwLWI5ZGQtYzRiNzczZTkxY2E2IiwidXRpIjoibXlzeHpSRTV3ay1ibTFlYkNqc09BQSIsInZlciI6IjEuMCIsInhtc19taXJpZCI6Ii9zdWJzY3JpcHRpb25zLzYzNDJkZDZkLTc1NTQtNDJjOS04NTM2LTdkZmU3MmY1MWZhZC9yZXNvdXJjZWdyb3Vwcy9pbWFnZS1waXBlbGluZS1ydW5uZXItcWEtZWFzdHVzMi1yZy9wcm92aWRlcnMvTWljcm9zb2Z0Lk1hbmFnZWRJZGVudGl0eS91c2VyQXNzaWduZWRJZGVudGl0aWVzL2ltYWdlLXBpcGVsaW5lLXJ1bm5lci1xYS1lYXN0dXMyLW1pIn0.BquzjN6d0g4zlvkbkdVwNEfRxIXSmxYwCHMk6UG3iza2fVioiOrcoP4Cp9P5--AB4G_CAhIXaP7YIZs3mq05QiDjSvkVAM0t67UPGhEr66sNXkV72iZBnKca_auh6EHsjPfxeVHkE1wdrsncrYdKhzgO4IAj8Jg4N5qjcE2q-OkliadmEuTwrhPhq" }
36
+ let(:token_response_mock) do
37
+ rm = Net::HTTPSuccess.new("1.0", "400", "OK")
38
+ allow(rm).to receive(:body).and_return(token_response_body)
39
+ rm
40
+ end
41
+ let(:client_id) { SecureRandom.uuid }
42
+ let(:http_mock) { instance_double("Net::HTTP", :use_ssl= => nil) }
43
+ let(:token_uri) { URI.parse("http://169.254.169.254/metadata/identity/oauth2/token") }
44
+ let(:vault_name) { "my-vault" }
45
+ let(:secret_name) { "my-secret" }
46
+ let(:vault_secret_uri) { URI.parse("https://#{vault_name}.vault.azure.net/secrets/#{secret_name}/?api-version=7.2") }
47
+
48
+ before do
49
+ # Cache these up front so we can pass into allow statements without hitting:
50
+ # URI received :parse with unexpected arguments
51
+ token_uri
52
+ vault_secret_uri
53
+ end
54
+
55
+ before do
56
+ allow(Net::HTTP).to receive(:new).and_return(http_mock)
57
+ allow(URI).to receive(:parse).with("http://169.254.169.254/metadata/identity/oauth2/token").and_return(token_uri)
58
+ allow(URI).to receive(:parse).with("https://#{vault_name}.vault.azure.net/secrets/#{secret_name}/?api-version=7.2").and_return(vault_secret_uri)
59
+ allow(http_mock).to receive(:get).with(token_uri, { "Metadata" => "true" }).and_return(token_response_mock)
60
+ allow(http_mock).to receive(:get).with(vault_secret_uri, { "Authorization" => "Bearer #{access_token}", "Content-Type" => "application/json" }).and_return(secrets_response_mock)
61
+ end
62
+
63
+ describe "#validate!" do
64
+ it "raises error when more than one is provided: :object_id, :client_id, :mi_res_id" do
65
+ expect { Chef::SecretFetcher::AzureKeyVault.new({ object_id: "abc", client_id: "abc", mi_res_id: "abc" }, nil).validate! }.to raise_error(Chef::Exceptions::Secret::ConfigurationInvalid)
66
+ expect { Chef::SecretFetcher::AzureKeyVault.new({ object_id: "abc", client_id: "abc" }, nil).validate! }.to raise_error(Chef::Exceptions::Secret::ConfigurationInvalid)
67
+ expect { Chef::SecretFetcher::AzureKeyVault.new({ object_id: "abc", mi_res_id: "abc" }, nil).validate! }.to raise_error(Chef::Exceptions::Secret::ConfigurationInvalid)
68
+ expect { Chef::SecretFetcher::AzureKeyVault.new({ client_id: "abc", mi_res_id: "abc" }, nil).validate! }.to raise_error(Chef::Exceptions::Secret::ConfigurationInvalid)
69
+ end
70
+ end
27
71
 
28
- context "when performing a fetch" do
29
- let(:body) { '{ "value" : "my secret value" }' }
30
- let(:response_mock) { double("response", body: body) }
31
- let(:http_mock) { double("http", :get => response_mock, :use_ssl= => nil) }
72
+ describe "#fetch_token" do
73
+ context "when Net::HTTPBadRequest is returned and the error description contains \"Identity not found\"" do
74
+ let(:token_response_mock) { Net::HTTPBadRequest.new("1.0", "400", "Bad Request") }
75
+
76
+ before do
77
+ allow(fetcher).to receive(:fetch_token).and_call_original
78
+ allow(token_response_mock).to receive(:body).and_return('{"error":"invalid_request","error_description":"Identity not found"}')
79
+ end
32
80
 
33
- before do
34
- allow(fetcher).to receive(:fetch_token).and_return "a token"
35
- allow(Net::HTTP).to receive(:new).and_return(http_mock)
81
+ it "raises Chef::Exceptions::Secret::Azure::IdentityNotFound" do
82
+ expect { fetcher.send(:fetch_token) }.to raise_error(Chef::Exceptions::Secret::Azure::IdentityNotFound)
83
+ end
36
84
  end
37
85
 
38
- context "and vault name is only provided in the secret name" do
39
- let(:body) { '{ "value" : "my secret value" }' }
86
+ context "when :object_id is provided" do
87
+ let(:object_id) { SecureRandom.uuid }
88
+ let(:config) { { vault: "my-vault", object_id: object_id } }
89
+
90
+ it "adds client_id to request params" do
91
+ fetcher.send(:fetch_token)
92
+ expect(token_uri.query).to match(/object_id=#{object_id}/)
93
+ end
94
+ end
95
+
96
+ context "when :client_id is provided" do
97
+ let(:config) { { vault: "my-vault", client_id: client_id } }
98
+
99
+ it "adds client_id to request params" do
100
+ fetcher.send(:fetch_token)
101
+ expect(token_uri.query).to match(/client_id=#{client_id}/)
102
+ end
103
+ end
104
+
105
+ context "when :mi_res_id is provided" do
106
+ let(:mi_res_id) { SecureRandom.uuid }
107
+ let(:config) { { vault: "my-vault", mi_res_id: mi_res_id } }
108
+
109
+ it "adds client_id to request params" do
110
+ fetcher.send(:fetch_token)
111
+ expect(token_uri.query).to match(/mi_res_id=#{mi_res_id}/)
112
+ end
113
+ end
114
+ end
115
+
116
+ describe "#fetch" do
117
+ context "when vault name is only provided in the secret name" do
118
+ let(:secrets_response_body) { '{ "value" : "my secret value" }' }
40
119
  let(:config) { {} }
41
120
  it "fetches the value" do
42
- expect(fetcher.fetch("my_vault/value")).to eq "my secret value"
121
+ expect(fetcher.fetch("my-vault/my-secret")).to eq "my secret value"
43
122
  end
44
123
  end
45
124
 
46
- context "and vault name is not provided in the secret name" do
125
+ context "when vault name is not provided in the secret name" do
47
126
  context "and vault name is not provided in config" do
48
127
  let(:config) { {} }
49
128
  it "raises a ConfigurationInvalid exception" do
50
- expect { fetcher.fetch("value") }.to raise_error(Chef::Exceptions::Secret::ConfigurationInvalid)
129
+ expect { fetcher.fetch("my-secret") }.to raise_error(Chef::Exceptions::Secret::ConfigurationInvalid)
51
130
  end
52
131
  end
53
132
 
54
133
  context "and vault name is provided in config" do
55
- let(:config) { { vault: "my_vault" } }
134
+ let(:config) { { vault: "my-vault" } }
56
135
  it "fetches the value" do
57
- expect(fetcher.fetch("value")).to eq "my secret value"
136
+ expect(fetcher.fetch("my-secret")).to eq "my secret value"
58
137
  end
59
138
  end
60
139
  end
61
- context "and an error response is received in the body" do
62
- let(:config) { { vault: "my_vault" } }
63
- let(:body) { '{ "error" : { "code" : 404, "message" : "secret not found" } }' }
140
+
141
+ context "when an error response is received in the response body" do
142
+ let(:config) { { vault: "my-vault" } }
143
+ let(:secrets_response_body) { '{ "error" : { "code" : 404, "message" : "secret not found" } }' }
64
144
  it "raises FetchFailed" do
65
- expect { fetcher.fetch("value") }.to raise_error(Chef::Exceptions::Secret::FetchFailed)
145
+ expect { fetcher.fetch("my-secret") }.to raise_error(Chef::Exceptions::Secret::FetchFailed)
66
146
  end
67
147
  end
68
148
  end
69
149
  end
70
-
@@ -132,7 +132,7 @@ describe Chef::Util::Backup do
132
132
  end
133
133
 
134
134
  it "uses the configured Chef::Config[:file_backup_path] and strips the drive on windows" do
135
- expect(@backup).to receive(:path).and_return('c:\\a\\b\\c.txt')
135
+ expect(@backup).to receive(:path).and_return("c:\\a\\b\\c.txt")
136
136
  Chef::Config[:file_backup_path] = 'c:\backupdir'
137
137
  expect(@backup.send(:backup_path)).to match(%r|^c:\\backupdir[\\/]+a\\b\\c.txt.chef-\d{14}.\d{6}$|)
138
138
  end
@@ -23,12 +23,12 @@ describe Chef::Win32::Registry do
23
23
 
24
24
  let(:value1) { { name: "one", type: :string, data: "1" } }
25
25
  let(:value1_upcase_name) { { name: "ONE", type: :string, data: "1" } }
26
- let(:key_path) { 'HKCU\Software\OpscodeNumbers' }
27
- let(:key) { 'Software\OpscodeNumbers' }
26
+ let(:key_path) { "HKCU\\Software\\OpscodeNumbers" }
27
+ let(:key) { "Software\\OpscodeNumbers" }
28
28
  let(:key_parent) { "Software" }
29
29
  let(:key_to_delete) { "OpscodeNumbers" }
30
30
  let(:sub_key) { "OpscodePrimes" }
31
- let(:missing_key_path) { 'HKCU\Software' }
31
+ let(:missing_key_path) { "HKCU\\Software" }
32
32
  let(:registry) { Chef::Win32::Registry.new }
33
33
  let(:hive_mock) { double("::Win32::Registry::HKEY_CURRENT_USER") }
34
34
  let(:reg_mock) { double("reg") }
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: chef
3
3
  version: !ruby/object:Gem::Version
4
- version: 17.6.18
4
+ version: 17.7.22
5
5
  platform: ruby
6
6
  authors:
7
7
  - Adam Jacob
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2021-10-01 00:00:00.000000000 Z
11
+ date: 2021-10-25 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: chef-config
@@ -16,28 +16,28 @@ dependencies:
16
16
  requirements:
17
17
  - - '='
18
18
  - !ruby/object:Gem::Version
19
- version: 17.6.18
19
+ version: 17.7.22
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
24
  - - '='
25
25
  - !ruby/object:Gem::Version
26
- version: 17.6.18
26
+ version: 17.7.22
27
27
  - !ruby/object:Gem::Dependency
28
28
  name: chef-utils
29
29
  requirement: !ruby/object:Gem::Requirement
30
30
  requirements:
31
31
  - - '='
32
32
  - !ruby/object:Gem::Version
33
- version: 17.6.18
33
+ version: 17.7.22
34
34
  type: :runtime
35
35
  prerelease: false
36
36
  version_requirements: !ruby/object:Gem::Requirement
37
37
  requirements:
38
38
  - - '='
39
39
  - !ruby/object:Gem::Version
40
- version: 17.6.18
40
+ version: 17.7.22
41
41
  - !ruby/object:Gem::Dependency
42
42
  name: train-core
43
43
  requirement: !ruby/object:Gem::Requirement
@@ -426,6 +426,20 @@ dependencies:
426
426
  - - "<"
427
427
  - !ruby/object:Gem::Version
428
428
  version: '3.0'
429
+ - !ruby/object:Gem::Dependency
430
+ name: corefoundation
431
+ requirement: !ruby/object:Gem::Requirement
432
+ requirements:
433
+ - - "~>"
434
+ - !ruby/object:Gem::Version
435
+ version: 0.3.4
436
+ type: :runtime
437
+ prerelease: false
438
+ version_requirements: !ruby/object:Gem::Requirement
439
+ requirements:
440
+ - - "~>"
441
+ - !ruby/object:Gem::Version
442
+ version: 0.3.4
429
443
  - !ruby/object:Gem::Dependency
430
444
  name: proxifier
431
445
  requirement: !ruby/object:Gem::Requirement
@@ -1729,6 +1743,7 @@ files:
1729
1743
  - spec/functional/resource/launchd_spec.rb
1730
1744
  - spec/functional/resource/link_spec.rb
1731
1745
  - spec/functional/resource/locale_spec.rb
1746
+ - spec/functional/resource/macos_userdefaults_spec.rb
1732
1747
  - spec/functional/resource/mount_spec.rb
1733
1748
  - spec/functional/resource/msu_package_spec.rb
1734
1749
  - spec/functional/resource/ohai_spec.rb