chef 17.2.29-universal-mingw32 → 17.5.22-universal-mingw32

Sign up to get free protection for your applications and to get access to all the features.
Files changed (173) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile +6 -5
  3. data/chef.gemspec +3 -0
  4. data/lib/chef/application/base.rb +11 -1
  5. data/lib/chef/application.rb +3 -1
  6. data/lib/chef/client.rb +2 -3
  7. data/lib/chef/compliance/default_attributes.rb +5 -3
  8. data/lib/chef/compliance/input.rb +115 -0
  9. data/lib/chef/compliance/input_collection.rb +139 -0
  10. data/lib/chef/compliance/profile.rb +122 -0
  11. data/lib/chef/compliance/profile_collection.rb +109 -0
  12. data/lib/chef/compliance/reporter/automate.rb +1 -1
  13. data/lib/chef/compliance/runner.rb +62 -6
  14. data/lib/chef/compliance/waiver.rb +115 -0
  15. data/lib/chef/compliance/waiver_collection.rb +143 -0
  16. data/lib/chef/data_bag.rb +1 -2
  17. data/lib/chef/data_bag_item.rb +1 -2
  18. data/lib/chef/deprecated.rb +10 -4
  19. data/lib/chef/dsl/compliance.rb +38 -0
  20. data/lib/chef/dsl/reader_helpers.rb +51 -0
  21. data/lib/chef/dsl/recipe.rb +4 -2
  22. data/lib/chef/dsl/render_helpers.rb +44 -0
  23. data/lib/chef/dsl/secret.rb +62 -0
  24. data/lib/chef/dsl/toml.rb +116 -0
  25. data/lib/chef/dsl/universal.rb +7 -0
  26. data/lib/chef/dsl.rb +1 -0
  27. data/lib/chef/event_dispatch/base.rb +44 -2
  28. data/lib/chef/exceptions.rb +20 -0
  29. data/lib/chef/formatters/doc.rb +60 -13
  30. data/lib/chef/formatters/error_mapper.rb +2 -2
  31. data/lib/chef/formatters/minimal.rb +6 -5
  32. data/lib/chef/handler/slow_report.rb +1 -1
  33. data/lib/chef/http/basic_client.rb +15 -7
  34. data/lib/chef/http.rb +12 -8
  35. data/lib/chef/json_compat.rb +1 -1
  36. data/lib/chef/policy_builder/policyfile.rb +88 -45
  37. data/lib/chef/provider/execute.rb +1 -1
  38. data/lib/chef/provider/file.rb +4 -2
  39. data/lib/chef/provider/group/dscl.rb +1 -1
  40. data/lib/chef/provider/launchd.rb +6 -6
  41. data/lib/chef/provider/link.rb +2 -2
  42. data/lib/chef/provider/lwrp_base.rb +1 -1
  43. data/lib/chef/provider/package/habitat.rb +168 -0
  44. data/lib/chef/provider/package/powershell.rb +5 -0
  45. data/lib/chef/provider/registry_key.rb +3 -2
  46. data/lib/chef/provider/remote_file/http.rb +1 -1
  47. data/lib/chef/provider/subversion.rb +4 -4
  48. data/lib/chef/provider/support/yum_repo.erb +1 -1
  49. data/lib/chef/provider/systemd_unit.rb +17 -16
  50. data/lib/chef/provider/template.rb +1 -1
  51. data/lib/chef/provider/user/mac.rb +3 -3
  52. data/lib/chef/provider/yum_repository.rb +27 -43
  53. data/lib/chef/provider/zypper_repository.rb +3 -3
  54. data/lib/chef/provider.rb +26 -1
  55. data/lib/chef/provider_resolver.rb +8 -2
  56. data/lib/chef/providers.rb +1 -0
  57. data/lib/chef/resource/archive_file.rb +17 -14
  58. data/lib/chef/resource/chef_client_config.rb +7 -2
  59. data/lib/chef/resource/chef_client_cron.rb +1 -1
  60. data/lib/chef/resource/chef_client_launchd.rb +1 -1
  61. data/lib/chef/resource/chef_client_scheduled_task.rb +46 -3
  62. data/lib/chef/resource/chef_client_systemd_timer.rb +1 -1
  63. data/lib/chef/resource/chef_client_trusted_certificate.rb +2 -2
  64. data/lib/chef/resource/chef_vault_secret.rb +2 -2
  65. data/lib/chef/resource/chocolatey_config.rb +13 -13
  66. data/lib/chef/resource/dsc_resource.rb +1 -1
  67. data/lib/chef/resource/execute.rb +5 -5
  68. data/lib/chef/resource/file/verification/json.rb +50 -0
  69. data/lib/chef/resource/file/verification/yaml.rb +52 -0
  70. data/lib/chef/resource/gem_package.rb +2 -1
  71. data/lib/chef/resource/habitat/_habitat_shared.rb +28 -0
  72. data/lib/chef/resource/habitat/habitat_package.rb +129 -0
  73. data/lib/chef/resource/habitat/habitat_sup.rb +329 -0
  74. data/lib/chef/resource/habitat/habitat_sup_systemd.rb +67 -0
  75. data/lib/chef/resource/habitat/habitat_sup_windows.rb +90 -0
  76. data/lib/chef/resource/habitat_config.rb +107 -0
  77. data/lib/chef/resource/habitat_install.rb +247 -0
  78. data/lib/chef/resource/habitat_service.rb +451 -0
  79. data/lib/chef/resource/habitat_user_toml.rb +92 -0
  80. data/lib/chef/resource/homebrew_cask.rb +1 -1
  81. data/lib/chef/resource/inspec_input.rb +128 -0
  82. data/lib/chef/resource/inspec_waiver.rb +185 -0
  83. data/lib/chef/resource/inspec_waiver_file_entry.rb +2 -2
  84. data/lib/chef/resource/launchd.rb +3 -3
  85. data/lib/chef/resource/lwrp_base.rb +1 -1
  86. data/lib/chef/resource/mount.rb +1 -1
  87. data/lib/chef/resource/registry_key.rb +36 -48
  88. data/lib/chef/resource/remote_file.rb +99 -3
  89. data/lib/chef/resource/rhsm_subscription.rb +5 -5
  90. data/lib/chef/resource/ruby_block.rb +100 -0
  91. data/lib/chef/resource/scm/subversion.rb +1 -1
  92. data/lib/chef/resource/support/HabService.dll.config.erb +19 -0
  93. data/lib/chef/resource/support/client.erb +8 -1
  94. data/lib/chef/resource/support/sup.toml.erb +179 -0
  95. data/lib/chef/resource/sysctl.rb +2 -2
  96. data/lib/chef/resource/systemd_unit.rb +3 -3
  97. data/lib/chef/resource/timezone.rb +2 -2
  98. data/lib/chef/resource/user_ulimit.rb +1 -0
  99. data/lib/chef/resource/windows_defender.rb +163 -0
  100. data/lib/chef/resource/windows_defender_exclusion.rb +125 -0
  101. data/lib/chef/resource/windows_printer.rb +78 -44
  102. data/lib/chef/resource/windows_printer_port.rb +1 -1
  103. data/lib/chef/resource/windows_uac.rb +3 -1
  104. data/lib/chef/resource/windows_update_settings.rb +259 -0
  105. data/lib/chef/resource/windows_user_privilege.rb +1 -1
  106. data/lib/chef/resource/yum_package.rb +1 -5
  107. data/lib/chef/resource.rb +13 -17
  108. data/lib/chef/resource_inspector.rb +6 -2
  109. data/lib/chef/resources.rb +14 -1
  110. data/lib/chef/run_context/cookbook_compiler.rb +112 -28
  111. data/lib/chef/run_context.rb +31 -1
  112. data/lib/chef/secret_fetcher/akeyless_vault.rb +57 -0
  113. data/lib/chef/secret_fetcher/aws_secrets_manager.rb +65 -0
  114. data/lib/chef/secret_fetcher/azure_key_vault.rb +78 -0
  115. data/lib/chef/secret_fetcher/base.rb +76 -0
  116. data/lib/chef/secret_fetcher/example.rb +46 -0
  117. data/lib/chef/secret_fetcher/hashi_vault.rb +100 -0
  118. data/lib/chef/secret_fetcher.rb +61 -0
  119. data/lib/chef/version.rb +1 -1
  120. data/spec/data/archive_file/test_archive.tar.gz +0 -0
  121. data/spec/functional/mixin/from_file_spec.rb +1 -1
  122. data/spec/functional/resource/archive_file_spec.rb +87 -0
  123. data/spec/functional/resource/group_spec.rb +5 -1
  124. data/spec/functional/resource/link_spec.rb +8 -0
  125. data/spec/integration/compliance/compliance_spec.rb +61 -0
  126. data/spec/integration/recipes/recipe_dsl_spec.rb +1 -1
  127. data/spec/integration/recipes/resource_action_spec.rb +6 -6
  128. data/spec/spec_helper.rb +3 -0
  129. data/spec/support/platform_helpers.rb +4 -0
  130. data/spec/support/ruby_installer.rb +51 -0
  131. data/spec/support/shared/unit/provider/file.rb +2 -8
  132. data/spec/unit/compliance/input_spec.rb +104 -0
  133. data/spec/unit/compliance/profile_spec.rb +120 -0
  134. data/spec/unit/compliance/runner_spec.rb +46 -2
  135. data/spec/unit/compliance/waiver_spec.rb +104 -0
  136. data/spec/unit/data_bag_item_spec.rb +2 -2
  137. data/spec/unit/data_bag_spec.rb +1 -1
  138. data/spec/unit/dsl/render_helpers_spec.rb +102 -0
  139. data/spec/unit/dsl/secret_spec.rb +71 -0
  140. data/spec/unit/formatters/doc_spec.rb +1 -1
  141. data/spec/unit/http/basic_client_spec.rb +30 -0
  142. data/spec/unit/http_spec.rb +8 -2
  143. data/spec/unit/policy_builder/dynamic_spec.rb +0 -5
  144. data/spec/unit/policy_builder/policyfile_spec.rb +144 -56
  145. data/spec/unit/provider/apt_update_spec.rb +3 -1
  146. data/spec/unit/provider/link_spec.rb +13 -7
  147. data/spec/unit/provider/mount/aix_spec.rb +1 -1
  148. data/spec/unit/provider/package/powershell_spec.rb +74 -12
  149. data/spec/unit/provider/remote_file/http_spec.rb +10 -0
  150. data/spec/unit/provider/template_spec.rb +2 -2
  151. data/spec/unit/provider_spec.rb +23 -0
  152. data/spec/unit/resource/archive_file_spec.rb +414 -3
  153. data/spec/unit/resource/chef_client_scheduled_task_spec.rb +69 -0
  154. data/spec/unit/resource/file/verification/json_spec.rb +72 -0
  155. data/spec/unit/resource/file/verification/yaml_spec.rb +67 -0
  156. data/spec/unit/resource/homebrew_cask_spec.rb +29 -11
  157. data/spec/unit/resource/inspec_input_spec.rb +300 -0
  158. data/spec/unit/resource/inspec_waiver_spec.rb +312 -0
  159. data/spec/unit/resource/mount_spec.rb +10 -0
  160. data/spec/unit/resource/rhsm_subscription_spec.rb +50 -3
  161. data/spec/unit/resource/systemd_unit_spec.rb +1 -1
  162. data/spec/unit/resource/user_ulimit_spec.rb +14 -1
  163. data/spec/unit/resource/windows_defender_exclusion_spec.rb +62 -0
  164. data/spec/unit/resource/windows_defender_spec.rb +71 -0
  165. data/spec/unit/resource/windows_update_settings_spec.rb +64 -0
  166. data/spec/unit/resource_spec.rb +19 -8
  167. data/spec/unit/secret_fetcher/akeyless_vault_spec.rb +37 -0
  168. data/spec/unit/secret_fetcher/aws_secrets_manager_spec.rb +70 -0
  169. data/spec/unit/secret_fetcher/azure_key_vault_spec.rb +70 -0
  170. data/spec/unit/secret_fetcher/hashi_vault_spec.rb +80 -0
  171. data/spec/unit/secret_fetcher_spec.rb +82 -0
  172. data/tasks/rspec.rb +2 -1
  173. metadata +106 -7
@@ -32,14 +32,8 @@ class Chef
32
32
  # Policyfile is a policy builder implementation that gets run
33
33
  # list and cookbook version information from a single document.
34
34
  #
35
- # == Unsupported Options:
36
- # * override_runlist:: This could potentially be integrated into the
37
- # policyfile, or replaced with a similar feature that has different
38
- # semantics.
39
- # * specific_recipes:: put more design thought into this use case.
40
- # * run_list in json_attribs:: would be ignored anyway, so it raises an error.
41
- # * chef-solo:: not currently supported. Need more design thought around
42
- # how this should work.
35
+ # Does not support legacy chef-solo or roles/environments.
36
+ #
43
37
  class Policyfile
44
38
 
45
39
  class UnsupportedFeature < StandardError; end
@@ -81,10 +75,12 @@ class Chef
81
75
  attr_reader :ohai_data
82
76
  attr_reader :json_attribs
83
77
  attr_reader :run_context
78
+ attr_reader :override_runlist
84
79
 
85
80
  def initialize(node_name, ohai_data, json_attribs, override_runlist, events)
86
81
  @node_name = node_name
87
82
  @ohai_data = ohai_data
83
+ @override_runlist = override_runlist
88
84
  @json_attribs = json_attribs
89
85
  @events = events
90
86
 
@@ -94,32 +90,11 @@ class Chef
94
90
  raise UnsupportedFeature, "Policyfile does not support chef-solo. Use #{ChefUtils::Dist::Infra::CLIENT} local mode instead."
95
91
  end
96
92
 
97
- if override_runlist
98
- raise UnsupportedFeature, "Policyfile does not support override run lists. Use named run_lists instead."
99
- end
100
-
101
- if json_attribs && json_attribs.key?("run_list")
102
- raise UnsupportedFeature, "Policyfile does not support setting the run_list in json data."
103
- end
104
-
105
93
  if Chef::Config[:environment] && !Chef::Config[:environment].chomp.empty?
106
94
  raise UnsupportedFeature, "Policyfile does not work with an Environment configured."
107
95
  end
108
96
  end
109
97
 
110
- ## API Compat ##
111
- # Methods related to unsupported features
112
-
113
- # Override run_list is not supported.
114
- def original_runlist
115
- nil
116
- end
117
-
118
- # Override run_list is not supported.
119
- def override_runlist
120
- nil
121
- end
122
-
123
98
  # Policyfile gives you the run_list already expanded, but users of this
124
99
  # class may expect to get a run_list expansion compatible object by
125
100
  # calling this method.
@@ -148,17 +123,27 @@ class Chef
148
123
  # consume_external_attrs may add items to the run_list. Save the
149
124
  # expanded run_list, which we will pass to the server later to
150
125
  # determine which versions of cookbooks to use.
126
+
127
+ unless Chef::Config[:policy_document_native_api]
128
+ Chef.deprecated(:policyfile_compat_mode, "The chef-server 11 policyfile compat mode is deprecated, please set policy_document_native_api to true in your config")
129
+ end
130
+
151
131
  node.reset_defaults_and_overrides
152
132
 
153
133
  node.consume_external_attrs(ohai_data, json_attribs)
154
134
 
135
+ setup_run_list_override
136
+
155
137
  expand_run_list
156
138
  apply_policyfile_attributes
157
139
 
140
+ if persistent_run_list_set?
141
+ Chef::Log.warn("The node.run_list setting is overriding the Policyfile run_list")
142
+ end
158
143
  Chef::Log.info("Run List is [#{run_list}]")
159
- Chef::Log.info("Run List expands to [#{run_list_with_versions_for_display.join(", ")}]")
144
+ Chef::Log.info("Run List expands to [#{run_list_with_versions_for_display(run_list).join(", ")}]")
160
145
 
161
- events.node_load_completed(node, run_list_with_versions_for_display, Chef::Config)
146
+ events.node_load_completed(node, run_list_with_versions_for_display(run_list), Chef::Config)
162
147
  events.run_list_expanded(run_list_expansion_ish)
163
148
 
164
149
  # we must do this after `node.consume_external_attrs`
@@ -194,6 +179,11 @@ class Chef
194
179
  events.cookbook_compilation_start(run_context)
195
180
 
196
181
  run_context.load(run_list_expansion_ish)
182
+ if specific_recipes
183
+ specific_recipes.each do |recipe_file|
184
+ run_context.load_recipe_file(recipe_file)
185
+ end
186
+ end
197
187
 
198
188
  events.cookbook_compilation_complete(run_context)
199
189
 
@@ -206,7 +196,7 @@ class Chef
206
196
  #
207
197
  # @return [RunListExpansionIsh] A RunListExpansion duck-type.
208
198
  def expand_run_list
209
- CookbookCacheCleaner.instance.skip_removal = true if named_run_list_requested?
199
+ validate_run_list!(run_list)
210
200
 
211
201
  node.run_list(run_list)
212
202
  node.automatic_attrs[:policy_revision] = revision_id
@@ -231,21 +221,25 @@ class Chef
231
221
  cookbooks_to_sync
232
222
  end
233
223
 
234
- # Whether or not this is a temporary policy. Since PolicyBuilder doesn't
235
- # support override_runlist, this is always false.
224
+ ## Internal Public API ##
225
+
226
+ # @api private
236
227
  #
237
- # @return [false]
238
- def temporary_policy?
239
- false
228
+ # Validate run_list against policyfile cookbooks
229
+ #
230
+ def validate_run_list!(run_list)
231
+ run_list.map do |recipe_spec|
232
+ cookbook, recipe = parse_recipe_spec(recipe_spec)
233
+ lock_data = cookbook_lock_for(cookbook)
234
+ raise PolicyfileError, "invalid run_list item '#{recipe_spec}' not in cookbook set of PolicyFile #{policyfile_location}" unless lock_data
235
+ end
240
236
  end
241
237
 
242
- ## Internal Public API ##
243
-
244
238
  # @api private
245
239
  #
246
240
  # Generates an array of strings with recipe names including version and
247
241
  # identifier info.
248
- def run_list_with_versions_for_display
242
+ def run_list_with_versions_for_display(run_list)
249
243
  run_list.map do |recipe_spec|
250
244
  cookbook, recipe = parse_recipe_spec(recipe_spec)
251
245
  lock_data = cookbook_lock_for(cookbook)
@@ -287,9 +281,14 @@ class Chef
287
281
 
288
282
  # @api private
289
283
  def parse_recipe_spec(recipe_spec)
290
- rmatch = recipe_spec.match(/recipe\[([^:]+)::([^:]+)\]/)
284
+ rmatch = recipe_spec.to_s.match(/recipe\[([^:]+)::([^:]+)\]/)
291
285
  if rmatch.nil?
292
- raise PolicyfileError, "invalid recipe specification #{recipe_spec} in Policyfile from #{policyfile_location}"
286
+ rmatch = recipe_spec.to_s.match(/recipe\[([^:]+)\]/)
287
+ if rmatch.nil?
288
+ raise PolicyfileError, "invalid recipe specification #{recipe_spec} in Policyfile from #{policyfile_location}"
289
+ else
290
+ [rmatch[1], "default"]
291
+ end
293
292
  else
294
293
  [rmatch[1], rmatch[2]]
295
294
  end
@@ -301,8 +300,15 @@ class Chef
301
300
  end
302
301
 
303
302
  # @api private
303
+ # @return [Array<String>]
304
304
  def run_list
305
- if named_run_list_requested?
305
+ return override_runlist.map(&:to_s) if override_runlist
306
+
307
+ if json_attribs["run_list"]
308
+ json_attribs["run_list"]
309
+ elsif persistent_run_list_set?
310
+ node.run_list
311
+ elsif named_run_list_requested?
306
312
  named_run_list || raise(ConfigurationError,
307
313
  "Policy '#{retrieved_policy_name}' revision '#{revision_id}' does not have named_run_list '#{named_run_list_name}'" +
308
314
  "(available named_run_lists: [#{available_named_run_lists.join(", ")}])")
@@ -458,7 +464,7 @@ class Chef
458
464
  # should be reduced to a single call.
459
465
  def cookbooks_to_sync
460
466
  @cookbook_to_sync ||= begin
461
- events.cookbook_resolution_start(run_list_with_versions_for_display)
467
+ events.cookbook_resolution_start(run_list_with_versions_for_display(run_list))
462
468
 
463
469
  cookbook_versions_by_name = cookbook_locks.inject({}) do |cb_map, (name, lock_data)|
464
470
  cb_map[name] = manifest_for(name, lock_data)
@@ -470,7 +476,7 @@ class Chef
470
476
  end
471
477
  rescue Exception => e
472
478
  # TODO: wrap/munge exception to provide helpful error output
473
- events.cookbook_resolution_failed(run_list_with_versions_for_display, e)
479
+ events.cookbook_resolution_failed(run_list_with_versions_for_display(run_list), e)
474
480
  raise
475
481
  end
476
482
 
@@ -509,6 +515,13 @@ class Chef
509
515
  Chef::Config
510
516
  end
511
517
 
518
+ # Indicates whether the policy is temporary, which means an
519
+ # override_runlist was provided. Chef::Client uses this to decide whether
520
+ # to do the final node save at the end of the run or not.
521
+ def temporary_policy?
522
+ node.override_runlist_set?
523
+ end
524
+
512
525
  private
513
526
 
514
527
  # This method injects the run_context and into the Chef class.
@@ -533,6 +546,10 @@ class Chef
533
546
  (policy["named_run_lists"] || {}).keys
534
547
  end
535
548
 
549
+ def persistent_run_list_set?
550
+ Chef::Config[:policy_persist_run_list] && node.run_list && !node.run_list.empty?
551
+ end
552
+
536
553
  def named_run_list_requested?
537
554
  !!Chef::Config[:named_run_list]
538
555
  end
@@ -567,6 +584,32 @@ class Chef
567
584
  Chef::CookbookVersion.from_cb_artifact_data(raw_manifest)
568
585
  end
569
586
 
587
+ def setup_run_list_override
588
+ unless override_runlist.nil?
589
+ runlist_override_sanity_check!
590
+ node.override_runlist = override_runlist
591
+ Chef::Log.warn "Run List override has been provided."
592
+ Chef::Log.warn "Original Run List: [#{node.primary_runlist}]"
593
+ Chef::Log.warn "Overridden Run List: [#{node.run_list}]"
594
+ end
595
+ end
596
+
597
+ # Ensures runlist override contains RunListItem instances
598
+ def runlist_override_sanity_check!
599
+ # Convert to array and remove whitespace
600
+ if override_runlist.is_a?(String)
601
+ @override_runlist = override_runlist.split(",").map(&:strip)
602
+ end
603
+ @override_runlist = [override_runlist].flatten.compact
604
+ override_runlist.map! do |item|
605
+ if item.is_a?(Chef::RunList::RunListItem)
606
+ item
607
+ else
608
+ Chef::RunList::RunListItem.new(item)
609
+ end
610
+ end
611
+ end
612
+
570
613
  end
571
614
  end
572
615
  end
@@ -41,7 +41,7 @@ class Chef
41
41
  end
42
42
  end
43
43
 
44
- action :run do
44
+ action :run, description: "Run a command." do
45
45
  if creates && sentinel_file.exist?
46
46
  logger.debug("#{new_resource} sentinel file #{sentinel_file} exists - nothing to do")
47
47
  return false
@@ -27,6 +27,8 @@ require_relative "../scan_access_control"
27
27
  require_relative "../mixin/checksum"
28
28
  require_relative "../mixin/file_class"
29
29
  require_relative "../mixin/enforce_ownership_and_permissions"
30
+ require_relative "../resource/file/verification/json"
31
+ require_relative "../resource/file/verification/yaml"
30
32
  require_relative "../util/backup"
31
33
  require_relative "../util/diff"
32
34
  require_relative "../util/selinux"
@@ -157,7 +159,7 @@ class Chef
157
159
  end
158
160
 
159
161
  action :delete do
160
- if ::File.exists?(new_resource.path)
162
+ if ::File.exist?(new_resource.path)
161
163
  converge_by("delete file #{new_resource.path}") do
162
164
  do_backup unless file_class.symlink?(new_resource.path)
163
165
  ::File.delete(new_resource.path)
@@ -393,7 +395,7 @@ class Chef
393
395
  # a nil tempfile is okay, means the resource has no content or no new content
394
396
  return if tempfile.nil?
395
397
  # but a tempfile that has no path or doesn't exist should not happen
396
- if tempfile.path.nil? || !::File.exists?(tempfile.path)
398
+ if tempfile.path.nil? || !::File.exist?(tempfile.path)
397
399
  raise "#{ChefUtils::Dist::Infra::CLIENT} is confused, trying to deploy a file that has no path or does not exist..."
398
400
  end
399
401
 
@@ -158,7 +158,7 @@ class Chef
158
158
  if new_resource.group_name && (current_resource.group_name != new_resource.group_name)
159
159
  dscl_create_group
160
160
  end
161
- if new_resource.gid && (current_resource.gid != new_resource.gid)
161
+ if new_resource.gid && (current_resource.gid != new_resource.gid.to_s)
162
162
  set_gid
163
163
  end
164
164
  if new_resource.members || new_resource.excluded_members
@@ -43,22 +43,22 @@ class Chef
43
43
  types[type]
44
44
  end
45
45
 
46
- action :create do
46
+ action :create, description: "Create a launchd property list." do
47
47
  manage_plist(:create)
48
48
  end
49
49
 
50
- action :create_if_missing do
50
+ action :create_if_missing, description: "Create a launchd property list, if it does not already exist." do
51
51
  manage_plist(:create_if_missing)
52
52
  end
53
53
 
54
- action :delete do
54
+ action :delete, description: "Delete a launchd property list. This will unload a daemon or agent, if loaded." do
55
55
  if ::File.exists?(path)
56
56
  manage_service(:disable)
57
57
  end
58
58
  manage_plist(:delete)
59
59
  end
60
60
 
61
- action :enable do
61
+ action :enable, description: "Create a launchd property list, and then ensure that it is enabled. If a launchd property list already exists, but does not match, updates the property list to match, and then restarts the daemon or agent." do
62
62
  manage_service(:nothing)
63
63
  manage_plist(:create) do
64
64
  notifies :restart, "macosx_service[#{label}]", :immediately
@@ -66,13 +66,13 @@ class Chef
66
66
  manage_service(:enable)
67
67
  end
68
68
 
69
- action :disable do
69
+ action :disable, description: "Disable a launchd property list." do
70
70
  return unless ::File.exist?(path)
71
71
 
72
72
  manage_service(:disable)
73
73
  end
74
74
 
75
- action :restart do
75
+ action :restart, description: "Restart a launchd managed daemon or agent." do
76
76
  manage_service(:restart)
77
77
  end
78
78
 
@@ -43,8 +43,8 @@ class Chef
43
43
  )
44
44
  else
45
45
  current_resource.link_type(:hard)
46
- if ::File.exists?(current_resource.target_file)
47
- if ::File.exists?(new_resource.to) &&
46
+ if ::File.exist?(current_resource.target_file)
47
+ if ::File.exist?(new_resource.to) &&
48
48
  file_class.stat(current_resource.target_file).ino ==
49
49
  file_class.stat(new_resource.to).ino
50
50
  current_resource.to(canonicalize(new_resource.to))
@@ -45,7 +45,7 @@ class Chef
45
45
  def load_current_resource; end
46
46
 
47
47
  # class methods
48
- class <<self
48
+ class << self
49
49
  include Chef::Mixin::ConvertToClassName
50
50
  include Chef::Mixin::FromFile
51
51
 
@@ -0,0 +1,168 @@
1
+ #
2
+ # Copyright:: Chef Software Inc.
3
+ #
4
+ # License:: Apache License, Version 2.0
5
+ #
6
+ # Licensed under the Apache License, Version 2.0 (the "License");
7
+ # you may not use this file except in compliance with the License.
8
+ # You may obtain a copy of the License at
9
+ #
10
+ # http://www.apache.org/licenses/LICENSE-2.0
11
+ #
12
+ # Unless required by applicable law or agreed to in writing, software
13
+ # distributed under the License is distributed on an "AS IS" BASIS,
14
+ # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15
+ # See the License for the specific language governing permissions and
16
+ # limitations under the License.
17
+ #
18
+ require_relative "../../http/simple"
19
+ require_relative "../../json_compat"
20
+ require_relative "../../exceptions"
21
+ require_relative "../package"
22
+ # Bring in needed shared methods
23
+
24
+ class Chef
25
+ class Provider
26
+ class Package
27
+ class Habitat < Chef::Provider::Package
28
+ use_multipackage_api
29
+ use "../../resource/habitat/habitat_shared"
30
+ provides :habitat_package
31
+
32
+ def load_current_resource
33
+ @current_resource = Chef::Resource::HabitatPackage.new(new_resource.name)
34
+ current_resource.package_name(strip_version(new_resource.package_name))
35
+
36
+ @candidate_version = candidate_versions
37
+ current_resource.version(current_versions)
38
+
39
+ current_resource
40
+ end
41
+
42
+ def install_package(names, versions)
43
+ names.zip(versions).map do |n, v|
44
+ opts = ["pkg", "install", "--channel", new_resource.channel, "--url", new_resource.bldr_url]
45
+ opts += ["--auth", new_resource.auth_token] if new_resource.auth_token
46
+ opts += ["#{strip_version(n)}/#{v}", new_resource.options]
47
+ opts += ["--binlink"] if new_resource.binlink
48
+ opts += ["--force"] if new_resource.binlink.eql? :force
49
+ hab(opts)
50
+ end
51
+ end
52
+
53
+ alias_method :upgrade_package, :install_package
54
+
55
+ def remove_package(names, versions)
56
+ # raise 'It is too dangerous to :remove packages with the habitat_package resource right now. This functionality should be deferred to the hab cli.'
57
+ names.zip(versions).map do |n, v|
58
+ opts = %w{pkg uninstall}
59
+ opts += ["--keep-latest", new_resource.keep_latest ] if new_resource.keep_latest
60
+ opts += ["#{strip_version(n).chomp("/")}#{v}", new_resource.options]
61
+ opts += ["--exclude"] if new_resource.exclude
62
+ opts += ["--no-deps"] if new_resource.no_deps
63
+ hab(opts)
64
+ # action :remove
65
+ end
66
+ end
67
+
68
+ alias_method :purge_package, :remove_package
69
+
70
+ private
71
+
72
+ def validate_name!(name)
73
+ raise ArgumentError, "package name must be specified as 'origin/name', use the 'version' property to specify a version" unless name.squeeze("/").count("/") < 2
74
+ end
75
+
76
+ def strip_version(name)
77
+ validate_name!(name)
78
+ n = name.squeeze("/").chomp("/").sub(%r{^\/}, "")
79
+ n = n[0..(n.rindex("/") - 1)] while n.count("/") >= 2
80
+ n
81
+ end
82
+
83
+ def platform_target
84
+ if windows?
85
+ "target=x86_64-windows"
86
+ elsif node["kernel"]["release"].to_i < 3
87
+ "target=x86_64-linux-kernel2"
88
+ else
89
+ ""
90
+ end
91
+ end
92
+
93
+ def depot_package(name, version = nil)
94
+ @depot_package ||= {}
95
+ @depot_package[name] ||=
96
+ begin
97
+ origin, pkg_name = name.split("/")
98
+ name_version = [pkg_name, version].compact.join("/").squeeze("/").chomp("/").sub(%r{^\/}, "")
99
+ url = if new_resource.bldr_url.include?("/v1/")
100
+ "#{new_resource.bldr_url.chomp("/")}/depot/channels/#{origin}/#{new_resource.channel}/pkgs/#{name_version}"
101
+ else
102
+ "#{new_resource.bldr_url.chomp("/")}/v1/depot/channels/#{origin}/#{new_resource.channel}/pkgs/#{name_version}"
103
+ end
104
+ url << "/latest" unless name_version.count("/") >= 2
105
+ url << "?#{platform_target}" unless platform_target.empty?
106
+
107
+ headers = {}
108
+ headers["Authorization"] = "Bearer #{new_resource.auth_token}" if new_resource.auth_token
109
+
110
+ Chef::JSONCompat.parse(http.get(url, headers))
111
+ rescue Net::HTTPServerException
112
+ nil
113
+ end
114
+ end
115
+
116
+ def package_version(name, version = nil)
117
+ p = depot_package(name, version)
118
+ "#{p["ident"]["version"]}/#{p["ident"]["release"]}" unless p.nil?
119
+ end
120
+
121
+ def http
122
+ # FIXME: use SimpleJSON when the depot mime-type is fixed
123
+ @http ||= Chef::HTTP::Simple.new(new_resource.bldr_url.to_s)
124
+ end
125
+
126
+ def candidate_versions
127
+ package_name_array.zip(new_version_array).map do |n, v|
128
+ package_version(n, v)
129
+ end
130
+ end
131
+
132
+ def current_versions
133
+ package_name_array.map do |n|
134
+ installed_version(n)
135
+ end
136
+ end
137
+
138
+ def installed_version(ident)
139
+ hab("pkg", "path", ident).stdout.chomp.split(windows? ? "\\" : "/")[-2..-1].join("/")
140
+ rescue Mixlib::ShellOut::ShellCommandFailed
141
+ nil
142
+ end
143
+
144
+ # This is used by the superclass Chef::Provider::Package
145
+ def version_requirement_satisfied?(current_version, new_version)
146
+ return false if new_version.nil? || current_version.nil?
147
+
148
+ nv_parts = new_version.squeeze("/").split("/")
149
+
150
+ if nv_parts.count < 2
151
+ current_version.squeeze("/").split("/")[0] == new_version.squeeze("/")
152
+ else
153
+ current_version.squeeze("/") == new_resource.version.squeeze("/")
154
+ end
155
+ end
156
+
157
+ # This is used by the superclass Chef::Provider::Package
158
+ def version_compare(v1, v2)
159
+ require "mixlib/versioning" unless defined?(Mixlib::Versioning)
160
+ # Convert the package version (X.Y.Z/DATE) into a version that Mixlib::Versioning understands (X.Y.Z+DATE)
161
+ hab_v1 = Mixlib::Versioning.parse(v1.tr("/", "+"))
162
+ hab_v2 = Mixlib::Versioning.parse(v2.tr("/", "+"))
163
+ hab_v1 <=> hab_v2
164
+ end
165
+ end
166
+ end
167
+ end
168
+ end
@@ -124,6 +124,11 @@ class Chef
124
124
  command.push("-RequiredVersion #{version}") if version
125
125
  command.push("-Source #{new_resource.source}") if new_resource.source && cmdlet_name =~ Regexp.union(/Install-Package/, /Find-Package/)
126
126
  command.push("-SkipPublisherCheck") if new_resource.skip_publisher_check && cmdlet_name !~ /Find-Package/
127
+ if new_resource.options && cmdlet_name !~ Regexp.union(/Get-Package/, /Find-Package/)
128
+ new_resource.options.each do |arg|
129
+ command.push(arg) unless command.include?(arg)
130
+ end
131
+ end
127
132
  command.push(").Version")
128
133
  command.join(" ")
129
134
  end
@@ -19,7 +19,7 @@
19
19
 
20
20
  require_relative "../config"
21
21
  require_relative "../log"
22
- require_relative "../resource/file"
22
+ require_relative "../resource/registry_key"
23
23
  require_relative "../mixin/checksum"
24
24
  require_relative "../provider"
25
25
  require "etc" unless defined?(Etc)
@@ -50,7 +50,8 @@ class Chef
50
50
  current_resource.architecture(new_resource.architecture)
51
51
  current_resource.recursive(new_resource.recursive)
52
52
  if registry.key_exists?(new_resource.key)
53
- current_resource.values(registry.get_values(new_resource.key))
53
+ current_registry_values = registry.get_values(new_resource.key) || []
54
+ current_resource.values(current_registry_values)
54
55
  end
55
56
  values_to_hash(current_resource.unscrubbed_values)
56
57
  current_resource
@@ -137,7 +137,7 @@ class Chef
137
137
  if new_resource.ssl_verify_mode
138
138
  opts[:ssl_verify_mode] = new_resource.ssl_verify_mode
139
139
  end
140
- opts
140
+ opts.merge(new_resource.http_options)
141
141
  end
142
142
 
143
143
  end
@@ -55,7 +55,7 @@ class Chef
55
55
  end
56
56
  end
57
57
 
58
- action :checkout do
58
+ action :checkout, description: "Clone or check out the source. When a checkout is available, this provider does nothing." do
59
59
  if target_dir_non_existent_or_empty?
60
60
  converge_by("perform checkout of #{new_resource.repository} into #{new_resource.destination}") do
61
61
  shell_out!(checkout_command, run_options)
@@ -65,7 +65,7 @@ class Chef
65
65
  end
66
66
  end
67
67
 
68
- action :export do
68
+ action :export, description: "Export the source, excluding or removing any version control artifacts." do
69
69
  if target_dir_non_existent_or_empty?
70
70
  action_force_export
71
71
  else
@@ -73,13 +73,13 @@ class Chef
73
73
  end
74
74
  end
75
75
 
76
- action :force_export do
76
+ action :force_export, description: "Export the source, excluding or removing any version control artifacts and force an export of the source that is overwriting the existing copy (if it exists)." do
77
77
  converge_by("export #{new_resource.repository} into #{new_resource.destination}") do
78
78
  shell_out!(export_command, run_options)
79
79
  end
80
80
  end
81
81
 
82
- action :sync do
82
+ action :sync, description: "Update the source to the specified version, or get a new clone or checkout. This action causes a hard reset of the index and working tree, discarding any uncommitted changes." do
83
83
  assert_target_directory_valid!
84
84
  if ::File.exist?(::File.join(new_resource.destination, ".svn"))
85
85
  current_rev = find_current_revision
@@ -1,4 +1,4 @@
1
- # This file was generated by Chef
1
+ # This file was generated by Chef Infra
2
2
  # Do NOT modify this file by hand.
3
3
 
4
4
  [<%= @config.repositoryid %>]