toys-core 0.9.4 → 0.10.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.yardopts +2 -1
- data/CHANGELOG.md +30 -0
- data/LICENSE.md +1 -1
- data/README.md +3 -3
- data/lib/toys-core.rb +11 -21
- data/lib/toys/acceptor.rb +0 -21
- data/lib/toys/arg_parser.rb +1 -22
- data/lib/toys/cli.rb +102 -70
- data/lib/toys/compat.rb +49 -41
- data/lib/toys/completion.rb +0 -21
- data/lib/toys/context.rb +0 -23
- data/lib/toys/core.rb +1 -22
- data/lib/toys/dsl/flag.rb +0 -21
- data/lib/toys/dsl/flag_group.rb +0 -21
- data/lib/toys/dsl/positional_arg.rb +0 -21
- data/lib/toys/dsl/tool.rb +135 -51
- data/lib/toys/errors.rb +0 -21
- data/lib/toys/flag.rb +0 -21
- data/lib/toys/flag_group.rb +0 -21
- data/lib/toys/input_file.rb +0 -21
- data/lib/toys/loader.rb +41 -78
- data/lib/toys/middleware.rb +146 -77
- data/lib/toys/mixin.rb +0 -21
- data/lib/toys/module_lookup.rb +3 -26
- data/lib/toys/positional_arg.rb +0 -21
- data/lib/toys/source_info.rb +49 -38
- data/lib/toys/standard_middleware/add_verbosity_flags.rb +0 -23
- data/lib/toys/standard_middleware/apply_config.rb +42 -0
- data/lib/toys/standard_middleware/handle_usage_errors.rb +7 -28
- data/lib/toys/standard_middleware/set_default_descriptions.rb +0 -23
- data/lib/toys/standard_middleware/show_help.rb +0 -23
- data/lib/toys/standard_middleware/show_root_version.rb +0 -23
- data/lib/toys/standard_mixins/bundler.rb +89 -0
- data/lib/toys/standard_mixins/exec.rb +124 -35
- data/lib/toys/standard_mixins/fileutils.rb +0 -21
- data/lib/toys/standard_mixins/gems.rb +2 -24
- data/lib/toys/standard_mixins/highline.rb +0 -21
- data/lib/toys/standard_mixins/terminal.rb +0 -21
- data/lib/toys/template.rb +0 -21
- data/lib/toys/tool.rb +22 -34
- data/lib/toys/utils/completion_engine.rb +0 -21
- data/lib/toys/utils/exec.rb +1 -21
- data/lib/toys/utils/gems.rb +174 -63
- data/lib/toys/utils/help_text.rb +0 -21
- data/lib/toys/utils/terminal.rb +46 -37
- data/lib/toys/wrappable_string.rb +0 -21
- metadata +25 -9
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 3a9f077375706e67827afa561f71081c121d0eb00c30be6586501e6c76ab47c5
|
4
|
+
data.tar.gz: 305e31b023d22f687a2406efdd0cea377a1c9725626c8320cebbf013b10f145b
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 661b472175296ea3224e3dee08902ca8b2bf04e78f949109a91f4fa471c0b7904a454e0b18e845cf46d8cf04458872c84f55fd3f43bcbb2f3ecd40478783b8a5
|
7
|
+
data.tar.gz: f9761ab43fffd295af8629906ae3fdee621c42d5df49a92b3539cc68a9588546338a4fdd3a70459639c3127c261de443c5f2359778807d281b451b4c2655316a
|
data/.yardopts
CHANGED
data/CHANGELOG.md
CHANGED
@@ -1,5 +1,35 @@
|
|
1
1
|
# Release History
|
2
2
|
|
3
|
+
### 0.10.0 / 2020-02-24
|
4
|
+
|
5
|
+
Functional changes:
|
6
|
+
|
7
|
+
* ADDED: `:bundler` mixin that installs and sets up a bundle for the tool
|
8
|
+
* ADDED: `bundle` method to `Toys::Utils::Gems` that performs bundler install and setup
|
9
|
+
* ADDED: `subtool_apply` directive which applies a block to all subtools.
|
10
|
+
* ADDED: Add `.lib` directories to the Ruby load path when executing a tool.
|
11
|
+
* ADDED: `toys_version?` and `toys_version!` directives that check against version requirements.
|
12
|
+
* ADDED: `exec_separate_tool` and `capture_separate_tool` methods in the `:exec` mixin, to support executing tools in a separate process without forking
|
13
|
+
* IMPROVED: `long_desc` directive can now read the description from a text file.
|
14
|
+
* IMPROVED: The `tool` directive can take delimited strings as tool names.
|
15
|
+
* IMPROVED: Subtool blocks aren't actually executed unless the tool is needed.
|
16
|
+
* CHANGED: Added `on_missing` and `on_conflict` arguments to `Toys::Utils::Gems` constructor (which also affects the `:gems` mixin), and deprecated `suppress_confirm` and `default_confirm`.
|
17
|
+
|
18
|
+
Internal interface changes:
|
19
|
+
|
20
|
+
* ADDED: `Toys::Tool#subtool_middleware_stack` allowing a tool to modify the middleware stack for its subtools.
|
21
|
+
* ADDED: The `Toys::Middleware::Stack` class represents a stack of middleware specs, and distinguishes the default set from those added afterward.
|
22
|
+
* ADDED: `Toys.executable_path` attribute allowing an executable to provide the executable for running tools separately.
|
23
|
+
* ADDED: `Toys::CLI` now has a `logger_factory` property, to generate separate loggers per tool execution.
|
24
|
+
* ADDED: `Toys::CLI` and `Toys::Loader` now let you set `:lib_dir_name`.
|
25
|
+
* IMPROVED: Toys-core no longer has a general dependency on rubygems. (Parts that do depend on rubygems, such as the `:gems` mixin, do an explicit `require "rubygems"`.) This makes it possible to write an executable with `ruby --disable=gems` which improves startup time.
|
26
|
+
* IMPROVED: Middleware objects no longer have to respond to all middleware methods. If a method is not implemented, it is simply considered a nop.
|
27
|
+
* IMPROVED: `Toys::Utils::Terminal` is now thread-safe.
|
28
|
+
* CHANGED: `Toys::Utils::Terminal#styled` is no longer mutable.
|
29
|
+
* CHANGED: `Toys::Tool#middleware_stack` renamed to `Toys::Tool#built_middleware` to clarify that it is an array of middleware objects rather than specs.
|
30
|
+
* CHANGED: `Toys::CLI.default_logger` removed and replaced with `Toys::CLI.default_logger_factory`. In general, global loggers for CLI are now discouraged because they are not thread-safe.
|
31
|
+
* CHANGED: `Toys::Loader` uses an internal monitor rather than including `MonitorMixin`.
|
32
|
+
|
3
33
|
### 0.9.4 / 2020-01-26
|
4
34
|
|
5
35
|
* FIXED: Crash in the loader when a non-ruby file appears in a toys directory
|
data/LICENSE.md
CHANGED
data/README.md
CHANGED
@@ -74,7 +74,7 @@ use to write Toys files. You could point your executable at a directory
|
|
74
74
|
containing actual Toys files, but the simplest option is to provide the
|
75
75
|
information to the Toys CLI object in a block.
|
76
76
|
|
77
|
-
Let's add some functionality.
|
77
|
+
Let's add some functionality.
|
78
78
|
|
79
79
|
#!/usr/bin/env ruby
|
80
80
|
|
@@ -150,7 +150,7 @@ available tools.
|
|
150
150
|
$ ./mycmd
|
151
151
|
|
152
152
|
Notice that the description set at the "root" of the config block (outside the
|
153
|
-
tool blocks) shows up here.
|
153
|
+
tool blocks) shows up here.
|
154
154
|
|
155
155
|
### Configuring the CLI
|
156
156
|
|
@@ -338,7 +338,7 @@ templates, and middleware, in the
|
|
338
338
|
|
339
339
|
## License
|
340
340
|
|
341
|
-
Copyright 2019 Daniel Azuma
|
341
|
+
Copyright 2019-2020 Daniel Azuma and the Toys contributors
|
342
342
|
|
343
343
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
344
344
|
of this software and associated documentation files (the "Software"), to deal
|
data/lib/toys-core.rb
CHANGED
@@ -1,26 +1,5 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
-
# Copyright 2019 Daniel Azuma
|
4
|
-
#
|
5
|
-
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
-
# of this software and associated documentation files (the "Software"), to deal
|
7
|
-
# in the Software without restriction, including without limitation the rights
|
8
|
-
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
-
# copies of the Software, and to permit persons to whom the Software is
|
10
|
-
# furnished to do so, subject to the following conditions:
|
11
|
-
#
|
12
|
-
# The above copyright notice and this permission notice shall be included in
|
13
|
-
# all copies or substantial portions of the Software.
|
14
|
-
#
|
15
|
-
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
-
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
-
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
-
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
-
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
20
|
-
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
21
|
-
# IN THE SOFTWARE.
|
22
|
-
;
|
23
|
-
|
24
3
|
##
|
25
4
|
# Toys is a configurable command line tool. Write commands in config files
|
26
5
|
# using a simple DSL, and Toys will provide the command line executable and
|
@@ -68,6 +47,17 @@ module Toys
|
|
68
47
|
# `require "toys/utils/exec"`.
|
69
48
|
#
|
70
49
|
module Utils; end
|
50
|
+
|
51
|
+
class << self
|
52
|
+
##
|
53
|
+
# Path to the executable. This can, for example, be invoked to run a subtool
|
54
|
+
# in a clean environment.
|
55
|
+
#
|
56
|
+
# @return [String] if there is an executable
|
57
|
+
# @return [nil] if there is no such executable
|
58
|
+
#
|
59
|
+
attr_accessor :executable_path
|
60
|
+
end
|
71
61
|
end
|
72
62
|
|
73
63
|
require "toys/acceptor"
|
data/lib/toys/acceptor.rb
CHANGED
@@ -1,26 +1,5 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
-
# Copyright 2019 Daniel Azuma
|
4
|
-
#
|
5
|
-
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
-
# of this software and associated documentation files (the "Software"), to deal
|
7
|
-
# in the Software without restriction, including without limitation the rights
|
8
|
-
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
-
# copies of the Software, and to permit persons to whom the Software is
|
10
|
-
# furnished to do so, subject to the following conditions:
|
11
|
-
#
|
12
|
-
# The above copyright notice and this permission notice shall be included in
|
13
|
-
# all copies or substantial portions of the Software.
|
14
|
-
#
|
15
|
-
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
-
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
-
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
-
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
-
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
20
|
-
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
21
|
-
# IN THE SOFTWARE.
|
22
|
-
;
|
23
|
-
|
24
3
|
module Toys
|
25
4
|
##
|
26
5
|
# An Acceptor validates and converts arguments. It is designed to be
|
data/lib/toys/arg_parser.rb
CHANGED
@@ -1,26 +1,5 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
-
# Copyright 2019 Daniel Azuma
|
4
|
-
#
|
5
|
-
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
-
# of this software and associated documentation files (the "Software"), to deal
|
7
|
-
# in the Software without restriction, including without limitation the rights
|
8
|
-
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
-
# copies of the Software, and to permit persons to whom the Software is
|
10
|
-
# furnished to do so, subject to the following conditions:
|
11
|
-
#
|
12
|
-
# The above copyright notice and this permission notice shall be included in
|
13
|
-
# all copies or substantial portions of the Software.
|
14
|
-
#
|
15
|
-
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
-
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
-
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
-
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
-
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
20
|
-
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
21
|
-
# IN THE SOFTWARE.
|
22
|
-
;
|
23
|
-
|
24
3
|
module Toys
|
25
4
|
##
|
26
5
|
# An internal class that parses command line arguments for a tool.
|
@@ -444,7 +423,7 @@ module Toys
|
|
444
423
|
Context::Key::ARGS => nil,
|
445
424
|
Context::Key::CLI => cli,
|
446
425
|
Context::Key::CONTEXT_DIRECTORY => tool.context_directory,
|
447
|
-
Context::Key::LOGGER => cli.
|
426
|
+
Context::Key::LOGGER => cli.logger_factory.call(tool),
|
448
427
|
Context::Key::TOOL => tool,
|
449
428
|
Context::Key::TOOL_SOURCE => tool.source_info,
|
450
429
|
Context::Key::TOOL_NAME => tool.full_name,
|
data/lib/toys/cli.rb
CHANGED
@@ -1,26 +1,6 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
-
|
4
|
-
#
|
5
|
-
# Permission is hereby granted, free of charge, to any person obtaining a copy
|
6
|
-
# of this software and associated documentation files (the "Software"), to deal
|
7
|
-
# in the Software without restriction, including without limitation the rights
|
8
|
-
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
9
|
-
# copies of the Software, and to permit persons to whom the Software is
|
10
|
-
# furnished to do so, subject to the following conditions:
|
11
|
-
#
|
12
|
-
# The above copyright notice and this permission notice shall be included in
|
13
|
-
# all copies or substantial portions of the Software.
|
14
|
-
#
|
15
|
-
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
16
|
-
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
17
|
-
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
18
|
-
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
19
|
-
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
|
20
|
-
# FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
|
21
|
-
# IN THE SOFTWARE.
|
22
|
-
;
|
23
|
-
|
3
|
+
require "rbconfig"
|
24
4
|
require "logger"
|
25
5
|
require "toys/completion"
|
26
6
|
|
@@ -71,7 +51,8 @@ module Toys
|
|
71
51
|
# roughly into four categories:
|
72
52
|
#
|
73
53
|
# * Options affecting output behavior:
|
74
|
-
# * `logger`:
|
54
|
+
# * `logger`: A global logger for all tools to use
|
55
|
+
# * `logger_factory`: A proc that returns a logger to use
|
75
56
|
# * `base_level`: The default log level
|
76
57
|
# * `error_handler`: Callback for handling exceptions
|
77
58
|
# * `executable_name`: The name of the executable
|
@@ -91,10 +72,17 @@ module Toys
|
|
91
72
|
# * `preload_dir_name`: Name of preload directories in tool directories
|
92
73
|
# * `data_dir_name`: Name of data directories in tool directories
|
93
74
|
#
|
94
|
-
# @param logger [Logger]
|
95
|
-
#
|
96
|
-
#
|
97
|
-
#
|
75
|
+
# @param logger [Logger] A global logger to use for all tools. This may be
|
76
|
+
# set if the CLI will call at most one tool at a time. However, it will
|
77
|
+
# behave incorrectly if CLI might run multiple tools at the same time
|
78
|
+
# with different verbosity settings (since the logger cannot have
|
79
|
+
# multiple level settings simultaneously). In that case, do not set a
|
80
|
+
# global logger, but use the `logger_factory` parameter instead.
|
81
|
+
# @param logger_factory [Proc] A proc that takes a {Toys::Tool} as an
|
82
|
+
# argument, and returns a `Logger` to use when running that tool.
|
83
|
+
# Optional. If not provided (and no global logger is set), CLI will use
|
84
|
+
# a default factory that writes generates loggers writing formatted
|
85
|
+
# output to `STDERR`, as defined by {Toys::CLI.default_logger_factory}.
|
98
86
|
# @param base_level [Integer] The logger level that should correspond
|
99
87
|
# to zero verbosity.
|
100
88
|
# Optional. If not provided, defaults to the current level of the
|
@@ -181,13 +169,31 @@ module Toys
|
|
181
169
|
# path for any tool file in that directory.
|
182
170
|
# Optional. If not provided, data directories are disabled.
|
183
171
|
# Note: the standard toys executable sets this to `".data"`.
|
184
|
-
#
|
185
|
-
|
186
|
-
|
187
|
-
|
188
|
-
|
189
|
-
|
190
|
-
|
172
|
+
# @param lib_dir_name [String] A directory with this name that appears in
|
173
|
+
# any configuration directory is added to the Ruby load path when
|
174
|
+
# executing any tool file in that directory.
|
175
|
+
# Optional. If not provided, lib directories are disabled.
|
176
|
+
# Note: the standard toys executable sets this to `".lib"`.
|
177
|
+
#
|
178
|
+
def initialize( # rubocop:disable Metrics/MethodLength
|
179
|
+
executable_name: nil,
|
180
|
+
middleware_stack: nil,
|
181
|
+
extra_delimiters: "",
|
182
|
+
config_dir_name: nil,
|
183
|
+
config_file_name: nil,
|
184
|
+
index_file_name: nil,
|
185
|
+
preload_file_name: nil,
|
186
|
+
preload_dir_name: nil,
|
187
|
+
data_dir_name: nil,
|
188
|
+
lib_dir_name: nil,
|
189
|
+
mixin_lookup: nil,
|
190
|
+
middleware_lookup: nil,
|
191
|
+
template_lookup: nil,
|
192
|
+
logger_factory: nil,
|
193
|
+
logger: nil,
|
194
|
+
base_level: nil,
|
195
|
+
error_handler: nil,
|
196
|
+
completion: nil
|
191
197
|
)
|
192
198
|
@executable_name = executable_name || ::File.basename($PROGRAM_NAME)
|
193
199
|
@middleware_stack = middleware_stack || CLI.default_middleware_stack
|
@@ -196,8 +202,9 @@ module Toys
|
|
196
202
|
@template_lookup = template_lookup || CLI.default_template_lookup
|
197
203
|
@error_handler = error_handler || DefaultErrorHandler.new
|
198
204
|
@completion = completion || DefaultCompletion.new
|
199
|
-
@logger = logger
|
200
|
-
@
|
205
|
+
@logger = logger
|
206
|
+
@logger_factory = logger ? proc { logger } : logger_factory || CLI.default_logger_factory
|
207
|
+
@base_level = base_level
|
201
208
|
@extra_delimiters = extra_delimiters
|
202
209
|
@config_dir_name = config_dir_name
|
203
210
|
@config_file_name = config_file_name
|
@@ -205,12 +212,18 @@ module Toys
|
|
205
212
|
@preload_file_name = preload_file_name
|
206
213
|
@preload_dir_name = preload_dir_name
|
207
214
|
@data_dir_name = data_dir_name
|
215
|
+
@lib_dir_name = lib_dir_name
|
208
216
|
@loader = Loader.new(
|
209
|
-
index_file_name: @index_file_name,
|
210
|
-
preload_dir_name: @preload_dir_name,
|
217
|
+
index_file_name: @index_file_name,
|
218
|
+
preload_dir_name: @preload_dir_name,
|
219
|
+
preload_file_name: @preload_file_name,
|
211
220
|
data_dir_name: @data_dir_name,
|
212
|
-
|
213
|
-
|
221
|
+
lib_dir_name: @lib_dir_name,
|
222
|
+
middleware_stack: @middleware_stack,
|
223
|
+
extra_delimiters: @extra_delimiters,
|
224
|
+
mixin_lookup: @mixin_lookup,
|
225
|
+
template_lookup: @template_lookup,
|
226
|
+
middleware_lookup: @middleware_lookup
|
214
227
|
)
|
215
228
|
end
|
216
229
|
|
@@ -235,12 +248,14 @@ module Toys
|
|
235
248
|
preload_dir_name: @preload_dir_name,
|
236
249
|
preload_file_name: @preload_file_name,
|
237
250
|
data_dir_name: @data_dir_name,
|
251
|
+
lib_dir_name: @lib_dir_name,
|
238
252
|
middleware_stack: @middleware_stack,
|
239
253
|
extra_delimiters: @extra_delimiters,
|
240
254
|
mixin_lookup: @mixin_lookup,
|
241
255
|
middleware_lookup: @middleware_lookup,
|
242
256
|
template_lookup: @template_lookup,
|
243
257
|
logger: @logger,
|
258
|
+
logger_factory: @logger_factory,
|
244
259
|
base_level: @base_level,
|
245
260
|
error_handler: @error_handler,
|
246
261
|
completion: @completion,
|
@@ -269,14 +284,21 @@ module Toys
|
|
269
284
|
attr_reader :extra_delimiters
|
270
285
|
|
271
286
|
##
|
272
|
-
# The logger
|
273
|
-
# @return [Logger]
|
287
|
+
# The global logger, if any.
|
288
|
+
# @return [Logger,nil]
|
274
289
|
#
|
275
290
|
attr_reader :logger
|
276
291
|
|
292
|
+
##
|
293
|
+
# The logger factory.
|
294
|
+
# @return [Proc]
|
295
|
+
#
|
296
|
+
attr_reader :logger_factory
|
297
|
+
|
277
298
|
##
|
278
299
|
# The initial logger level in this CLI, used as the level for verbosity 0.
|
279
|
-
#
|
300
|
+
# May be `nil`, indicating it will use the initial logger setting.
|
301
|
+
# @return [Integer,nil]
|
280
302
|
#
|
281
303
|
attr_reader :base_level
|
282
304
|
|
@@ -432,19 +454,22 @@ module Toys
|
|
432
454
|
require_exact_flag_match: tool.exact_flag_match_required?)
|
433
455
|
arg_parser.parse(args).finish
|
434
456
|
context = tool.tool_class.new(arg_parser.data)
|
457
|
+
tool.source_info&.apply_lib_paths
|
435
458
|
tool.run_initializers(context)
|
436
459
|
|
437
|
-
cur_logger =
|
438
|
-
|
439
|
-
|
460
|
+
cur_logger = context[Context::Key::LOGGER]
|
461
|
+
if cur_logger
|
462
|
+
original_level = cur_logger.level
|
463
|
+
cur_logger.level = (base_level || original_level) - context[Context::Key::VERBOSITY].to_i
|
464
|
+
end
|
440
465
|
begin
|
441
|
-
|
466
|
+
execute_tool_in_context(context, tool)
|
442
467
|
ensure
|
443
|
-
cur_logger.level = original_level
|
468
|
+
cur_logger.level = original_level if cur_logger
|
444
469
|
end
|
445
470
|
end
|
446
471
|
|
447
|
-
def
|
472
|
+
def execute_tool_in_context(context, tool)
|
448
473
|
executor = proc do
|
449
474
|
begin
|
450
475
|
if !context[Context::Key::USAGE_ERRORS].empty?
|
@@ -459,7 +484,7 @@ module Toys
|
|
459
484
|
handle_interrupt(context, tool.interrupt_handler, e)
|
460
485
|
end
|
461
486
|
end
|
462
|
-
tool.
|
487
|
+
tool.built_middleware.reverse_each do |middleware|
|
463
488
|
executor = make_executor(middleware, context, executor)
|
464
489
|
end
|
465
490
|
catch(:result) do
|
@@ -493,7 +518,11 @@ module Toys
|
|
493
518
|
end
|
494
519
|
|
495
520
|
def make_executor(middleware, context, next_executor)
|
496
|
-
|
521
|
+
if middleware.respond_to?(:run)
|
522
|
+
proc { middleware.run(context, &next_executor) }
|
523
|
+
else
|
524
|
+
next_executor
|
525
|
+
end
|
497
526
|
end
|
498
527
|
|
499
528
|
##
|
@@ -646,30 +675,33 @@ module Toys
|
|
646
675
|
end
|
647
676
|
|
648
677
|
##
|
649
|
-
# Returns a
|
678
|
+
# Returns a logger factory that generates loggers that write to stderr.
|
679
|
+
# All loggers generated by this factory share a single
|
680
|
+
# {Toys::Utils::Terminal}, so log entries may interleave but will not
|
681
|
+
# interrupt one another.
|
650
682
|
#
|
651
|
-
# @
|
652
|
-
# @return [Logger]
|
683
|
+
# @return [Proc]
|
653
684
|
#
|
654
|
-
def
|
685
|
+
def default_logger_factory
|
655
686
|
require "toys/utils/terminal"
|
656
|
-
output
|
657
|
-
|
658
|
-
|
659
|
-
|
660
|
-
|
661
|
-
|
662
|
-
|
663
|
-
|
664
|
-
|
665
|
-
|
666
|
-
|
667
|
-
|
668
|
-
|
669
|
-
|
687
|
+
shared_terminal = Utils::Terminal.new(output: $stderr)
|
688
|
+
proc do
|
689
|
+
logger = ::Logger.new(shared_terminal)
|
690
|
+
logger.formatter = proc do |severity, time, _progname, msg|
|
691
|
+
msg_str =
|
692
|
+
case msg
|
693
|
+
when ::String
|
694
|
+
msg
|
695
|
+
when ::Exception
|
696
|
+
"#{msg.message} (#{msg.class})\n" << (msg.backtrace || []).join("\n")
|
697
|
+
else
|
698
|
+
msg.inspect
|
699
|
+
end
|
700
|
+
format_log(shared_terminal, time, severity, msg_str)
|
701
|
+
end
|
702
|
+
logger.level = ::Logger::WARN
|
703
|
+
logger
|
670
704
|
end
|
671
|
-
logger.level = ::Logger::WARN
|
672
|
-
logger
|
673
705
|
end
|
674
706
|
|
675
707
|
private
|