is-command 0.9.3

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.
Files changed (3) hide show
  1. data/.yardopts +9 -0
  2. data/lib/is/command.rb +351 -0
  3. metadata +48 -0
@@ -0,0 +1,9 @@
1
+ --no-cache
2
+ --private
3
+ --protected
4
+ --hide-void-return
5
+ --plugin yard-is-monkey
6
+ --title 'Ruby Gems by Ivan Shikhalev'
7
+ --query="/^@@/ !~ o.name && @api.text != 'ignore'"
8
+ lib/**/*.rb ./*.rb
9
+ - *.md
@@ -0,0 +1,351 @@
1
+ # encoding: utf-8
2
+
3
+ require 'optparse'
4
+
5
+ module Is
6
+
7
+ class Command
8
+
9
+ VERSION = '0.9.3'
10
+
11
+ module Mixin
12
+
13
+ @@messages = {
14
+ :commands => 'Commands',
15
+ :actions => 'Actions',
16
+ :aliases => 'Aliases',
17
+ :commons => 'Common options',
18
+ :options => 'Options'
19
+ }
20
+
21
+ class << self
22
+
23
+ # @param [Hash] values
24
+ # @return [Hash]
25
+ def messages values = {}
26
+ @@messages.merge! values
27
+ end
28
+
29
+ end
30
+
31
+ # @return [Symbol, nil]
32
+ attr_reader :name
33
+
34
+ # @return [Array<String>, nil]
35
+ attr_reader :description
36
+
37
+ # @param [Symbol, String] name
38
+ # @param [Array<String>] description
39
+ # @yield [*args]
40
+ # @return [Command]
41
+ def command name, *description, &block
42
+ @actions ||= {}
43
+ @actions[name.intern] = Command.new self, name, *description, &block
44
+ end
45
+
46
+ # @param [Symbol, String, nil] name
47
+ # @param [Array<String>] description
48
+ # @yield [*args]
49
+ # @return [Hash, Proc]
50
+ def action name = nil, *description, &block
51
+ @actions ||= {}
52
+ if name
53
+ @actions[name.intern] = {
54
+ :name => name.intern,
55
+ :description => description,
56
+ :block => block
57
+ }
58
+ else
59
+ @block = block
60
+ end
61
+ end
62
+
63
+ # @param [Symbol, String] name
64
+ # @return [Command, Hash, Array, String, Symbol, nil]
65
+ def [] name
66
+ @actions[name.intern]
67
+ end
68
+
69
+ # @param [Hash, Array<Symbol>, nil] args
70
+ # @yield [name, action]
71
+ # @return [void]
72
+ def each *args, &block
73
+ if args.size == 0
74
+ c = a = s = true
75
+ elsif Hash === args[0]
76
+ h = args[0]
77
+ c = h[:command]
78
+ a = h[:action]
79
+ s = h[:synonym] || h[:alias]
80
+ else
81
+ c = args.include? :command
82
+ a = args.include? :action
83
+ s = args.include?(:synonym) || args.include?(:alias)
84
+ end
85
+ @actions.select do |k, v|
86
+ (c && Command === v) || (a && Hash === v) ||
87
+ (s && (Array === v || String === v || Symbol === v))
88
+ end.each &block
89
+ end
90
+
91
+ # @yield [*args]
92
+ # @return [Proc]
93
+ def default &block
94
+ action &block
95
+ end
96
+
97
+ # @param [Symbol, String] name
98
+ # @param [Array<String>, String, Symbol] source
99
+ # @return [Array<String>, String, Symbol]
100
+ def synonym name, source
101
+ @actions ||= {}
102
+ @actions[name.intern] = source
103
+ end
104
+
105
+ # @return [Array<Hash>]
106
+ def commons
107
+ @commons ||= []
108
+ if @up.respond_to? :commons
109
+ @up.commons + @commons
110
+ else
111
+ @commons
112
+ end
113
+ end
114
+
115
+ # @param [Array<String, Class>] defs
116
+ # @yield [value]
117
+ # @return [Hash]
118
+ def key *defs, &block
119
+ @keys ||= []
120
+ @commons ||= []
121
+ if Hash === defs[-1]
122
+ opts = defs.pop
123
+ else
124
+ opts = {}
125
+ end
126
+ k = { :defs => defs, :block => block }
127
+ if opts[:common]
128
+ @commons << k
129
+ else
130
+ @keys << k
131
+ end
132
+ k
133
+ end
134
+
135
+ # @param [Array<String>] args
136
+ # @return [Array<String>]
137
+ def parse *args
138
+ @options ||= {}
139
+ @keys ||= []
140
+ @commons ||= []
141
+ context = self
142
+ opts = OptionParser.new do |o|
143
+ (commons + @keys).each do |k|
144
+ defs = k[:defs]
145
+ block = proc do |value|
146
+ context.instance_exec value, &k[:block]
147
+ end
148
+ o.on *defs, &block
149
+ end
150
+ end
151
+ opts.order args
152
+ end
153
+
154
+ # @param [Array<String>] args
155
+ # @return [Object, nil]
156
+ def process *args
157
+ @actions ||= {}
158
+ if Hash === args[-1]
159
+ @options = args.pop
160
+ else
161
+ @options = {}
162
+ end
163
+ args = parse *args
164
+ if args[0]
165
+ a = @actions[args[0].intern]
166
+ case a
167
+ when Command
168
+ args.shift
169
+ return a.process *args, @options
170
+ when Hash
171
+ args.shift
172
+ args = parse *args
173
+ return instance_exec *args, &a[:block]
174
+ when Array
175
+ args.shift
176
+ return process *a, *args, @options
177
+ when String, Symbol
178
+ args.shift
179
+ return process a.to_s, *args, @options
180
+ end
181
+ end
182
+ if @block
183
+ return instance_exec *args, &@block
184
+ else
185
+ raise 'Invalid command line.'
186
+ end
187
+ end
188
+
189
+ # @return [String, nil]
190
+ def fullname
191
+ if @up && @up.respond_to?(:fullname)
192
+ @up.fullname + ' ' + @name.to_s
193
+ else
194
+ @name.to_s
195
+ end
196
+ end
197
+
198
+ # @param [Hash] opts
199
+ # @option opts [Boolean, String, :auto] :highlight
200
+ # @option opts [Boolean, String, :auto] :color
201
+ # @option opts [String] :marker
202
+ # @return [String]
203
+ def help opts = {}
204
+ h = opts[:highlight] || opts[:color]
205
+ hl = opts[:marker] || "\e[1m"
206
+ hr = ''
207
+ case h
208
+ when true, :true, :TRUE, :yes, :YES
209
+ hr = "\e[0m;"
210
+ when false, :false, :FALSE, :no, :NO
211
+ hl = ''
212
+ when nil, :auto, :AUTO
213
+ if $stdout.stat.chardev?
214
+ hr = "\e[0m"
215
+ else
216
+ hl = ''
217
+ end
218
+ else
219
+ hl = h
220
+ hr = "\e[0m"
221
+ end
222
+ cc = {}
223
+ aa = {}
224
+ ss = {}
225
+ @actions.each do |k, v|
226
+ case v
227
+ when Command
228
+ cc[k] = v
229
+ when Hash
230
+ aa[k] = v
231
+ else
232
+ ss[k] = v
233
+ end
234
+ end
235
+ mm = opts[:nocommons] ? @commons : commons or []
236
+ kk = @keys || []
237
+ result = ''
238
+ result << "#{hl}#{fullname}#{hr}\n"
239
+ result << "\t#{@description.join("\n\t")}\n"
240
+ result << "\n"
241
+ if ! cc.empty?
242
+ result << "#{hl}#{@@messages[:commands]}:#{hr}\n"
243
+ cc.each do |k, v|
244
+ result << "\t#{k}\n"
245
+ end
246
+ result << "\n"
247
+ end
248
+ if ! aa.empty?
249
+ result << "#{hl}#{@@messages[:actions]}:#{hr}\n"
250
+ aa.each do |k, v|
251
+ result << "\t#{k}\n"
252
+ end
253
+ result << "\n"
254
+ end
255
+ if ! ss.empty?
256
+ result << "#{hl}#{@@messages[:aliases]}:#{hr}\n"
257
+ aa.each do |k, v|
258
+ if Array === v
259
+ value = v.join ' '
260
+ else
261
+ value = v.to_s
262
+ end
263
+ result << "\t#{k} = #{value}\n"
264
+ end
265
+ result << "\n"
266
+ end
267
+ if ! mm.empty?
268
+ result << "#{hl}#{@@messages[:commons]}:#{hr}\n"
269
+ o = OptionParser.new
270
+ mm.each do |k|
271
+ o.on *k[:defs]
272
+ end
273
+ result << "#{o.summarize.join('')}\n"
274
+ #result << "\n"
275
+ end
276
+ if ! kk.empty?
277
+ result << "#{hl}#{@@messages[:options]}:#{hr}\n"
278
+ o = OptionParser.new
279
+ kk.each do |k|
280
+ o.on *k[:defs]
281
+ end
282
+ result << "#{o.summarize.join('')}\n"
283
+ #result << "\n"
284
+ end
285
+ aa.each do |k, v|
286
+ result << "#{hl}#{fullname} #{k}#{hr}\n"
287
+ result << "\t#{v[:description].join("\n\t")}\n"
288
+ result << "\n"
289
+ end
290
+ cc.each do |k, v|
291
+ result << v.help(:nocommons => true)
292
+ end
293
+ # result << "\n"
294
+ GC.start
295
+ result
296
+ end
297
+
298
+ # @return [Proc]
299
+ def to_proc
300
+ method(:process).to_proc
301
+ end
302
+
303
+ private :command, :action, :default, :synonym, :key, :parse
304
+ protected :commons
305
+
306
+ end
307
+
308
+ class Application
309
+
310
+ include Mixin
311
+
312
+ def initialize name = nil, *description, &block
313
+ if name
314
+ @name = name.intern
315
+ end
316
+ @description = description
317
+ instance_eval &block
318
+ end
319
+
320
+ # @return [Object, nil]
321
+ def run
322
+ process *ARGV
323
+ end
324
+
325
+ end
326
+
327
+ class << self
328
+
329
+ # @param [Symbol, String, nil] name
330
+ # @param [Array<String>] description
331
+ # @yield
332
+ # @return [Object, nil]
333
+ def runapp name = nil, *description, &block
334
+ app = Command::Application.new name, *description, &block
335
+ app.run
336
+ end
337
+
338
+ end
339
+
340
+ include Mixin
341
+
342
+ def initialize up, name, *description, &block
343
+ @up = up
344
+ @name = name.intern if name
345
+ @description = description
346
+ instance_eval &block
347
+ end
348
+
349
+ end
350
+
351
+ end
metadata ADDED
@@ -0,0 +1,48 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: is-command
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.9.3
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Ivan Shikhalev
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2013-04-27 00:00:00.000000000 Z
13
+ dependencies: []
14
+ description: Multicommand apps helper.
15
+ email: shikhalev@gmail.com
16
+ executables: []
17
+ extensions: []
18
+ extra_rdoc_files: []
19
+ files:
20
+ - lib/is/command.rb
21
+ - .yardopts
22
+ homepage: https://github.com/shikhalev/gems/
23
+ licenses:
24
+ - GNU LGPL
25
+ post_install_message:
26
+ rdoc_options: []
27
+ require_paths:
28
+ - lib
29
+ required_ruby_version: !ruby/object:Gem::Requirement
30
+ none: false
31
+ requirements:
32
+ - - ! '>='
33
+ - !ruby/object:Gem::Version
34
+ version: 1.9.2
35
+ required_rubygems_version: !ruby/object:Gem::Requirement
36
+ none: false
37
+ requirements:
38
+ - - ! '>='
39
+ - !ruby/object:Gem::Version
40
+ version: '0'
41
+ requirements: []
42
+ rubyforge_project:
43
+ rubygems_version: 1.8.25
44
+ signing_key:
45
+ specification_version: 3
46
+ summary: Multicommand apps helper
47
+ test_files: []
48
+ has_rdoc: