bolt 2.31.0 → 2.35.0
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of bolt might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/Puppetfile +7 -7
- data/bolt-modules/boltlib/lib/puppet/functions/catch_errors.rb +1 -3
- data/bolt-modules/boltlib/lib/puppet/functions/download_file.rb +17 -6
- data/bolt-modules/boltlib/lib/puppet/functions/facts.rb +6 -0
- data/bolt-modules/boltlib/lib/puppet/functions/parallelize.rb +56 -0
- data/bolt-modules/boltlib/lib/puppet/functions/puppetdb_query.rb +2 -2
- data/bolt-modules/boltlib/lib/puppet/functions/run_command.rb +24 -6
- data/bolt-modules/boltlib/lib/puppet/functions/run_script.rb +27 -8
- data/bolt-modules/boltlib/lib/puppet/functions/run_task.rb +21 -1
- data/bolt-modules/boltlib/lib/puppet/functions/run_task_with.rb +18 -1
- data/bolt-modules/boltlib/lib/puppet/functions/upload_file.rb +24 -6
- data/bolt-modules/out/lib/puppet/functions/out/message.rb +44 -1
- data/bolt-modules/prompt/lib/puppet/functions/prompt.rb +3 -0
- data/guides/logging.txt +18 -0
- data/guides/module.txt +19 -0
- data/guides/modulepath.txt +25 -0
- data/lib/bolt/bolt_option_parser.rb +6 -1
- data/lib/bolt/cli.rb +70 -144
- data/lib/bolt/config/options.rb +35 -17
- data/lib/bolt/config/transport/options.rb +1 -1
- data/lib/bolt/error.rb +37 -3
- data/lib/bolt/executor.rb +111 -13
- data/lib/bolt/inventory/group.rb +2 -1
- data/lib/bolt/module_installer.rb +71 -115
- data/lib/bolt/{puppetfile → module_installer}/installer.rb +3 -2
- data/lib/bolt/module_installer/puppetfile.rb +117 -0
- data/lib/bolt/module_installer/puppetfile/forge_module.rb +54 -0
- data/lib/bolt/module_installer/puppetfile/git_module.rb +37 -0
- data/lib/bolt/module_installer/puppetfile/module.rb +26 -0
- data/lib/bolt/module_installer/resolver.rb +76 -0
- data/lib/bolt/module_installer/specs.rb +93 -0
- data/lib/bolt/module_installer/specs/forge_spec.rb +85 -0
- data/lib/bolt/module_installer/specs/git_spec.rb +179 -0
- data/lib/bolt/outputter.rb +0 -47
- data/lib/bolt/outputter/human.rb +23 -11
- data/lib/bolt/outputter/json.rb +1 -1
- data/lib/bolt/pal.rb +48 -30
- data/lib/bolt/pal/yaml_plan.rb +11 -2
- data/lib/bolt/pal/yaml_plan/evaluator.rb +23 -1
- data/lib/bolt/pal/yaml_plan/loader.rb +14 -9
- data/lib/bolt/plan_creator.rb +160 -0
- data/lib/bolt/plugin.rb +1 -1
- data/lib/bolt/project.rb +5 -10
- data/lib/bolt/project_migrator/config.rb +2 -1
- data/lib/bolt/project_migrator/inventory.rb +2 -2
- data/lib/bolt/project_migrator/modules.rb +10 -8
- data/lib/bolt/puppetdb/client.rb +3 -2
- data/lib/bolt/puppetdb/config.rb +8 -6
- data/lib/bolt/result.rb +23 -11
- data/lib/bolt/shell/bash.rb +11 -6
- data/lib/bolt/shell/powershell.rb +12 -7
- data/lib/bolt/task/run.rb +1 -1
- data/lib/bolt/transport/base.rb +18 -18
- data/lib/bolt/transport/docker.rb +23 -6
- data/lib/bolt/transport/orch.rb +23 -19
- data/lib/bolt/transport/orch/connection.rb +10 -3
- data/lib/bolt/transport/remote.rb +3 -3
- data/lib/bolt/transport/simple.rb +6 -6
- data/lib/bolt/util.rb +5 -0
- data/lib/bolt/version.rb +1 -1
- data/lib/bolt/yarn.rb +23 -0
- data/lib/bolt_server/file_cache.rb +2 -0
- data/lib/bolt_server/schemas/partials/task.json +17 -2
- data/lib/bolt_server/transport_app.rb +38 -7
- data/lib/bolt_spec/plans/action_stubs/command_stub.rb +1 -1
- data/lib/bolt_spec/plans/action_stubs/script_stub.rb +1 -1
- data/lib/bolt_spec/plans/mock_executor.rb +9 -6
- metadata +25 -8
- data/lib/bolt/puppetfile.rb +0 -149
- data/lib/bolt/puppetfile/module.rb +0 -93
- data/modules/secure_env_vars/plans/init.pp +0 -20
@@ -0,0 +1,179 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'json'
|
4
|
+
require 'set'
|
5
|
+
|
6
|
+
require 'bolt/error'
|
7
|
+
|
8
|
+
# This class represents a Git module specification.
|
9
|
+
#
|
10
|
+
module Bolt
|
11
|
+
class ModuleInstaller
|
12
|
+
class Specs
|
13
|
+
class GitSpec
|
14
|
+
NAME_REGEX = %r{\A(?:[a-zA-Z0-9]+[-/])?(?<name>[a-z][a-z0-9_]*)\z}.freeze
|
15
|
+
REQUIRED_KEYS = Set.new(%w[git ref]).freeze
|
16
|
+
|
17
|
+
attr_reader :git, :ref, :type
|
18
|
+
|
19
|
+
def initialize(init_hash)
|
20
|
+
@name = parse_name(init_hash['name'])
|
21
|
+
@git, @repo = parse_git(init_hash['git'])
|
22
|
+
@ref = init_hash['ref']
|
23
|
+
@type = :git
|
24
|
+
end
|
25
|
+
|
26
|
+
def self.implements?(hash)
|
27
|
+
REQUIRED_KEYS == hash.keys.to_set
|
28
|
+
end
|
29
|
+
|
30
|
+
# Parses the name into owner and name segments, and formats the full
|
31
|
+
# name.
|
32
|
+
#
|
33
|
+
private def parse_name(name)
|
34
|
+
return unless name
|
35
|
+
|
36
|
+
unless (match = name.match(NAME_REGEX))
|
37
|
+
raise Bolt::ValidationError,
|
38
|
+
"Invalid name for Git module specification: #{name}. Name must match "\
|
39
|
+
"'name' or 'owner/name'. Owner segment may only include letters or digits. "\
|
40
|
+
"Name segment must start with a lowercase letter and may only include "\
|
41
|
+
"lowercase letters, digits, and underscores."
|
42
|
+
end
|
43
|
+
|
44
|
+
match[:name]
|
45
|
+
end
|
46
|
+
|
47
|
+
# Gets the repo from the git URL.
|
48
|
+
#
|
49
|
+
private def parse_git(git)
|
50
|
+
repo = if git.start_with?('git@github.com:')
|
51
|
+
git.split('git@github.com:').last.split('.git').first
|
52
|
+
elsif git.start_with?('https://github.com')
|
53
|
+
git.split('https://github.com/').last.split('.git').first
|
54
|
+
else
|
55
|
+
raise Bolt::ValidationError,
|
56
|
+
"Invalid git source: #{git}. Only GitHub modules are supported."
|
57
|
+
end
|
58
|
+
|
59
|
+
[git, repo]
|
60
|
+
end
|
61
|
+
|
62
|
+
# Returns true if the specification is satisfied by the module.
|
63
|
+
#
|
64
|
+
def satisfied_by?(mod)
|
65
|
+
@type == mod.type && @git == mod.git
|
66
|
+
end
|
67
|
+
|
68
|
+
# Returns a hash matching the module spec in bolt-project.yaml
|
69
|
+
#
|
70
|
+
def to_hash
|
71
|
+
{
|
72
|
+
'git' => @git,
|
73
|
+
'ref' => @ref
|
74
|
+
}
|
75
|
+
end
|
76
|
+
|
77
|
+
# Returns a PuppetfileResolver::Model::GitModule object for resolving.
|
78
|
+
#
|
79
|
+
def to_resolver_module
|
80
|
+
require 'puppetfile-resolver'
|
81
|
+
|
82
|
+
PuppetfileResolver::Puppetfile::GitModule.new(name).tap do |mod|
|
83
|
+
mod.remote = @git
|
84
|
+
mod.ref = sha
|
85
|
+
end
|
86
|
+
end
|
87
|
+
|
88
|
+
# Resolves the module's title from the module metadata. This is lazily
|
89
|
+
# resolved since Bolt does not always need to know a Git module's name.
|
90
|
+
#
|
91
|
+
def name
|
92
|
+
@name ||= begin
|
93
|
+
url = "https://raw.githubusercontent.com/#{@repo}/#{sha}/metadata.json"
|
94
|
+
response = make_request(:Get, url)
|
95
|
+
|
96
|
+
case response
|
97
|
+
when Net::HTTPOK
|
98
|
+
body = JSON.parse(response.body)
|
99
|
+
|
100
|
+
unless body.key?('name')
|
101
|
+
raise Bolt::Error.new(
|
102
|
+
"Missing name in metadata.json at #{git}. This is not a valid module.",
|
103
|
+
"bolt/missing-module-name-error"
|
104
|
+
)
|
105
|
+
end
|
106
|
+
|
107
|
+
parse_name(body['name'])
|
108
|
+
else
|
109
|
+
raise Bolt::Error.new(
|
110
|
+
"Missing metadata.json at #{git}. This is not a valid module.",
|
111
|
+
"bolt/missing-module-metadata-error"
|
112
|
+
)
|
113
|
+
end
|
114
|
+
end
|
115
|
+
end
|
116
|
+
|
117
|
+
# Resolves the SHA for the specified ref. This is lazily resolved since
|
118
|
+
# Bolt does not always need to know a Git module's SHA.
|
119
|
+
#
|
120
|
+
def sha
|
121
|
+
@sha ||= begin
|
122
|
+
url = "https://api.github.com/repos/#{@repo}/commits/#{ref}"
|
123
|
+
headers = ENV['GITHUB_TOKEN'] ? { "Authorization" => "token #{ENV['GITHUB_TOKEN']}" } : {}
|
124
|
+
response = make_request(:Get, url, headers)
|
125
|
+
|
126
|
+
case response
|
127
|
+
when Net::HTTPOK
|
128
|
+
body = JSON.parse(response.body)
|
129
|
+
body['sha']
|
130
|
+
when Net::HTTPUnauthorized
|
131
|
+
raise Bolt::Error.new(
|
132
|
+
"Invalid token at GITHUB_TOKEN, unable to resolve git modules.",
|
133
|
+
"bolt/invalid-git-token-error"
|
134
|
+
)
|
135
|
+
when Net::HTTPForbidden
|
136
|
+
message = "GitHub API rate limit exceeded, unable to resolve git modules. "
|
137
|
+
|
138
|
+
unless ENV['GITHUB_TOKEN']
|
139
|
+
message += "To increase your rate limit, set the GITHUB_TOKEN environment "\
|
140
|
+
"variable with a GitHub personal access token."
|
141
|
+
end
|
142
|
+
|
143
|
+
raise Bolt::Error.new(message, 'bolt/github-api-rate-limit-error')
|
144
|
+
when Net::HTTPNotFound
|
145
|
+
raise Bolt::Error.new(
|
146
|
+
"#{git} is not a git repository.",
|
147
|
+
"bolt/missing-git-repository-error"
|
148
|
+
)
|
149
|
+
else
|
150
|
+
raise Bolt::Error.new(
|
151
|
+
"Ref #{ref} at #{git} is not a commit, tag, or branch.",
|
152
|
+
"bolt/invalid-git-ref-error"
|
153
|
+
)
|
154
|
+
end
|
155
|
+
end
|
156
|
+
end
|
157
|
+
|
158
|
+
# Makes a generic HTTP request.
|
159
|
+
#
|
160
|
+
private def make_request(verb, url, headers = {})
|
161
|
+
require 'net/http'
|
162
|
+
|
163
|
+
uri = URI.parse(url)
|
164
|
+
opts = { use_ssl: uri.scheme == 'https' }
|
165
|
+
|
166
|
+
Net::HTTP.start(uri.host, uri.port, opts) do |client|
|
167
|
+
request = Net::HTTP.const_get(verb).new(uri, headers)
|
168
|
+
client.request(request)
|
169
|
+
end
|
170
|
+
rescue StandardError => e
|
171
|
+
raise Bolt::Error.new(
|
172
|
+
"Failed to connect to #{uri}: #{e.message}",
|
173
|
+
"bolt/http-connect-error"
|
174
|
+
)
|
175
|
+
end
|
176
|
+
end
|
177
|
+
end
|
178
|
+
end
|
179
|
+
end
|
data/lib/bolt/outputter.rb
CHANGED
@@ -27,10 +27,6 @@ module Bolt
|
|
27
27
|
string.gsub(/^/, indent.to_s)
|
28
28
|
end
|
29
29
|
|
30
|
-
def print_message_event(event)
|
31
|
-
print_message(stringify(event[:message]))
|
32
|
-
end
|
33
|
-
|
34
30
|
def print_message
|
35
31
|
raise NotImplementedError, "print_message() must be implemented by the outputter class"
|
36
32
|
end
|
@@ -38,49 +34,6 @@ module Bolt
|
|
38
34
|
def print_error
|
39
35
|
raise NotImplementedError, "print_error() must be implemented by the outputter class"
|
40
36
|
end
|
41
|
-
|
42
|
-
def stringify(message)
|
43
|
-
formatted = format_message(message)
|
44
|
-
if formatted.is_a?(Hash) || formatted.is_a?(Array)
|
45
|
-
::JSON.pretty_generate(formatted)
|
46
|
-
else
|
47
|
-
formatted
|
48
|
-
end
|
49
|
-
end
|
50
|
-
|
51
|
-
def format_message(message)
|
52
|
-
case message
|
53
|
-
when Array
|
54
|
-
message.map { |item| format_message(item) }
|
55
|
-
when Bolt::ApplyResult
|
56
|
-
format_apply_result(message)
|
57
|
-
when Bolt::Result, Bolt::ResultSet
|
58
|
-
# This is equivalent to to_s, but formattable
|
59
|
-
message.to_data
|
60
|
-
when Bolt::RunFailure
|
61
|
-
formatted_resultset = message.result_set.to_data
|
62
|
-
message.to_h.merge('result_set' => formatted_resultset)
|
63
|
-
when Hash
|
64
|
-
message.each_with_object({}) do |(k, v), h|
|
65
|
-
h[format_message(k)] = format_message(v)
|
66
|
-
end
|
67
|
-
when Integer, Float, NilClass
|
68
|
-
message
|
69
|
-
else
|
70
|
-
message.to_s
|
71
|
-
end
|
72
|
-
end
|
73
|
-
|
74
|
-
def format_apply_result(result)
|
75
|
-
logs = result.resource_logs&.map do |log|
|
76
|
-
# Omit low-level info/debug messages
|
77
|
-
next if %w[info debug].include?(log['level'])
|
78
|
-
indent(2, format_log(log))
|
79
|
-
end
|
80
|
-
hash = result.to_data
|
81
|
-
hash['logs'] = logs unless logs.empty?
|
82
|
-
hash
|
83
|
-
end
|
84
37
|
end
|
85
38
|
end
|
86
39
|
|
data/lib/bolt/outputter/human.rb
CHANGED
@@ -45,7 +45,7 @@ module Bolt
|
|
45
45
|
when :disable_default_output
|
46
46
|
@disable_depth += 1
|
47
47
|
when :message
|
48
|
-
|
48
|
+
print_message(event[:message])
|
49
49
|
end
|
50
50
|
|
51
51
|
if enabled?
|
@@ -214,9 +214,10 @@ module Bolt
|
|
214
214
|
end
|
215
215
|
|
216
216
|
def print_tasks(tasks, modulepath)
|
217
|
-
|
217
|
+
command = Bolt::Util.powershell? ? 'Get-BoltTask -Task <TASK NAME>' : 'bolt task show <TASK NAME>'
|
218
|
+
tasks.any? ? print_table(tasks) : print_message('No available tasks')
|
218
219
|
print_message("\nMODULEPATH:\n#{modulepath.join(File::PATH_SEPARATOR)}\n"\
|
219
|
-
"\nUse
|
220
|
+
"\nUse '#{command}' to view "\
|
220
221
|
"details and parameters for a specific task.")
|
221
222
|
end
|
222
223
|
|
@@ -225,20 +226,26 @@ module Bolt
|
|
225
226
|
# Building lots of strings...
|
226
227
|
pretty_params = +""
|
227
228
|
task_info = +""
|
228
|
-
usage =
|
229
|
+
usage = if Bolt::Util.powershell?
|
230
|
+
+"Invoke-BoltTask -Name #{task.name} -Targets <targets>"
|
231
|
+
else
|
232
|
+
+"bolt task run #{task.name} --targets <targets>"
|
233
|
+
end
|
229
234
|
|
230
235
|
task.parameters&.each do |k, v|
|
231
236
|
pretty_params << "- #{k}: #{v['type'] || 'Any'}\n"
|
232
237
|
pretty_params << " Default: #{v['default'].inspect}\n" if v.key?('default')
|
233
238
|
pretty_params << " #{v['description']}\n" if v['description']
|
234
|
-
usage << if v['type'].
|
239
|
+
usage << if v['type'].start_with?("Optional")
|
235
240
|
" [#{k}=<value>]"
|
236
241
|
else
|
237
242
|
" #{k}=<value>"
|
238
243
|
end
|
239
244
|
end
|
240
245
|
|
241
|
-
|
246
|
+
if task.supports_noop
|
247
|
+
usage << Bolt::Util.powershell? ? '[-Noop]' : '[--noop]'
|
248
|
+
end
|
242
249
|
|
243
250
|
task_info << "\n#{task.name}"
|
244
251
|
task_info << " - #{task.description}" if task.description
|
@@ -261,7 +268,11 @@ module Bolt
|
|
261
268
|
# Building lots of strings...
|
262
269
|
pretty_params = +""
|
263
270
|
plan_info = +""
|
264
|
-
usage =
|
271
|
+
usage = if Bolt::Util.powershell?
|
272
|
+
+"Invoke-BoltPlan -Name #{plan['name']}"
|
273
|
+
else
|
274
|
+
+"bolt plan run #{plan['name']}"
|
275
|
+
end
|
265
276
|
|
266
277
|
plan['parameters'].each do |name, p|
|
267
278
|
pretty_params << "- #{name}: #{p['type']}\n"
|
@@ -287,16 +298,17 @@ module Bolt
|
|
287
298
|
end
|
288
299
|
|
289
300
|
def print_plans(plans, modulepath)
|
290
|
-
|
301
|
+
command = Bolt::Util.powershell? ? 'Get-BoltPlan -Name <PLAN NAME>' : 'bolt plan show <PLAN NAME>'
|
302
|
+
plans.any? ? print_table(plans) : print_message('No available plans')
|
291
303
|
print_message("\nMODULEPATH:\n#{modulepath.join(File::PATH_SEPARATOR)}\n"\
|
292
|
-
"\nUse
|
304
|
+
"\nUse '#{command}' to view "\
|
293
305
|
"details and parameters for a specific plan.")
|
294
306
|
end
|
295
307
|
|
296
308
|
def print_topics(topics)
|
297
309
|
print_message("Available topics are:")
|
298
310
|
print_message(topics.join("\n"))
|
299
|
-
print_message("\nUse
|
311
|
+
print_message("\nUse 'bolt guide <TOPIC>' to view a specific guide.")
|
300
312
|
end
|
301
313
|
|
302
314
|
def print_guide(guide, _topic)
|
@@ -344,7 +356,7 @@ module Bolt
|
|
344
356
|
end
|
345
357
|
|
346
358
|
@stream.puts "INVENTORY FILE:"
|
347
|
-
if
|
359
|
+
if File.exist?(inventoryfile)
|
348
360
|
@stream.puts inventoryfile
|
349
361
|
else
|
350
362
|
@stream.puts wrap("Tried to load inventory from #{inventoryfile}, but the file does not exist")
|
data/lib/bolt/outputter/json.rb
CHANGED
data/lib/bolt/pal.rb
CHANGED
@@ -14,17 +14,11 @@ module Bolt
|
|
14
14
|
# Bolt::Errors
|
15
15
|
class PALError < Bolt::Error
|
16
16
|
def self.from_preformatted_error(err)
|
17
|
-
if err.cause.is_a? Bolt::Error
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
end
|
23
|
-
|
24
|
-
# Generate a Bolt::Pal::PALError for non-bolt errors
|
25
|
-
def self.from_error(err)
|
26
|
-
# Use the original error message if available
|
27
|
-
message = err.cause ? err.cause.message : err.message
|
17
|
+
error = if err.cause.is_a? Bolt::Error
|
18
|
+
err.cause
|
19
|
+
else
|
20
|
+
from_error(err)
|
21
|
+
end
|
28
22
|
|
29
23
|
# Provide the location of an error if it came from a plan
|
30
24
|
details = {}
|
@@ -32,8 +26,15 @@ module Bolt
|
|
32
26
|
details[:line] = err.line if defined?(err.line)
|
33
27
|
details[:column] = err.pos if defined?(err.pos)
|
34
28
|
|
35
|
-
|
29
|
+
error.add_filelineno(details.compact)
|
30
|
+
error
|
31
|
+
end
|
36
32
|
|
33
|
+
# Generate a Bolt::Pal::PALError for non-bolt errors
|
34
|
+
def self.from_error(err)
|
35
|
+
# Use the original error message if available
|
36
|
+
message = err.cause ? err.cause.message : err.message
|
37
|
+
e = new(message)
|
37
38
|
e.set_backtrace(err.backtrace)
|
38
39
|
e
|
39
40
|
end
|
@@ -256,19 +257,24 @@ module Bolt
|
|
256
257
|
|
257
258
|
# TODO: PUP-8553 should replace this
|
258
259
|
def with_puppet_settings
|
259
|
-
Dir.mktmpdir('bolt')
|
260
|
-
|
261
|
-
|
262
|
-
|
263
|
-
|
264
|
-
Puppet.settings.send(:clear_everything_for_tests)
|
265
|
-
Puppet.initialize_settings(cli)
|
266
|
-
Puppet::GettextConfig.create_default_text_domain
|
267
|
-
Puppet[:trusted_external_command] = @trusted_external
|
268
|
-
Puppet.settings[:hiera_config] = @hiera_config
|
269
|
-
self.class.configure_logging
|
270
|
-
yield
|
260
|
+
dir = Dir.mktmpdir('bolt')
|
261
|
+
|
262
|
+
cli = []
|
263
|
+
Puppet::Settings::REQUIRED_APP_SETTINGS.each do |setting|
|
264
|
+
cli << "--#{setting}" << dir
|
271
265
|
end
|
266
|
+
Puppet.settings.send(:clear_everything_for_tests)
|
267
|
+
Puppet.initialize_settings(cli)
|
268
|
+
Puppet::GettextConfig.create_default_text_domain
|
269
|
+
Puppet[:trusted_external_command] = @trusted_external
|
270
|
+
Puppet.settings[:hiera_config] = @hiera_config
|
271
|
+
self.class.configure_logging
|
272
|
+
yield
|
273
|
+
ensure
|
274
|
+
# Delete the tmpdir if it still exists. This check is needed to
|
275
|
+
# prevent Bolt from erroring if the tmpdir is somehow deleted
|
276
|
+
# before reaching this point.
|
277
|
+
FileUtils.remove_entry_secure(dir) if File.exist?(dir)
|
272
278
|
end
|
273
279
|
|
274
280
|
# Parses a snippet of Puppet manifest code and returns the AST represented
|
@@ -280,15 +286,26 @@ module Bolt
|
|
280
286
|
raise Bolt::PAL::PALError, "Failed to parse manifest: #{e}"
|
281
287
|
end
|
282
288
|
|
283
|
-
|
289
|
+
# Filters content by a list of names and glob patterns specified in project
|
290
|
+
# configuration.
|
291
|
+
def filter_content(content, patterns)
|
292
|
+
return content unless content && patterns
|
293
|
+
|
294
|
+
content.select do |name,|
|
295
|
+
patterns.any? { |pattern| File.fnmatch?(pattern, name, File::FNM_EXTGLOB) }
|
296
|
+
end
|
297
|
+
end
|
298
|
+
|
299
|
+
def list_tasks(filter_content: false)
|
284
300
|
in_bolt_compiler do |compiler|
|
285
|
-
tasks = compiler.list_tasks
|
286
|
-
tasks.map(&:name).sort.each_with_object([]) do |task_name, data|
|
301
|
+
tasks = compiler.list_tasks.map(&:name).sort.each_with_object([]) do |task_name, data|
|
287
302
|
task_sig = compiler.task_signature(task_name)
|
288
303
|
unless task_sig.task_hash['metadata']['private']
|
289
304
|
data << [task_name, task_sig.task_hash['metadata']['description']]
|
290
305
|
end
|
291
306
|
end
|
307
|
+
|
308
|
+
filter_content ? filter_content(tasks, @project&.tasks) : tasks
|
292
309
|
end
|
293
310
|
end
|
294
311
|
|
@@ -340,14 +357,15 @@ module Bolt
|
|
340
357
|
Bolt::Task.from_task_signature(task)
|
341
358
|
end
|
342
359
|
|
343
|
-
def list_plans
|
360
|
+
def list_plans(filter_content: false)
|
344
361
|
in_bolt_compiler do |compiler|
|
345
362
|
errors = []
|
346
363
|
plans = compiler.list_plans(nil, errors).map { |plan| [plan.name] }.sort
|
347
364
|
errors.each do |error|
|
348
365
|
@logger.warn(error.details['original_error'])
|
349
366
|
end
|
350
|
-
|
367
|
+
|
368
|
+
filter_content ? filter_content(plans, @project&.plans) : plans
|
351
369
|
end
|
352
370
|
end
|
353
371
|
|
@@ -384,7 +402,7 @@ module Bolt
|
|
384
402
|
plan.docstring
|
385
403
|
end
|
386
404
|
|
387
|
-
defaults = plan.parameters.
|
405
|
+
defaults = plan.parameters.to_h.compact
|
388
406
|
signature_params = Set.new(plan.parameters.map(&:first))
|
389
407
|
parameters = plan.tags(:param).each_with_object({}) do |param, params|
|
390
408
|
name = param.name
|