cli-dispatcher 1.2.4 → 1.2.6
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/cli-dispatcher.rb +73 -23
- data/lib/structured.rb +1 -1
- metadata +2 -2
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: be7440d7ccb3b1dfd9b90eae4b32d62597a864e4dd6676deaf9dc36e08d08470
|
|
4
|
+
data.tar.gz: 3338fab7655d4074368786f822ffac62c9b12d3e74ea98ef7bc554f44b248e93
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 16e45a2046ebbd9679789549b53e15afb4b4cd556bf1857feb25e61c4d90f55a4bb4d555f242fc66af926550566aa4e75fcf5bd693133475c00070ffbc102b91
|
|
7
|
+
data.tar.gz: 2f09de799fcca6242233880aa6452abf600e3d179f6ddd7b9b3d03747980d327e68e56cb8609264c3ac7b29397f5285d2264c4b96ef55c5d1eb4c74e05a26cb0
|
data/lib/cli-dispatcher.rb
CHANGED
|
@@ -1,5 +1,7 @@
|
|
|
1
1
|
require 'optparse'
|
|
2
2
|
require 'texttools'
|
|
3
|
+
require 'reline'
|
|
4
|
+
require 'shellwords'
|
|
3
5
|
|
|
4
6
|
#
|
|
5
7
|
# Constructs a program that can operate a number of user-provided commands. To
|
|
@@ -31,12 +33,12 @@ class Dispatcher
|
|
|
31
33
|
# Reads ARGV and dispatches a command. If no arguments are given, an
|
|
32
34
|
# appropriate warning is issued and the program terminates.
|
|
33
35
|
#
|
|
34
|
-
def dispatch_argv
|
|
36
|
+
def dispatch_argv(default_interactive = false)
|
|
35
37
|
@option_parser ||= OptionParser.new
|
|
36
38
|
add_options(@option_parser)
|
|
37
39
|
@option_parser.banner = <<~EOF
|
|
38
|
-
Usage:
|
|
39
|
-
Run '
|
|
40
|
+
Usage: #{File.basename($0)} [options] command [arguments...]
|
|
41
|
+
Run '#{File.basename($0)} help' for a list of commands.
|
|
40
42
|
|
|
41
43
|
Options:
|
|
42
44
|
EOF
|
|
@@ -48,35 +50,39 @@ class Dispatcher
|
|
|
48
50
|
end
|
|
49
51
|
|
|
50
52
|
@option_parser.parse!
|
|
51
|
-
if ARGV.empty?
|
|
53
|
+
if !ARGV.empty?
|
|
54
|
+
exit dispatch(*ARGV) ? 0 : 1
|
|
55
|
+
elsif default_interactive
|
|
56
|
+
cmd_interactive
|
|
57
|
+
else
|
|
52
58
|
STDERR.puts(@option_parser)
|
|
53
59
|
exit 1
|
|
54
60
|
end
|
|
55
|
-
dispatch(*ARGV)
|
|
56
61
|
end
|
|
57
62
|
|
|
58
63
|
#
|
|
59
64
|
# Dispatches a single command with given arguments. If the command is not
|
|
60
|
-
# found, then issues a help warning.
|
|
65
|
+
# found, then issues a help warning. Returns true or false depending on
|
|
66
|
+
# whether the command executed successfully.
|
|
61
67
|
#
|
|
62
68
|
def dispatch(cmd, *args)
|
|
63
69
|
cmd_sym = "cmd_#{cmd}".to_sym
|
|
64
70
|
begin
|
|
65
71
|
if respond_to?(cmd_sym)
|
|
66
72
|
send(cmd_sym, *args)
|
|
73
|
+
return true
|
|
67
74
|
else
|
|
68
|
-
warn("
|
|
69
|
-
|
|
70
|
-
exit(1)
|
|
75
|
+
warn("Unknown command #{cmd_sym}. Run 'help' for a list of commands.")
|
|
76
|
+
return false
|
|
71
77
|
end
|
|
72
78
|
rescue ArgumentError
|
|
73
79
|
if $!.backtrace_locations.first.base_label == cmd_sym.to_s
|
|
74
|
-
warn("#{cmd}: wrong number of arguments")
|
|
80
|
+
warn("#{cmd}: wrong number of arguments.")
|
|
75
81
|
warn("Usage: #{signature_string(cmd)}")
|
|
76
|
-
exit(1)
|
|
77
82
|
else
|
|
78
|
-
raise
|
|
83
|
+
raise
|
|
79
84
|
end
|
|
85
|
+
return false
|
|
80
86
|
end
|
|
81
87
|
end
|
|
82
88
|
|
|
@@ -143,12 +149,48 @@ class Dispatcher
|
|
|
143
149
|
cmds.sort.each do |cmd|
|
|
144
150
|
warn(TextTools.line_break(
|
|
145
151
|
help_string(cmd, all: false),
|
|
146
|
-
prefix: " " *
|
|
147
|
-
first_prefix: cmd.ljust(
|
|
152
|
+
prefix: " " * 12,
|
|
153
|
+
first_prefix: cmd.ljust(11) + ' ',
|
|
148
154
|
))
|
|
149
155
|
end
|
|
150
156
|
end
|
|
151
157
|
|
|
158
|
+
def help_interactive
|
|
159
|
+
return "Start an interactive shell for entering commands."
|
|
160
|
+
end
|
|
161
|
+
|
|
162
|
+
#
|
|
163
|
+
# Runs the dispatcher in interactive mode, in which command lines are read
|
|
164
|
+
# from a prompt.
|
|
165
|
+
#
|
|
166
|
+
def cmd_interactive
|
|
167
|
+
stty_save = `stty -g`.chomp
|
|
168
|
+
loop do
|
|
169
|
+
begin
|
|
170
|
+
buf = Reline.readline(interactive_prompt, true)
|
|
171
|
+
exit unless buf
|
|
172
|
+
args = buf.shellsplit
|
|
173
|
+
next if args.empty?
|
|
174
|
+
exit if args.first == 'exit'
|
|
175
|
+
dispatch(*args)
|
|
176
|
+
rescue Interrupt
|
|
177
|
+
system("stty", stty_save)
|
|
178
|
+
exit
|
|
179
|
+
rescue
|
|
180
|
+
STDERR.puts $!.full_message
|
|
181
|
+
end
|
|
182
|
+
end
|
|
183
|
+
end
|
|
184
|
+
|
|
185
|
+
#
|
|
186
|
+
# Returns the string for the interactive prompt. Subclasses can override this
|
|
187
|
+
# method to offer more detailed prompts.
|
|
188
|
+
#
|
|
189
|
+
def interactive_prompt
|
|
190
|
+
return "#{File.basename($0)}> "
|
|
191
|
+
end
|
|
192
|
+
|
|
193
|
+
|
|
152
194
|
#
|
|
153
195
|
# Adds commands relevant when this dispatcher uses Structured data inputs.
|
|
154
196
|
#
|
|
@@ -185,12 +227,16 @@ class Dispatcher
|
|
|
185
227
|
end
|
|
186
228
|
|
|
187
229
|
|
|
188
|
-
# Receives options, passing them to OptionParser. The options are processed
|
|
189
|
-
# when dispatch_argv is called. The usage of this method is that after the
|
|
190
|
-
# Dispatcher object is created, this method is called to instantiate the
|
|
191
|
-
# options for the class. See #add_options for another way of doing this.
|
|
192
230
|
#
|
|
193
|
-
#
|
|
231
|
+
# Creates an OptionParser object for this Dispatcher. The options for the
|
|
232
|
+
# OptionParser are defined in a block passed to this method. The block
|
|
233
|
+
# receives one argument, which is the OptionParser object being created.
|
|
234
|
+
#
|
|
235
|
+
# The banner and -h/--help options will be added automatically to the created
|
|
236
|
+
# OptionParser object.
|
|
237
|
+
#
|
|
238
|
+
# For a slightly simpler way to set up options for this Dispatcher object, see
|
|
239
|
+
# the add_options method.
|
|
194
240
|
#
|
|
195
241
|
def setup_options
|
|
196
242
|
@option_parser = OptionParser.new do |opts|
|
|
@@ -199,10 +245,14 @@ class Dispatcher
|
|
|
199
245
|
end
|
|
200
246
|
|
|
201
247
|
#
|
|
202
|
-
#
|
|
203
|
-
# nothing.
|
|
204
|
-
#
|
|
205
|
-
#
|
|
248
|
+
# Adds command-line options for this class. By default, this method does
|
|
249
|
+
# nothing. Subclasses may override this method to add options. The method will
|
|
250
|
+
# be automatically invoked during a dispatch_argv call, thereby constructing
|
|
251
|
+
# an OptionParser object to handle the command-line arguments.
|
|
252
|
+
#
|
|
253
|
+
# The argument to this method is an OptionParser object, to which the desired
|
|
254
|
+
# options may be added. The banner and -h/--help options will be added
|
|
255
|
+
# automatically to the OptionParser object.
|
|
206
256
|
#
|
|
207
257
|
def add_options(opts)
|
|
208
258
|
end
|
data/lib/structured.rb
CHANGED
metadata
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: cli-dispatcher
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 1.2.
|
|
4
|
+
version: 1.2.6
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Charles Duan
|
|
8
8
|
bindir: bin
|
|
9
9
|
cert_chain: []
|
|
10
|
-
date: 2025-
|
|
10
|
+
date: 2025-12-04 00:00:00.000000000 Z
|
|
11
11
|
dependencies: []
|
|
12
12
|
description: |
|
|
13
13
|
Library for creating command-line programs that accept commands. Also
|