chef-apply 0.4.12 → 0.5.16

Sign up to get free protection for your applications and to get access to all the features.
Files changed (34) hide show
  1. checksums.yaml +4 -4
  2. data/Gemfile +2 -2
  3. data/bin/chef-run +1 -1
  4. data/chef-apply.gemspec +10 -15
  5. data/i18n/en.yml +3 -2
  6. data/i18n/errors/en.yml +14 -6
  7. data/lib/chef_apply/action/base.rb +2 -2
  8. data/lib/chef_apply/action/converge_target.rb +4 -4
  9. data/lib/chef_apply/action/converge_target/ccr_failure_mapper.rb +1 -1
  10. data/lib/chef_apply/action/generate_local_policy.rb +3 -2
  11. data/lib/chef_apply/action/generate_temp_cookbook.rb +4 -4
  12. data/lib/chef_apply/action/generate_temp_cookbook/recipe_lookup.rb +5 -5
  13. data/lib/chef_apply/action/generate_temp_cookbook/temp_cookbook.rb +6 -6
  14. data/lib/chef_apply/action/install_chef.rb +4 -4
  15. data/lib/chef_apply/action/install_chef/minimum_chef_version.rb +2 -2
  16. data/lib/chef_apply/cli.rb +27 -29
  17. data/lib/chef_apply/cli/help.rb +1 -1
  18. data/lib/chef_apply/cli/options.rb +3 -3
  19. data/lib/chef_apply/cli/validation.rb +3 -1
  20. data/lib/chef_apply/config.rb +6 -6
  21. data/lib/chef_apply/errors/standard_error_resolver.rb +2 -2
  22. data/lib/chef_apply/file_fetcher.rb +4 -4
  23. data/lib/chef_apply/startup.rb +21 -12
  24. data/lib/chef_apply/target_host.rb +7 -5
  25. data/lib/chef_apply/target_resolver.rb +2 -2
  26. data/lib/chef_apply/telemeter.rb +10 -128
  27. data/lib/chef_apply/telemeter/patch.rb +1 -1
  28. data/lib/chef_apply/text.rb +2 -2
  29. data/lib/chef_apply/ui/error_printer.rb +6 -6
  30. data/lib/chef_apply/ui/plain_text_header.rb +1 -2
  31. data/lib/chef_apply/ui/terminal.rb +5 -5
  32. data/lib/chef_apply/version.rb +1 -1
  33. metadata +17 -32
  34. data/lib/chef_apply/telemeter/sender.rb +0 -121
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 6838824639553486d507ce912e1346c743de3dc13d93c75930ba87392bd3750b
4
- data.tar.gz: 1866addf7d4356516b5afd94a21e59de43c32c2fef117a71bec883950ded266f
3
+ metadata.gz: 40e1ef3f302762a273ab6fcdf15f0102bf0de5199d20cd22df2125a237551ab5
4
+ data.tar.gz: f65616505eed1c2afd0393b45709ad683c8372903790408a6c1020003122487a
5
5
  SHA512:
6
- metadata.gz: 36712f4c00946b09a9d20b1c859c02041213453baf7d6404f3b3dc064eb8f40267fce2267f614477016535fc4de88a1f4ca882cec8b365a91e932719a888438e
7
- data.tar.gz: 30b001fcf8643a2bd8aaed14798162721f26c0a9b1959f74ac56bdbe4035b4c6017244a6750397a6bb1f232938ab4947e408567d4a3a58fb2209ba9c9939704c
6
+ metadata.gz: 72f59e61c72e8f8f470b392344e382193a2e51d977d9f9a8687ff9fa86563e2fdfe512bbd2d12d8fb418f5734b229a92b6947fc9a587e10df7630456d0229a47
7
+ data.tar.gz: ed03fd5cb7b9cbf2af42cf987a55e2821d8098989ee067f105a6af28413ab50d782c1824e8a5f2e79f43f54063b46a80b20a8b9597a081acded5a13044010317
data/Gemfile CHANGED
@@ -1,5 +1,5 @@
1
1
  #
2
- # Copyright:: Copyright (c) 2018 Chef Software Inc.
2
+ # Copyright:: Copyright (c) Chef Software Inc.
3
3
  # License:: Apache License, Version 2.0
4
4
  #
5
5
  # Licensed under the Apache License, Version 2.0 (the "License");
@@ -19,7 +19,7 @@ source "https://rubygems.org"
19
19
  gemspec
20
20
 
21
21
  group :development do
22
- gem "chefstyle"
22
+ gem "chefstyle", "1.7.2"
23
23
  gem "rake", ">= 10.1.0"
24
24
  gem "rspec", "~> 3.0"
25
25
  gem "simplecov"
data/bin/chef-run CHANGED
@@ -20,4 +20,4 @@ require "chef_apply/startup"
20
20
 
21
21
  # Perform initialization tasks then hand off control to
22
22
  # CLI to run the command.
23
- ChefApply::Startup.new(ARGV).run
23
+ ChefApply::Startup.new(ARGV).run(enforce_license: true)
data/chef-apply.gemspec CHANGED
@@ -15,7 +15,7 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- lib = File.expand_path("../lib", __FILE__)
18
+ lib = File.expand_path("lib", __dir__)
19
19
  $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
20
20
  require "chef_apply/version"
21
21
 
@@ -29,7 +29,7 @@ Gem::Specification.new do |spec|
29
29
  spec.description = "Ad-hoc management of individual nodes and devices."
30
30
  spec.homepage = "https://github.com/chef/chef-apply"
31
31
  spec.license = "Apache-2.0"
32
- spec.required_ruby_version = ">= 2.5.0"
32
+ spec.required_ruby_version = ">= 2.6"
33
33
 
34
34
  spec.files = %w{Rakefile LICENSE warning.txt} +
35
35
  Dir.glob("Gemfile*") + # Includes Gemfile and locks
@@ -40,24 +40,19 @@ Gem::Specification.new do |spec|
40
40
  spec.require_paths = ["lib"]
41
41
 
42
42
  spec.add_dependency "mixlib-cli" # Provides argument handling DSL for CLI applications
43
- spec.add_dependency "mixlib-config", ">= 3.0.5" # shared chef configuration library that
44
- # simplifies managing a configuration file
43
+ spec.add_dependency "mixlib-config", ">= 3.0.5" # shared chef configuration library that simplifies managing a configuration file
45
44
  spec.add_dependency "mixlib-log" # Basis for our traditional logger
46
45
  spec.add_dependency "mixlib-install" # URL resolver + install tool for chef products
47
- spec.add_dependency "r18n-desktop" # easy path to message text management via
48
- # localization gem...
49
- spec.add_dependency "toml-rb" # This isn't ideal because mixlib-config uses 'tomlrb'
50
- # but that library does not support a dumper
46
+ spec.add_dependency "r18n-desktop" # easy path to message text management via localization gem...
47
+ spec.add_dependency "toml-rb" # This isn't ideal because mixlib-config uses 'tomlrb' but that library does not support a dumper
51
48
  spec.add_dependency "train-core", "~> 3.0" # remote connection management over ssh, winrm
52
49
  spec.add_dependency "train-winrm" # winrm transports were pulled out into this plugin
53
50
  spec.add_dependency "pastel" # A color library
54
51
  spec.add_dependency "tty-spinner" # Pretty output for status updates in the CLI
55
- spec.add_dependency "chef", ">= 15.0" # Needed to load cookbooks
56
- spec.add_dependency "chef-cli", ">= 1.0.3 " # Policyfile
57
- spec.add_dependency "chef-telemetry", "<= 0.1.10" # telemetry, updates required to pull in later versions
58
- spec.add_dependency "license-acceptance", "~> 1.0", ">= 1.0.11"
52
+ spec.add_dependency "chef", ">= 16.0" # Needed to load cookbooks
53
+ spec.add_dependency "chef-cli", ">= 2.0.10 " # Policyfile
54
+ spec.add_dependency "chef-telemetry", ">= 1.0.2"
55
+ spec.add_dependency "license-acceptance", ">= 1.0.11", "< 3"
59
56
 
60
- spec.add_development_dependency "bundler"
61
-
62
- spec.post_install_message = File.read(File.expand_path("../warning.txt", __FILE__))
57
+ spec.post_install_message = File.read(File.expand_path("warning.txt", __dir__))
63
58
  end
data/i18n/en.yml CHANGED
@@ -25,10 +25,10 @@ cli:
25
25
  %1:
26
26
 
27
27
  [telemetry]
28
- enable=false
28
+ enabled=false
29
29
 
30
30
  For more information about what we data gather and additional opt-out
31
- options, visit https://chef.sh/docs/chef-workstation/privacy/
31
+ options, visit https://docs.chef.io/workstation/privacy/
32
32
 
33
33
  description: |
34
34
  Chef Run is a tool to execute ad-hoc tasks using Chef.
@@ -113,6 +113,7 @@ cli:
113
113
  cookbook is found we run the default recipe.
114
114
  3. This behaves similarly to 'cookbook name' above, but it also allows
115
115
  you to specify which recipe to use from the cookbook.
116
+ Usage: cookbookname::recipename
116
117
  error:
117
118
  bad_config_file: |
118
119
 
data/i18n/errors/en.yml CHANGED
@@ -146,7 +146,7 @@ errors:
146
146
  For more information, please consult the documentation
147
147
  for this resource:
148
148
 
149
- https://docs.chef.io/resource_reference.html
149
+ https://docs.chef.io/resources/
150
150
 
151
151
  CHEFCCR004:
152
152
  text: |
@@ -157,7 +157,7 @@ errors:
157
157
  Please consult the documentation for properties
158
158
  supported by your resource and their valid values:
159
159
 
160
- https://docs.chef.io/resource_reference.html
160
+ https://docs.chef.io/resources/
161
161
 
162
162
  CHEFCCR005:
163
163
  text: |
@@ -165,7 +165,7 @@ errors:
165
165
 
166
166
  Please consult the documentation for a list of valid resources:
167
167
 
168
- https://docs.chef.io/resource_reference.html
168
+ https://docs.chef.io/resources/
169
169
 
170
170
  CHEFCCR006:
171
171
  text: |
@@ -174,7 +174,7 @@ errors:
174
174
  Please consult the documentation for %2 for a list of
175
175
  valid properties:
176
176
 
177
- https://docs.chef.io/resource_reference.html
177
+ https://docs.chef.io/resources/
178
178
 
179
179
  CHEFCCR099:
180
180
  text: |
@@ -246,7 +246,7 @@ errors:
246
246
 
247
247
  Additional instructions can be found in the troubleshooting documentation:
248
248
 
249
- https://www.chef.sh/docs/chef-workstation/troubleshooting/#error-code-cheftrn007
249
+ https://docs.chef.io/workstation/troubleshooting/#cheftrn007
250
250
 
251
251
  CHEFTRN999:
252
252
  text: |
@@ -257,6 +257,14 @@ errors:
257
257
  %1
258
258
 
259
259
  # CLI argument validation errors
260
+ #
261
+ CHEFVAL001:
262
+ display: { decorations: false }
263
+ text: |
264
+ The key file you specified does not exist or can't be read.
265
+
266
+ You provided '%1'.
267
+
260
268
  CHEFVAL002:
261
269
  display: { decorations: false }
262
270
  text: |
@@ -311,7 +319,7 @@ errors:
311
319
  CHEFVAL009:
312
320
  display: { decorations: false }
313
321
  text: |
314
- File extension '%1' is unsupported. Currently recipes must be specified with a `.rb` extension.
322
+ File extension '%1' is unsupported. Currently recipes must be specified with a `.rb` or `.yml` extension.
315
323
 
316
324
  CHEFVAL010:
317
325
  display: { decorations: false }
@@ -15,8 +15,8 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "chef_apply/telemeter"
19
- require "chef_apply/error"
18
+ require "chef/telemeter"
19
+ require_relative "../error"
20
20
 
21
21
  module ChefApply
22
22
  module Action
@@ -15,9 +15,9 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "chef_apply/action/base"
19
- require "pathname"
20
- require "tempfile"
18
+ require_relative "base"
19
+ require "pathname" unless defined?(Pathname)
20
+ require "tempfile" unless defined?(Tempfile)
21
21
  # FLAG: require "chef/util/path_helper"
22
22
  require "chef/util/path_helper"
23
23
 
@@ -159,7 +159,7 @@ module ChefApply::Action
159
159
  end
160
160
 
161
161
  def handle_ccr_error
162
- require "chef_apply/action/converge_target/ccr_failure_mapper"
162
+ require_relative "converge_target/ccr_failure_mapper"
163
163
  mapper_opts = {}
164
164
  content = target_host.fetch_file_contents(chef_report_path)
165
165
  if content.nil?
@@ -15,7 +15,7 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "chef_apply/error"
18
+ require_relative "../../error"
19
19
 
20
20
  module ChefApply
21
21
  module Action
@@ -15,8 +15,8 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "chef_apply/action/base"
19
- require "chef_apply/error"
18
+ require_relative "base"
19
+ require_relative "../error"
20
20
  module ChefApply::Action
21
21
  class GenerateLocalPolicy < Base
22
22
  attr_reader :archive_file_location
@@ -53,6 +53,7 @@ module ChefApply::Action
53
53
  end
54
54
 
55
55
  end
56
+
56
57
  class PolicyfileInstallError < ChefApply::Error
57
58
  def initialize(cause_err); super("CHEFPOLICY001", cause_err.message); end
58
59
  end
@@ -14,8 +14,8 @@
14
14
  # See the License for the specific language governing permissions and
15
15
  # limitations under the License.
16
16
  #
17
- require "chef_apply/action/base"
18
- require "chef_apply/error"
17
+ require_relative "base"
18
+ require_relative "../error"
19
19
  module ChefApply
20
20
  module Action
21
21
  class GenerateTempCookbook < Base
@@ -35,7 +35,7 @@ module ChefApply
35
35
 
36
36
  def initialize(options)
37
37
  super(options)
38
- require "chef_apply/action/generate_temp_cookbook/temp_cookbook"
38
+ require_relative "generate_temp_cookbook/temp_cookbook"
39
39
  @generated_cookbook ||= TempCookbook.new
40
40
  end
41
41
 
@@ -59,7 +59,7 @@ module ChefApply
59
59
  ChefApply::Log.debug("#{recipe_specifier} is a valid path to a recipe")
60
60
  recipe_path = recipe_specifier
61
61
  else
62
- require "chef_apply/action/generate_temp_cookbook/recipe_lookup"
62
+ require_relative "generate_temp_cookbook/recipe_lookup"
63
63
  rl = RecipeLookup.new(repo_paths)
64
64
  cookbook_path_or_name, optional_recipe_name = rl.split(recipe_specifier)
65
65
  cookbook = rl.load_cookbook(cookbook_path_or_name)
@@ -16,10 +16,10 @@
16
16
  #
17
17
 
18
18
  require "chef-config/config"
19
- require "chef_apply/config"
20
- require "chef_apply/error"
21
- require "chef_apply/log"
22
- require "chef_apply/action/base"
19
+ require_relative "../../config"
20
+ require_relative "../../error"
21
+ require_relative "../../log"
22
+ require_relative "../base"
23
23
 
24
24
  module ChefApply
25
25
  module Action
@@ -81,7 +81,7 @@ module ChefApply
81
81
  # Find the specified recipe or default recipe if none is specified.
82
82
  # Raise an error if recipe cannot be found.
83
83
  def find_recipe(cookbook, recipe_name = nil)
84
- recipes = cookbook.recipe_filenames_by_name
84
+ recipes = cookbook.recipe_filenames_by_name.merge(cookbook.recipe_yml_filenames_by_name)
85
85
  if recipe_name.nil?
86
86
  default_recipe = recipes["default"]
87
87
  raise NoDefaultRecipe.new(cookbook.root_dir, cookbook.name) if default_recipe.nil?
@@ -15,11 +15,11 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "tmpdir"
19
- require "fileutils"
20
- require "chef_apply/log"
21
- require "chef_apply/error"
22
- require "chef_apply/action/generate_temp_cookbook"
18
+ require "tmpdir" unless defined?(Dir.mktmpdir)
19
+ require "fileutils" unless defined?(FileUtils)
20
+ require_relative "../../log"
21
+ require_relative "../../error"
22
+ require_relative "../generate_temp_cookbook"
23
23
  module ChefApply
24
24
  module Action
25
25
  class GenerateTempCookbook
@@ -34,7 +34,7 @@ module ChefApply
34
34
 
35
35
  def from_existing_recipe(existing_recipe_path)
36
36
  ext_name = File.extname(existing_recipe_path)
37
- raise UnsupportedExtension.new(ext_name) unless ext_name == ".rb"
37
+ raise UnsupportedExtension.new(ext_name) unless ext_name == ".rb" || ext_name == ".yml"
38
38
 
39
39
  cb = cookbook_for_recipe(existing_recipe_path)
40
40
  if cb
@@ -15,9 +15,9 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "chef_apply/action/base"
19
- require "chef_apply/action/install_chef/minimum_chef_version"
20
- require "fileutils"
18
+ require_relative "base"
19
+ require_relative "install_chef/minimum_chef_version"
20
+ require "fileutils" unless defined?(FileUtils)
21
21
 
22
22
  module ChefApply
23
23
  module Action
@@ -104,7 +104,7 @@ module ChefApply
104
104
  end
105
105
 
106
106
  def download_to_workstation(url_path)
107
- require "chef_apply/file_fetcher"
107
+ require_relative "../file_fetcher"
108
108
  ChefApply::FileFetcher.fetch(url_path)
109
109
  end
110
110
 
@@ -15,8 +15,8 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "chef_apply/error"
19
- require "chef_apply/action/install_chef/minimum_chef_version"
18
+ require_relative "../../error"
19
+ require_relative "minimum_chef_version"
20
20
 
21
21
  module ChefApply
22
22
  module Action
@@ -15,29 +15,29 @@
15
15
  # See the License for the specific language governing permissions and
16
16
  # limitations under the License.
17
17
  #
18
- require "mixlib/cli"
18
+ require "mixlib/cli" unless defined?(Mixlib::CLI)
19
19
 
20
- require "chef_apply/config"
20
+ require_relative "config"
21
21
  require "chef-config/config"
22
22
  require "chef-config/logger"
23
23
 
24
- require "chef_apply/cli/validation"
25
- require "chef_apply/cli/options"
26
- require "chef_apply/cli/help"
27
- require "chef_apply/error"
28
- require "chef_apply/log"
29
- require "chef_apply/target_host"
30
- require "chef_apply/target_resolver"
31
- require "chef_apply/telemeter"
32
- require "chef_apply/ui/error_printer"
33
- require "chef_apply/ui/terminal"
34
- require "chef_apply/ui/terminal/job"
24
+ require_relative "cli/validation"
25
+ require_relative "cli/options"
26
+ require_relative "cli/help"
27
+ require_relative "error"
28
+ require_relative "log"
29
+ require_relative "target_host"
30
+ require_relative "target_resolver"
31
+ require_relative "telemeter"
32
+ require_relative "ui/error_printer"
33
+ require_relative "ui/terminal"
34
+ require_relative "ui/terminal/job"
35
35
  require "license_acceptance/cli_flags/mixlib_cli"
36
36
  require "license_acceptance/acceptor"
37
37
 
38
- require "chef_apply/action/generate_temp_cookbook"
39
- require "chef_apply/action/generate_local_policy"
40
- require "chef_apply/action/converge_target"
38
+ require_relative "action/generate_temp_cookbook"
39
+ require_relative "action/generate_local_policy"
40
+ require_relative "action/converge_target"
41
41
 
42
42
  module ChefApply
43
43
  class CLI
@@ -63,24 +63,22 @@ module ChefApply
63
63
  super()
64
64
  end
65
65
 
66
- def run
66
+ def run(enforce_license: false)
67
67
  # Perform a timing and capture of the run. Individual methods and actions may perform
68
- # nested Telemeter.timed_*_capture or Telemeter.capture calls in their operation, and
68
+ # nested Chef::Telemeter.timed_*_capture or Chef::Telemeter.capture calls in their operation, and
69
69
  # they will be captured in the same telemetry session.
70
- # NOTE: We're not currently sending arguments to telemetry because we have not implemented
71
- # pre-parsing of arguments to eliminate potentially sensitive data such as
72
- # passwords in host name, or in ad-hoc converge properties.
73
- Telemeter.timed_run_capture([:redacted]) do
70
+
71
+ Chef::Telemeter.timed_run_capture([:redacted]) do
74
72
  begin
75
- perform_run
73
+ perform_run(enforce_license: enforce_license)
76
74
  rescue Exception => e
77
75
  @rc = handle_run_error(e)
78
76
  end
79
77
  end
80
- rescue => e
78
+ rescue => e # can occur if exception thrown in error handling
81
79
  @rc = handle_run_error(e)
82
80
  ensure
83
- Telemeter.commit
81
+ Chef::Telemeter.commit
84
82
  exit @rc
85
83
  end
86
84
 
@@ -102,14 +100,14 @@ module ChefApply
102
100
  end
103
101
  end
104
102
 
105
- def perform_run
103
+ def perform_run(enforce_license: false)
106
104
  parse_options(@argv)
107
105
  if @argv.empty? || parsed_options[:help]
108
106
  show_help
109
107
  elsif parsed_options[:version]
110
108
  show_version
111
109
  else
112
- check_license_acceptance
110
+ check_license_acceptance if enforce_license
113
111
  validate_params(cli_arguments)
114
112
  target_hosts = resolve_targets(cli_arguments.shift, parsed_options)
115
113
  render_cookbook_setup(cli_arguments)
@@ -181,7 +179,7 @@ module ChefApply
181
179
  end
182
180
 
183
181
  def install(target_host, reporter)
184
- require "chef_apply/action/install_chef"
182
+ require_relative "action/install_chef"
185
183
  context = TS.install_chef
186
184
  reporter.update(context.verifying)
187
185
  installer = Action::InstallChef.new(target_host: target_host, check_only: !parsed_options[:install])
@@ -284,7 +282,7 @@ module ChefApply
284
282
  end
285
283
 
286
284
  def handle_perform_error(e)
287
- require "chef_apply/errors/standard_error_resolver"
285
+ require_relative "errors/standard_error_resolver"
288
286
  id = e.respond_to?(:id) ? e.id : e.class.to_s
289
287
  # TODO: This is currently sending host information for certain ssh errors
290
288
  # post release we need to scrub this data. For now I'm redacting the
@@ -61,7 +61,7 @@ module ChefApply
61
61
  end
62
62
 
63
63
  def show_version
64
- require "chef_apply/version"
64
+ require_relative "../version"
65
65
  UI::Terminal.output T.version.show(ChefApply::VERSION)
66
66
  end
67
67
  end
@@ -15,7 +15,7 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "chef_apply/text"
18
+ require_relative "../text"
19
19
 
20
20
  # Moving the options into here so the cli.rb file is smaller and easier to read
21
21
  # For options that need to be merged back into the global ChefApply::Config object
@@ -64,8 +64,8 @@ module ChefApply
64
64
  description: T.identity_file,
65
65
  proc: (Proc.new do |paths|
66
66
  path = paths
67
- unless File.exist?(path)
68
- raise OptionValidationError.new("CHEFVAL001", self, path)
67
+ unless File.readable?(path)
68
+ raise OptionValidationError.new("CHEFVAL001", nil, path)
69
69
  end
70
70
 
71
71
  path
@@ -15,7 +15,7 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "chef_apply/error"
18
+ require_relative "../error"
19
19
 
20
20
  module ChefApply
21
21
  class CLI
@@ -76,6 +76,8 @@ module ChefApply
76
76
  value.to_i
77
77
  when /^\d+\.\d*$/, /^\d*\.\d+$/
78
78
  value.to_f
79
+ when /^[:].+$/
80
+ value.split(":").last.to_sym
79
81
  when /true/i
80
82
  true
81
83
  when /false/i
@@ -15,10 +15,10 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "chef_apply/log"
19
- require "mixlib/config"
20
- require "fileutils"
21
- require "pathname"
18
+ require_relative "log"
19
+ require "mixlib/config" unless defined?(Mixlib::Config)
20
+ require "fileutils" unless defined?(FileUtils)
21
+ require "pathname" unless defined?(Pathname)
22
22
  require "chef-config/config"
23
23
  require "chef-config/workstation_config_loader"
24
24
 
@@ -109,8 +109,8 @@ module ChefApply
109
109
  # in their local configuration to ensure that dev usage
110
110
  # doesn't skew customer telemetry.
111
111
  config_context :telemetry do
112
- default(:dev, false)
113
- default(:enable, true)
112
+ default(:dev_mode, false)
113
+ default(:enabled, true)
114
114
  end
115
115
 
116
116
  config_context :log do
@@ -37,8 +37,8 @@ module ChefApply
37
37
 
38
38
  def self.deps
39
39
  # Avoid loading additional includes until they're needed
40
- require "socket"
41
- require "openssl"
40
+ require "socket" unless defined?(Socket)
41
+ require "openssl" unless defined?(OpenSSL)
42
42
  end
43
43
  end
44
44
  end
@@ -15,10 +15,10 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "net/http"
19
- require "uri"
20
- require "chef_apply/config"
21
- require "chef_apply/log"
18
+ require "net/http" unless defined?(Net::HTTP)
19
+ require "uri" unless defined?(URI)
20
+ require_relative "config"
21
+ require_relative "log"
22
22
 
23
23
  module ChefApply
24
24
  class FileFetcher
@@ -14,10 +14,10 @@
14
14
  # See the License for the specific language governing permissions and
15
15
  # limitations under the License.
16
16
 
17
- require "chef_apply/config"
18
- require "chef_apply/text"
19
- require "chef_apply/ui/terminal"
20
- require "chef_apply/telemeter/sender"
17
+ require_relative "config"
18
+ require_relative "text"
19
+ require_relative "ui/terminal"
20
+ require_relative "telemeter"
21
21
  require "chef/log"
22
22
  require "chef/config"
23
23
  module ChefApply
@@ -33,7 +33,7 @@ module ChefApply
33
33
  init_terminal
34
34
  end
35
35
 
36
- def run
36
+ def run(enforce_license: false)
37
37
  # This component is not supported in ChefDK; an exception will be raised
38
38
  # if running in that context.
39
39
  verify_not_in_chefdk
@@ -62,7 +62,7 @@ module ChefApply
62
62
  start_telemeter_upload
63
63
 
64
64
  # Launch the actual Chef Apply behavior
65
- start_chef_apply
65
+ start_chef_apply(enforce_license: enforce_license)
66
66
 
67
67
  # NOTE: Because these exceptions occur outside of the
68
68
  # CLI handling, they won't be tracked in telemtry.
@@ -119,7 +119,7 @@ module ChefApply
119
119
  end
120
120
 
121
121
  def setup_telemetry
122
- require "securerandom"
122
+ require "securerandom" unless defined?(SecureRandom)
123
123
  installation_id = SecureRandom.uuid
124
124
  File.write(Config.telemetry_installation_identifier_file, installation_id)
125
125
 
@@ -130,7 +130,14 @@ module ChefApply
130
130
  end
131
131
 
132
132
  def start_telemeter_upload
133
- ChefApply::Telemeter::Sender.start_upload_thread
133
+ cfg = {
134
+ enabled: Config.telemetry[:enabled],
135
+ dev_mode: Config.telemetry[:dev_mode],
136
+ payload_dir: Config.telemetry_path,
137
+ installation_identifier_file: Config.telemetry_installation_identifier_file,
138
+ session_file: Config.telemetry_session_file,
139
+ }
140
+ Chef::Telemeter.setup(cfg)
134
141
  end
135
142
 
136
143
  def setup_workstation_user_directories
@@ -187,24 +194,26 @@ module ChefApply
187
194
  Chef::Log.level = ChefApply::Log.level
188
195
  end
189
196
 
190
- def start_chef_apply
191
- require "chef_apply/cli"
192
- ChefApply::CLI.new(@argv).run
197
+ def start_chef_apply(enforce_license: false)
198
+ require_relative "cli"
199
+ ChefApply::CLI.new(@argv).run(enforce_license: enforce_license)
193
200
  end
194
201
 
195
202
  private
196
203
 
197
204
  def script_path
198
- File.expand_path File.dirname(__FILE__)
205
+ __dir__
199
206
  end
200
207
 
201
208
  class ConfigPathNotProvided < StandardError; end
209
+
202
210
  class ConfigPathInvalid < StandardError
203
211
  attr_reader :path
204
212
  def initialize(path)
205
213
  @path = path
206
214
  end
207
215
  end
216
+
208
217
  class UnsupportedInstallation < StandardError; end
209
218
  end
210
219
  end
@@ -15,8 +15,8 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "chef_apply/log"
19
- require "chef_apply/error"
18
+ require_relative "log"
19
+ require_relative "error"
20
20
  require "train"
21
21
 
22
22
  module ChefApply
@@ -134,10 +134,10 @@ module ChefApply
134
134
  def mix_in_target_platform!
135
135
  case base_os
136
136
  when :linux
137
- require "chef_apply/target_host/linux"
137
+ require_relative "target_host/linux"
138
138
  class << self; include ChefApply::TargetHost::Linux; end
139
139
  when :windows
140
- require "chef_apply/target_host/windows"
140
+ require_relative "target_host/windows"
141
141
  class << self; include ChefApply::TargetHost::Windows; end
142
142
  when :other
143
143
  raise ChefApply::TargetHost::UnsupportedTargetOS.new(platform.name)
@@ -280,7 +280,7 @@ module ChefApply
280
280
  end
281
281
 
282
282
  def ssh_config_for_host(host)
283
- require "net/ssh"
283
+ require "net/ssh" unless defined?(Net::SSH)
284
284
  Net::SSH::Config.for(host)
285
285
  end
286
286
 
@@ -323,7 +323,9 @@ module ChefApply
323
323
  super(*(Array(init_params).flatten))
324
324
  end
325
325
  end
326
+
326
327
  class ChefNotInstalled < StandardError; end
328
+
327
329
  class UnsupportedTargetOS < ChefApply::ErrorNoLogs
328
330
  def initialize(os_name); super("CHEFTARG001", os_name); end
329
331
  end
@@ -15,8 +15,8 @@
15
15
  # limitations under the License.
16
16
  #
17
17
 
18
- require "chef_apply/target_host"
19
- require "chef_apply/error"
18
+ require_relative "target_host"
19
+ require_relative "error"
20
20
 
21
21
  module ChefApply
22
22
  class TargetResolver
@@ -1,5 +1,6 @@
1
1
  #
2
- # Copyright:: Copyright (c) 2018 Chef Software Inc.
2
+ # Copyright:: Copyright (c) 2018-2019 Chef Software Inc.
3
+ # Author:: Marc A. Paradise <marc.paradise@gmail.com>
3
4
  # License:: Apache License, Version 2.0
4
5
  #
5
6
  # Licensed under the Apache License, Version 2.0 (the "License");
@@ -13,48 +14,14 @@
13
14
  # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
15
  # See the License for the specific language governing permissions and
15
16
  # limitations under the License.
16
- #
17
-
18
- require "benchmark"
19
- require "forwardable"
20
- require "singleton"
21
- require "json"
22
- require "digest/sha1"
23
- require "securerandom"
24
- require "chef_apply/version"
25
- require "chef_apply/config"
26
- require "yaml"
27
17
 
18
+ require "chef/telemeter"
19
+ # Monkey patch the telemetry lib to respect our config.toml
20
+ # entry for telemetry.
21
+ require_relative "telemeter/patch"
28
22
  module ChefApply
29
-
30
- # This definites the Telemeter interface. Implementation thoughts for
31
- # when we unstub it:
32
- # - let's track the call sequence; most of our calls will be nested inside
33
- # a main 'timed_capture', and it would be good to see ordering within nested calls.
34
23
  class Telemeter
35
- include Singleton
36
- DEFAULT_INSTALLATION_GUID = "00000000-0000-0000-0000-000000000000".freeze
37
-
38
- class << self
39
- extend Forwardable
40
- def_delegators :instance, :timed_capture, :capture, :commit, :timed_action_capture, :timed_run_capture
41
- def_delegators :instance, :pending_event_count, :last_event, :enabled?
42
- def_delegators :instance, :make_event_payload
43
- end
44
-
45
- attr_reader :events_to_send, :run_timestamp
46
-
47
- def enabled?
48
- require "telemetry/decision"
49
- ChefApply::Config.telemetry.enable && !Telemetry::Decision.env_opt_out?
50
- end
51
-
52
- def initialize
53
- @events_to_send = []
54
- @run_timestamp = Time.now.utc.strftime("%FT%TZ")
55
- end
56
-
57
- def timed_action_capture(action, &block)
24
+ def self.timed_action_capture(action, &block)
58
25
  # Note: we do not directly capture hostname for privacy concerns, but
59
26
  # using a sha1 digest will allow us to anonymously see
60
27
  # unique hosts to derive number of hosts affected by a command
@@ -67,96 +34,11 @@ module ChefApply
67
34
  target_data[:hostname_sha1] = Digest::SHA1.hexdigest(target.hostname.downcase)
68
35
  target_data[:transport_type] = target.transport_type
69
36
  end
70
- timed_capture(:action, { action: action.name, target: target_data }, &block)
71
- end
72
-
73
- def timed_run_capture(arguments, &block)
74
- timed_capture(:run, arguments: arguments, &block)
75
- end
76
-
77
- def capture(name, data = {})
78
- # Adding it to the head of the list will ensure that the
79
- # sequence of events is preserved when we send the final payload
80
- payload = make_event_payload(name, data)
81
- @events_to_send.unshift payload
37
+ Chef::Telemeter.timed_capture(:action, { action: action.name, target: target_data }, &block)
82
38
  end
83
39
 
84
- def timed_capture(name, data = {})
85
- time = Benchmark.measure { yield }
86
- data[:duration] = time.real
87
- capture(name, data)
40
+ def self.capture(name, data = {}, options = {})
41
+ Chef::Telemeter.capture(name, data, options)
88
42
  end
89
-
90
- def commit
91
- if enabled?
92
- session = convert_events_to_session
93
- write_session(session)
94
- end
95
- @events_to_send = []
96
- end
97
-
98
- def make_event_payload(name, data)
99
- {
100
- event: name,
101
- properties: {
102
- installation_id: installation_id,
103
- run_timestamp: run_timestamp,
104
- host_platform: host_platform,
105
- event_data: data,
106
- },
107
- }
108
- end
109
-
110
- def installation_id
111
- @installation_id ||=
112
- begin
113
- File.read(ChefApply::Config.telemetry_installation_identifier_file).chomp
114
- rescue
115
- ChefApply::Log.info "could not read #{ChefApply::Config.telemetry_installation_identifier_file} - using default id"
116
- DEFAULT_INSTALLATION_GUID
117
- end
118
- end
119
-
120
- # For testing.
121
- def pending_event_count
122
- @events_to_send.length
123
- end
124
-
125
- def last_event
126
- @events_to_send.last
127
- end
128
-
129
- private
130
-
131
- def host_platform
132
- @host_platform ||= case RUBY_PLATFORM
133
- when /mswin|mingw|windows/
134
- "windows"
135
- else
136
- RUBY_PLATFORM.split("-")[1]
137
- end
138
- end
139
-
140
- def convert_events_to_session
141
- YAML.dump({ "version" => ChefApply::VERSION,
142
- "entries" => @events_to_send })
143
- end
144
-
145
- def write_session(session)
146
- File.write(next_filename, convert_events_to_session)
147
- end
148
-
149
- def next_filename
150
- id = 0
151
- filename = ""
152
- loop do
153
- id += 1
154
- filename = File.join(ChefApply::Config.telemetry_path,
155
- "telemetry-payload-#{id}.yml")
156
- break unless File.exist?(filename)
157
- end
158
- filename
159
- end
160
-
161
43
  end
162
44
  end
@@ -24,7 +24,7 @@ class Telemetry
24
24
  end
25
25
 
26
26
  def deliver(data = {})
27
- if ChefApply::Telemeter.instance.enabled?
27
+ if Chef::Telemeter.instance.enabled?
28
28
  payload = event.prepare(data)
29
29
  client.await.fire(payload)
30
30
  end
@@ -16,8 +16,8 @@
16
16
  #
17
17
 
18
18
  require "r18n-desktop"
19
- require "chef_apply/text/text_wrapper"
20
- require "chef_apply/text/error_translation"
19
+ require_relative "text/text_wrapper"
20
+ require_relative "text/error_translation"
21
21
 
22
22
  # A very thin wrapper around R18n, the idea being that we're likely to replace r18n
23
23
  # down the road and don't want to have to change all of our commands.
@@ -16,12 +16,12 @@
16
16
  #
17
17
 
18
18
  require "train/errors"
19
- require "pastel"
20
- require "chef_apply/error"
21
- require "chef_apply/config"
22
- require "chef_apply/text"
23
- require "chef_apply/ui/terminal"
24
- require "chef_apply/errors/standard_error_resolver"
19
+ require "pastel" unless defined?(Pastel)
20
+ require_relative "../error"
21
+ require_relative "../config"
22
+ require_relative "../text"
23
+ require_relative "terminal"
24
+ require_relative "../errors/standard_error_resolver"
25
25
 
26
26
  module ChefApply::UI
27
27
  class ErrorPrinter
@@ -14,8 +14,7 @@
14
14
  # See the License for the specific language governing permissions and
15
15
  # limitations under the License.
16
16
  #
17
- require "thread"
18
- require "chef_apply/ui/plain_text_element"
17
+ require_relative "plain_text_element"
19
18
 
20
19
  module ChefApply
21
20
  module UI
@@ -17,11 +17,11 @@
17
17
 
18
18
  require "tty-spinner"
19
19
  require "tty-cursor"
20
- require "chef_apply/status_reporter"
21
- require "chef_apply/config"
22
- require "chef_apply/log"
23
- require "chef_apply/ui/plain_text_element"
24
- require "chef_apply/ui/plain_text_header"
20
+ require_relative "../status_reporter"
21
+ require_relative "../config"
22
+ require_relative "../log"
23
+ require_relative "plain_text_element"
24
+ require_relative "plain_text_header"
25
25
 
26
26
  module ChefApply
27
27
  module UI
@@ -16,5 +16,5 @@
16
16
  #
17
17
 
18
18
  module ChefApply
19
- VERSION = "0.4.12".freeze
19
+ VERSION = "0.5.16".freeze
20
20
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: chef-apply
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.12
4
+ version: 0.5.16
5
5
  platform: ruby
6
6
  authors:
7
7
  - Chef Software, Inc
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2019-11-22 00:00:00.000000000 Z
11
+ date: 2021-03-24 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: mixlib-cli
@@ -156,76 +156,62 @@ dependencies:
156
156
  requirements:
157
157
  - - ">="
158
158
  - !ruby/object:Gem::Version
159
- version: '15.0'
159
+ version: '16.0'
160
160
  type: :runtime
161
161
  prerelease: false
162
162
  version_requirements: !ruby/object:Gem::Requirement
163
163
  requirements:
164
164
  - - ">="
165
165
  - !ruby/object:Gem::Version
166
- version: '15.0'
166
+ version: '16.0'
167
167
  - !ruby/object:Gem::Dependency
168
168
  name: chef-cli
169
169
  requirement: !ruby/object:Gem::Requirement
170
170
  requirements:
171
171
  - - ">="
172
172
  - !ruby/object:Gem::Version
173
- version: 1.0.3
173
+ version: 2.0.10
174
174
  type: :runtime
175
175
  prerelease: false
176
176
  version_requirements: !ruby/object:Gem::Requirement
177
177
  requirements:
178
178
  - - ">="
179
179
  - !ruby/object:Gem::Version
180
- version: 1.0.3
180
+ version: 2.0.10
181
181
  - !ruby/object:Gem::Dependency
182
182
  name: chef-telemetry
183
183
  requirement: !ruby/object:Gem::Requirement
184
184
  requirements:
185
- - - "<="
185
+ - - ">="
186
186
  - !ruby/object:Gem::Version
187
- version: 0.1.10
187
+ version: 1.0.2
188
188
  type: :runtime
189
189
  prerelease: false
190
190
  version_requirements: !ruby/object:Gem::Requirement
191
191
  requirements:
192
- - - "<="
192
+ - - ">="
193
193
  - !ruby/object:Gem::Version
194
- version: 0.1.10
194
+ version: 1.0.2
195
195
  - !ruby/object:Gem::Dependency
196
196
  name: license-acceptance
197
197
  requirement: !ruby/object:Gem::Requirement
198
198
  requirements:
199
- - - "~>"
200
- - !ruby/object:Gem::Version
201
- version: '1.0'
202
199
  - - ">="
203
200
  - !ruby/object:Gem::Version
204
201
  version: 1.0.11
202
+ - - "<"
203
+ - !ruby/object:Gem::Version
204
+ version: '3'
205
205
  type: :runtime
206
206
  prerelease: false
207
207
  version_requirements: !ruby/object:Gem::Requirement
208
208
  requirements:
209
- - - "~>"
210
- - !ruby/object:Gem::Version
211
- version: '1.0'
212
209
  - - ">="
213
210
  - !ruby/object:Gem::Version
214
211
  version: 1.0.11
215
- - !ruby/object:Gem::Dependency
216
- name: bundler
217
- requirement: !ruby/object:Gem::Requirement
218
- requirements:
219
- - - ">="
212
+ - - "<"
220
213
  - !ruby/object:Gem::Version
221
- version: '0'
222
- type: :development
223
- prerelease: false
224
- version_requirements: !ruby/object:Gem::Requirement
225
- requirements:
226
- - - ">="
227
- - !ruby/object:Gem::Version
228
- version: '0'
214
+ version: '3'
229
215
  description: Ad-hoc management of individual nodes and devices.
230
216
  email:
231
217
  - workstation@chef.io
@@ -269,7 +255,6 @@ files:
269
255
  - lib/chef_apply/target_resolver.rb
270
256
  - lib/chef_apply/telemeter.rb
271
257
  - lib/chef_apply/telemeter/patch.rb
272
- - lib/chef_apply/telemeter/sender.rb
273
258
  - lib/chef_apply/text.rb
274
259
  - lib/chef_apply/text/error_translation.rb
275
260
  - lib/chef_apply/text/text_wrapper.rb
@@ -295,14 +280,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
295
280
  requirements:
296
281
  - - ">="
297
282
  - !ruby/object:Gem::Version
298
- version: 2.5.0
283
+ version: '2.6'
299
284
  required_rubygems_version: !ruby/object:Gem::Requirement
300
285
  requirements:
301
286
  - - ">="
302
287
  - !ruby/object:Gem::Version
303
288
  version: '0'
304
289
  requirements: []
305
- rubygems_version: 3.0.3
290
+ rubygems_version: 3.1.4
306
291
  signing_key:
307
292
  specification_version: 4
308
293
  summary: The ad-hoc execution tool for the Chef ecosystem.
@@ -1,121 +0,0 @@
1
- #
2
- # Copyright:: Copyright (c) 2018 Chef Software Inc.
3
- # License:: Apache License, Version 2.0
4
- #
5
- # Licensed under the Apache License, Version 2.0 (the "License");
6
- # you may not use this file except in compliance with the License.
7
- # You may obtain a copy of the License at
8
- #
9
- # http://www.apache.org/licenses/LICENSE-2.0
10
- #
11
- # Unless required by applicable law or agreed to in writing, software
12
- # distributed under the License is distributed on an "AS IS" BASIS,
13
- # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14
- # See the License for the specific language governing permissions and
15
- # limitations under the License.
16
- #
17
-
18
- require "telemetry"
19
- require "chef_apply/telemeter"
20
- require "chef_apply/telemeter/patch"
21
- require "chef_apply/log"
22
- require "chef_apply/version"
23
-
24
- module ChefApply
25
- class Telemeter
26
- class Sender
27
- attr_reader :session_files
28
-
29
- def self.start_upload_thread
30
- # Find the files before we spawn the thread - otherwise
31
- # we may accidentally pick up the current run's session file if it
32
- # finishes before the thread scans for new files
33
- session_files = Sender.find_session_files
34
- sender = Sender.new(session_files)
35
- Thread.new { sender.run }
36
- end
37
-
38
- def self.find_session_files
39
- ChefApply::Log.info("Looking for telemetry data to submit")
40
- session_search = File.join(ChefApply::Config.telemetry_path, "telemetry-payload-*.yml")
41
- session_files = Dir.glob(session_search)
42
- ChefApply::Log.info("Found #{session_files.length} sessions to submit")
43
- session_files
44
- end
45
-
46
- def initialize(session_files)
47
- @session_files = session_files
48
- end
49
-
50
- def run
51
- if ChefApply::Telemeter.enabled?
52
- ChefApply::Log.info("Telemetry enabled, beginning upload of previous session(s)")
53
- # dev mode telemetry gets sent to a different location
54
- if ChefApply::Config.telemetry.dev
55
- ENV["CHEF_TELEMETRY_ENDPOINT"] ||= "https://telemetry-acceptance.chef.io"
56
- end
57
- session_files.each { |path| process_session(path) }
58
- else
59
- # If telemetry is not enabled, just clean up and return. Even though
60
- # the telemetry gem will not send if disabled, log output saying that we're submitting
61
- # it when it has been disabled can be alarming.
62
- ChefApply::Log.info("Telemetry disabled, clearing any existing session captures without sending them.")
63
- session_files.each { |path| FileUtils.rm_rf(path) }
64
- end
65
- FileUtils.rm_rf(ChefApply::Config.telemetry_session_file)
66
- ChefApply::Log.info("Terminating, nothing more to do.")
67
- rescue => e
68
- ChefApply::Log.fatal "Sender thread aborted: '#{e}' failed at #{e.backtrace[0]}"
69
- end
70
-
71
- def process_session(path)
72
- ChefApply::Log.info("Processing telemetry entries from #{path}")
73
- content = load_and_clear_session(path)
74
- submit_session(content)
75
- end
76
-
77
- def submit_session(content)
78
- # Each file contains the actions taken within a single run of the chef tool.
79
- # Each run is one session, so we'll first remove remove the session file
80
- # to force creating a new one.
81
- FileUtils.rm_rf(ChefApply::Config.telemetry_session_file)
82
- # We'll use the version captured in the sesion file
83
- entries = content["entries"]
84
- cli_version = content["version"]
85
- total = entries.length
86
- telemetry = Telemetry.new(product: "chef-workstation",
87
- origin: "command-line",
88
- product_version: cli_version,
89
- install_context: "omnibus")
90
- total = entries.length
91
- entries.each_with_index do |entry, x|
92
- submit_entry(telemetry, entry, x + 1, total)
93
- end
94
- end
95
-
96
- def submit_entry(telemetry, entry, sequence, total)
97
- ChefApply::Log.info("Submitting telemetry entry #{sequence}/#{total}: #{entry} ")
98
- telemetry.deliver(entry)
99
- ChefApply::Log.info("Entry #{sequence}/#{total} submitted.")
100
- rescue => e
101
- # No error handling in telemetry lib, so at least track the failrue
102
- ChefApply::Log.error("Failed to send entry #{sequence}/#{total}: #{e}")
103
- ChefApply::Log.error("Backtrace: #{e.backtrace} ")
104
- end
105
-
106
- private
107
-
108
- def load_and_clear_session(path)
109
- content = File.read(path)
110
- # We'll remove it now instead of after we parse or submit it -
111
- # if we fail to deliver, we don't want to be stuck resubmitting it if the problem
112
- # was due to payload. This is a trade-off - if we get a transient error, the
113
- # payload will be lost.
114
- # TODO: Improve error handling so we can intelligently decide whether to
115
- # retry a failed load or failed submit.
116
- FileUtils.rm_rf(path)
117
- YAML.load(content)
118
- end
119
- end
120
- end
121
- end