squared 0.6.1 → 0.6.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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +88 -0
- data/README.md +23 -13
- data/lib/squared/common/base.rb +2 -2
- data/lib/squared/common/format.rb +39 -32
- data/lib/squared/common/prompt.rb +6 -4
- data/lib/squared/common/shell.rb +5 -4
- data/lib/squared/config.rb +7 -8
- data/lib/squared/version.rb +1 -1
- data/lib/squared/workspace/application.rb +72 -23
- data/lib/squared/workspace/project/base.rb +205 -116
- data/lib/squared/workspace/project/docker.rb +20 -24
- data/lib/squared/workspace/project/git.rb +100 -47
- data/lib/squared/workspace/project/node.rb +226 -132
- data/lib/squared/workspace/project/python.rb +20 -18
- data/lib/squared/workspace/project/ruby.rb +62 -60
- data/lib/squared/workspace/project/support/class.rb +88 -616
- data/lib/squared/workspace/project/support/optionpartition.rb +641 -0
- data/lib/squared/workspace/project.rb +0 -1
- data/lib/squared/workspace/repo.rb +23 -14
- data/lib/squared/workspace/series.rb +10 -8
- data/squared.gemspec +2 -2
- metadata +2 -2
- data/lib/squared/workspace/project/support.rb +0 -3
|
@@ -1,638 +1,55 @@
|
|
|
1
1
|
# frozen_string_literal: true
|
|
2
2
|
|
|
3
|
-
require 'forwardable'
|
|
4
|
-
|
|
5
3
|
module Squared
|
|
6
4
|
module Workspace
|
|
7
5
|
module Project
|
|
8
6
|
module Support
|
|
9
|
-
|
|
10
|
-
include Common::Shell
|
|
11
|
-
extend Forwardable
|
|
12
|
-
|
|
13
|
-
OPT_NAME = /\A(?:(--)|-)((?(1)[^\[\]=\s-][^\[\]=\s]*|[^\[\]=\s-]))\z/
|
|
14
|
-
OPT_VALUE = /\A-{0,2}([^\[\]=\s-][^\[\]=\s]*)(?:\s*=\s*|\s+)(.+)\z/
|
|
15
|
-
OPT_SINGLE = /\A-([^\[\]=\s-])(.+)\z/
|
|
16
|
-
private_constant :OPT_NAME, :OPT_VALUE, :OPT_SINGLE
|
|
17
|
-
|
|
18
|
-
class << self
|
|
19
|
-
include Common::Format
|
|
20
|
-
include Shell
|
|
21
|
-
include Prompt
|
|
22
|
-
|
|
23
|
-
def append(target, *args, delim: false, escape: false, quote: true, strip: nil, force: true, double: false,
|
|
24
|
-
filter: nil, **)
|
|
25
|
-
return if (ret = args.flatten).empty?
|
|
26
|
-
|
|
27
|
-
target << '--' if delim && !target.include?('--')
|
|
28
|
-
if strip
|
|
29
|
-
pat, s = Array(strip)
|
|
30
|
-
ret.map! { |val| val.gsub(pat, s || '') }
|
|
31
|
-
end
|
|
32
|
-
ret, err = ret.partition { |val| filter.match?(val) } if filter
|
|
33
|
-
if block_given?
|
|
34
|
-
out = []
|
|
35
|
-
err ||= []
|
|
36
|
-
ret.each do |val|
|
|
37
|
-
case (s = yield val)
|
|
38
|
-
when String
|
|
39
|
-
out << s
|
|
40
|
-
when NilClass, FalseClass
|
|
41
|
-
err << val
|
|
42
|
-
else
|
|
43
|
-
out << val
|
|
44
|
-
end
|
|
45
|
-
end
|
|
46
|
-
ret = out
|
|
47
|
-
end
|
|
48
|
-
if escape || quote
|
|
49
|
-
ret.map! do |val|
|
|
50
|
-
if opt?(val)
|
|
51
|
-
val
|
|
52
|
-
elsif escape
|
|
53
|
-
shell_escape(val, quote: quote, double: double)
|
|
54
|
-
else
|
|
55
|
-
shell_quote(val, force: force, double: double)
|
|
56
|
-
end
|
|
57
|
-
end
|
|
58
|
-
end
|
|
59
|
-
if target.is_a?(Set)
|
|
60
|
-
target.merge(ret)
|
|
61
|
-
else
|
|
62
|
-
target.concat(ret)
|
|
63
|
-
end
|
|
64
|
-
err || ret
|
|
65
|
-
end
|
|
66
|
-
|
|
67
|
-
def clear(target, opts, pass: true, styles: nil, **kwargs)
|
|
68
|
-
return if opts.empty?
|
|
69
|
-
|
|
70
|
-
kwargs[:subject] ||= target.first.stripext
|
|
71
|
-
kwargs[:hint] ||= 'unrecognized'
|
|
72
|
-
append(target, opts, delim: true) if kwargs.delete(:append)
|
|
73
|
-
warn log_message(Logger::WARN, opts.join(', '), pass: true, **kwargs)
|
|
74
|
-
exit 1 unless pass || confirm("Run? [#{sub_style(target, styles: styles)}]", 'N')
|
|
75
|
-
end
|
|
76
|
-
|
|
77
|
-
def delete_key(target, *args, value: false, reverse: false, count: -1)
|
|
78
|
-
ret = []
|
|
79
|
-
args.each do |val|
|
|
80
|
-
next if (opts = target.grep(matchopt(val, value))).empty?
|
|
81
|
-
|
|
82
|
-
opts = opts.first(count) if count >= 0
|
|
83
|
-
opts.send(reverse ? :reverse_each : :each) { |key| target.delete(key) }
|
|
84
|
-
ret.concat(opts)
|
|
85
|
-
end
|
|
86
|
-
ret
|
|
87
|
-
end
|
|
88
|
-
|
|
89
|
-
def strip(val)
|
|
90
|
-
return [] unless val
|
|
91
|
-
|
|
92
|
-
val = shell_split val if val.is_a?(String)
|
|
93
|
-
val.map { |s| s.sub(OPT_SINGLE, '\1=\2').sub(OPT_VALUE, '\1=\2').sub(OPT_NAME, '\2') }.reject(&:empty?)
|
|
94
|
-
end
|
|
95
|
-
|
|
96
|
-
def select(list, bare: true, no: true, single: false, double: false)
|
|
97
|
-
ret = bare ? list.grep_v(/=/) : list.grep(/=/).map! { |val| val.split('=', 2).first }
|
|
98
|
-
ret.map! { |val| val.split('|', 2).last }
|
|
99
|
-
ret = ret.grep_v(/\Ano-/) unless no
|
|
100
|
-
return ret if single == double
|
|
101
|
-
|
|
102
|
-
ret.select { |val| single ? val.size == 1 : val.size > 1 }
|
|
103
|
-
end
|
|
7
|
+
autoload :OptionPartition, File.expand_path('optionpartition', __dir__)
|
|
104
8
|
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
j = val =~ OPT_VALUE ? $1 : val
|
|
109
|
-
(keys[j] ||= []) << i unless pass.include?(j)
|
|
110
|
-
end
|
|
111
|
-
data = keys.map { |item| item[1].size > 1 ? item[1][0..-2] : [] }.reject(&:empty?)
|
|
112
|
-
return if data.empty?
|
|
113
|
-
|
|
114
|
-
data.each { |key| key.each { |i| list[i] = nil } }
|
|
115
|
-
list.compact!
|
|
116
|
-
list
|
|
117
|
-
end
|
|
118
|
-
|
|
119
|
-
def arg?(target, *args, value: false, **)
|
|
120
|
-
r, s = args.partition { |val| val.is_a?(Regexp) }
|
|
121
|
-
r << matchopts(s, value) unless s.empty?
|
|
122
|
-
s = target.to_a.compact
|
|
123
|
-
r.any? { |pat| s.any?(pat) }
|
|
124
|
-
end
|
|
125
|
-
|
|
126
|
-
def opt?(val)
|
|
127
|
-
val.start_with?('-') && (OPT_NAME.match?(val) || OPT_VALUE.match?(val) || OPT_SINGLE.match?(val))
|
|
128
|
-
end
|
|
129
|
-
|
|
130
|
-
def pattern?(val)
|
|
131
|
-
val.match?(/(?:\A\^|\$\z)/) || val.match?(/(?:\.[*+]|\(\?:|\\[dsw]|\[.+\]|\{\d+,?\d*\})/)
|
|
132
|
-
end
|
|
133
|
-
|
|
134
|
-
private
|
|
135
|
-
|
|
136
|
-
def matchopt(val, value = false)
|
|
137
|
-
/\A#{val.size == 1 ? shortopt(val) : longopt(val, value)}/
|
|
138
|
-
end
|
|
139
|
-
|
|
140
|
-
def matchopts(list, value = false)
|
|
141
|
-
a, b = Array(list).partition { |val| val.size == 1 || val.match?(OPT_SINGLE) }
|
|
142
|
-
return /\A#{shortopt(*a)}}/ if b.empty?
|
|
143
|
-
return /\A#{longopt(*b, value)}/ if a.empty?
|
|
144
|
-
|
|
145
|
-
/\A(?:#{shortopt(*a)}|#{longopt(*b, value)})/
|
|
146
|
-
end
|
|
147
|
-
|
|
148
|
-
def shortopt(*group)
|
|
149
|
-
group.map! { |s| s.delete_prefix('-') }
|
|
150
|
-
"-(?:#{Regexp.escape(group.join('|'))})(?:\\z|[^ =]| +[^ -])"
|
|
151
|
-
end
|
|
152
|
-
|
|
153
|
-
def longopt(*group, value)
|
|
154
|
-
group.map! { |s| s.delete_prefix('--') }
|
|
155
|
-
"--(?:#{Regexp.escape(group.join('|'))})(?:#{value ? '=[^ ]| +[^ -]' : '[= ]|\z'})"
|
|
156
|
-
end
|
|
9
|
+
class JoinSet < Set
|
|
10
|
+
def self.to_s
|
|
11
|
+
super[/[^:]+\z/, 0]
|
|
157
12
|
end
|
|
158
13
|
|
|
159
|
-
|
|
14
|
+
alias to_ary to_a
|
|
160
15
|
|
|
161
|
-
|
|
162
|
-
:merge, :delete, :delete?, :delete_if, :grep, :grep_v, :inspect, :to_a, :to_s
|
|
163
|
-
def_delegators :@extras, :empty?, :each, :each_with_index, :partition, :dup, :first, :shift, :unshift,
|
|
164
|
-
:pop, :push, :concat, :index, :join, :map, :map!, :detect, :select, :select!, :reject, :size
|
|
165
|
-
|
|
166
|
-
def_delegator :@extras, :delete, :remove
|
|
167
|
-
def_delegator :@extras, :delete_at, :remove_at
|
|
168
|
-
def_delegator :@extras, :delete_if, :remove_if
|
|
169
|
-
def_delegator :@extras, :find_all, :detect_all
|
|
170
|
-
def_delegator :@extras, :find_index, :detect_index
|
|
171
|
-
|
|
172
|
-
def initialize(opts, list, target = Set.new, project: nil, path: nil, sep: '=', **kwargs, &blk)
|
|
173
|
-
@target = target.is_a?(Set) ? target : target.to_set
|
|
174
|
-
@project = project
|
|
175
|
-
@path = path || project&.path
|
|
176
|
-
@sep = sep
|
|
177
|
-
@errors = []
|
|
178
|
-
@found = []
|
|
179
|
-
parse(list, opts, **kwargs, &blk)
|
|
180
|
-
end
|
|
16
|
+
attr_reader :delim, :extras, :multiple
|
|
181
17
|
|
|
182
|
-
def
|
|
18
|
+
def initialize(data = [], delim: ' ', partition: '--', uniq: /\A--?[^=\s-]/, multiple: [])
|
|
19
|
+
@delim = delim
|
|
20
|
+
@partition = partition
|
|
21
|
+
@uniq = uniq
|
|
22
|
+
@multiple = multiple
|
|
183
23
|
@extras = []
|
|
184
|
-
|
|
185
|
-
bare = []
|
|
186
|
-
e = []
|
|
187
|
-
b = []
|
|
188
|
-
m = []
|
|
189
|
-
p = []
|
|
190
|
-
q = []
|
|
191
|
-
qq = []
|
|
192
|
-
i = []
|
|
193
|
-
f = []
|
|
194
|
-
si = []
|
|
195
|
-
bl = []
|
|
196
|
-
list.flat_map do |val|
|
|
197
|
-
x, y = val.split('|', 2)
|
|
198
|
-
if y
|
|
199
|
-
if (n = val.index('='))
|
|
200
|
-
x += val[n..-1]
|
|
201
|
-
end
|
|
202
|
-
[x, y]
|
|
203
|
-
else
|
|
204
|
-
x
|
|
205
|
-
end
|
|
206
|
-
end
|
|
207
|
-
.each do |val|
|
|
208
|
-
if (n = val.index('='))
|
|
209
|
-
flag = val[0, n]
|
|
210
|
-
case val[n.succ]
|
|
211
|
-
when 'e'
|
|
212
|
-
e << flag
|
|
213
|
-
when 'b'
|
|
214
|
-
b << flag
|
|
215
|
-
when 'm'
|
|
216
|
-
m << flag
|
|
217
|
-
when 'q'
|
|
218
|
-
qq << flag if val[n + 2] == 'q'
|
|
219
|
-
q << flag
|
|
220
|
-
when 'p'
|
|
221
|
-
p << flag
|
|
222
|
-
when 'i'
|
|
223
|
-
i << flag
|
|
224
|
-
when 'f'
|
|
225
|
-
f << flag
|
|
226
|
-
when 'n'
|
|
227
|
-
si << flag
|
|
228
|
-
when 'v'
|
|
229
|
-
@values << Regexp.escape(flag)
|
|
230
|
-
when '!'
|
|
231
|
-
bl << flag
|
|
232
|
-
else
|
|
233
|
-
next
|
|
234
|
-
end
|
|
235
|
-
m << flag if val[n + 2] == 'm'
|
|
236
|
-
bare << flag if val.end_with?('?')
|
|
237
|
-
else
|
|
238
|
-
bare << val
|
|
239
|
-
end
|
|
240
|
-
end
|
|
241
|
-
no = (no || []).map { |val| (n = val.index('=')) ? val[0, n] : val }
|
|
242
|
-
bare.concat(no)
|
|
243
|
-
if underscore
|
|
244
|
-
tr = ->(a) { a.map { |val| val.tr('-', '_') } }
|
|
245
|
-
@values.concat(tr.call(@values))
|
|
246
|
-
bare.concat(tr.call(bare))
|
|
247
|
-
e.concat(tr.call(e))
|
|
248
|
-
b.concat(tr.call(b))
|
|
249
|
-
m.concat(tr.call(m))
|
|
250
|
-
p.concat(tr.call(p))
|
|
251
|
-
q.concat(tr.call(q))
|
|
252
|
-
qq.concat(tr.call(qq))
|
|
253
|
-
i.concat(tr.call(i))
|
|
254
|
-
f.concat(tr.call(f))
|
|
255
|
-
si.concat(tr.call(si))
|
|
256
|
-
bl.concat(tr.call(bl))
|
|
257
|
-
no.concat(tr.call(no))
|
|
258
|
-
end
|
|
259
|
-
numtype = [
|
|
260
|
-
[i, /\A\d+\z/],
|
|
261
|
-
[f, /\A\d*(?:\.\d+)?\z/],
|
|
262
|
-
[si, /\A-?\d+\z/]
|
|
263
|
-
].freeze
|
|
264
|
-
numcheck = ->(k, v) { numtype.any? { |flag, pat| flag.include?(k) && v.match?(pat) } }
|
|
265
|
-
skip = false
|
|
266
|
-
opts.each do |opt|
|
|
267
|
-
next skip = true if opt == '--'
|
|
268
|
-
next push opt if skip
|
|
269
|
-
|
|
270
|
-
if single&.match?(opt)
|
|
271
|
-
add "-#{opt}"
|
|
272
|
-
elsif bare.include?(opt)
|
|
273
|
-
add(opt.size == 1 ? "-#{opt}" : "--#{opt}")
|
|
274
|
-
elsif opt.start_with?(/no[-_]/) && no.include?(name = opt[3..-1])
|
|
275
|
-
add "--no-#{name}"
|
|
276
|
-
else
|
|
277
|
-
if opt =~ OPT_VALUE
|
|
278
|
-
key = $1
|
|
279
|
-
val = $2
|
|
280
|
-
merge = m.include?(key)
|
|
281
|
-
if e.include?(key)
|
|
282
|
-
add shell_option(key, val, merge: merge, sep: sep)
|
|
283
|
-
elsif q.include?(key)
|
|
284
|
-
add quote_option(key, val, double: qq.include?(key), merge: merge, sep: sep)
|
|
285
|
-
elsif p.include?(key)
|
|
286
|
-
if val.match?(/\A(["']).+\1\z/)
|
|
287
|
-
add shell_option(key, val, escape: false, merge: merge, sep: sep)
|
|
288
|
-
elsif path
|
|
289
|
-
add quote_option(key, path + val, merge: merge, sep: sep)
|
|
290
|
-
else
|
|
291
|
-
push opt
|
|
292
|
-
end
|
|
293
|
-
elsif b.include?(key) || (bl.include?(key) && %w[true false].include?(val)) || numcheck.call(key, val)
|
|
294
|
-
add basic_option(key, val, merge: merge, sep: sep)
|
|
295
|
-
elsif merge
|
|
296
|
-
add basic_option(key, val, merge: true, sep: sep)
|
|
297
|
-
else
|
|
298
|
-
push opt
|
|
299
|
-
end
|
|
300
|
-
opt = key
|
|
301
|
-
else
|
|
302
|
-
push opt
|
|
303
|
-
skip = true if args
|
|
304
|
-
end
|
|
305
|
-
skip = true if first&.any? { |s| s.is_a?(Regexp) ? opt.match?(s) : !opt.include?(s) }
|
|
306
|
-
end
|
|
307
|
-
end
|
|
308
|
-
@values = @values.empty? ? /\A\s+\z/ : /\A(#{@values.join('|')})#{sep}(.+)\z/m
|
|
309
|
-
@extras.each_with_index(&blk) if block_given?
|
|
310
|
-
self
|
|
311
|
-
end
|
|
312
|
-
|
|
313
|
-
def swap(opts = nil, &blk)
|
|
314
|
-
unless opts
|
|
315
|
-
opts = found
|
|
316
|
-
@found = []
|
|
317
|
-
end
|
|
318
|
-
opts.sort!(&blk) if block_given?
|
|
319
|
-
@extras = opts
|
|
320
|
-
self
|
|
321
|
-
end
|
|
322
|
-
|
|
323
|
-
def append(*args, **kwargs, &blk)
|
|
324
|
-
args = extras if args.empty?
|
|
325
|
-
out = OptionPartition.append(target, *args, **kwargs, &blk)
|
|
326
|
-
errors.concat(out) if out && (block_given? || kwargs[:filter])
|
|
327
|
-
self
|
|
328
|
-
end
|
|
329
|
-
|
|
330
|
-
def append_any(*args, quote: true, **kwargs)
|
|
331
|
-
(args.empty? ? extras : args.flatten).each do |val|
|
|
332
|
-
val = yield val if block_given?
|
|
333
|
-
next unless val.is_a?(String)
|
|
334
|
-
|
|
335
|
-
if exist?(val)
|
|
336
|
-
add_path(val, **kwargs)
|
|
337
|
-
elsif quote
|
|
338
|
-
add_quote(val, **kwargs)
|
|
339
|
-
else
|
|
340
|
-
add val
|
|
341
|
-
end
|
|
342
|
-
end
|
|
343
|
-
self
|
|
344
|
-
end
|
|
345
|
-
|
|
346
|
-
def delete_key(*args, **kwargs)
|
|
347
|
-
OptionPartition.delete_key(target, *args, **kwargs)
|
|
348
|
-
self
|
|
349
|
-
end
|
|
350
|
-
|
|
351
|
-
def values_of(*args, strict: true, first: false, last: false)
|
|
352
|
-
eq, s = strict ? [sep, '[^ ]+'] : ['(?:=| +)', '[^-][^ ]*']
|
|
353
|
-
g = ["\"((?:[^\"]|(?<=\\\\)\"(?!$#{windows? ? '| ' : ''}))*)\""]
|
|
354
|
-
g << "'((?:[^']|'\\\\'')*)'" unless windows?
|
|
355
|
-
g << "(#{s})"
|
|
356
|
-
args.map! do |opt|
|
|
357
|
-
if opt.size == 1
|
|
358
|
-
/(?:\A| )-#{opt} ?([^ ]+)/
|
|
359
|
-
else
|
|
360
|
-
/(?:\A| )--#{opt + eq}(?:#{g.join('|')})/
|
|
361
|
-
end
|
|
362
|
-
end
|
|
363
|
-
ret = []
|
|
364
|
-
target.each do |opt|
|
|
365
|
-
args.each do |pat|
|
|
366
|
-
next unless opt =~ pat
|
|
367
|
-
|
|
368
|
-
ret << ($1 || $2 || $3)
|
|
369
|
-
break
|
|
370
|
-
end
|
|
371
|
-
end
|
|
372
|
-
return ret unless first || last
|
|
373
|
-
|
|
374
|
-
if last.is_a?(Numeric)
|
|
375
|
-
ret.last(last)
|
|
376
|
-
elsif last
|
|
377
|
-
ret.last
|
|
378
|
-
else
|
|
379
|
-
first.is_a?(Numeric) ? ret.first(first) : ret.first
|
|
380
|
-
end
|
|
381
|
-
end
|
|
382
|
-
|
|
383
|
-
def uniq(list)
|
|
384
|
-
ignore = map { |val| nameonly(val) }
|
|
385
|
-
list.reject { |val| ignore.include?(s = nameonly(val)) || any?(OptionPartition.send(:matchopt, s)) }
|
|
386
|
-
end
|
|
387
|
-
|
|
388
|
-
def clear(opts = nil, errors: false, **kwargs)
|
|
389
|
-
styles = project.theme[:inline] if project
|
|
390
|
-
if errors
|
|
391
|
-
OptionPartition.clear(target, @errors, styles: styles, **kwargs)
|
|
392
|
-
@errors.clear
|
|
393
|
-
return self unless opts
|
|
394
|
-
end
|
|
395
|
-
opts ||= extras
|
|
396
|
-
OptionPartition.clear(target, opts - found, styles: styles, **kwargs)
|
|
397
|
-
opts.clear
|
|
398
|
-
self
|
|
399
|
-
end
|
|
400
|
-
|
|
401
|
-
def adjoin(*args, with: nil, start: false)
|
|
402
|
-
index = -1
|
|
403
|
-
temp = to_a
|
|
404
|
-
if with
|
|
405
|
-
pat = case with
|
|
406
|
-
when String, Symbol
|
|
407
|
-
/\A#{Regexp.escape(with)}\z/
|
|
408
|
-
when Array
|
|
409
|
-
OptionPartition.send(:matchopts, with)
|
|
410
|
-
else
|
|
411
|
-
with
|
|
412
|
-
end
|
|
413
|
-
temp.each_with_index do |val, i|
|
|
414
|
-
if val.to_s.match?(pat)
|
|
415
|
-
index = i + (start.is_a?(Numeric) ? start : 1)
|
|
416
|
-
break
|
|
417
|
-
end
|
|
418
|
-
end
|
|
419
|
-
else
|
|
420
|
-
temp.each_with_index do |val, i|
|
|
421
|
-
if index == 0
|
|
422
|
-
next unless val.start_with?('-')
|
|
423
|
-
|
|
424
|
-
index = i
|
|
425
|
-
break
|
|
426
|
-
elsif i > 0 && !val.start_with?('-')
|
|
427
|
-
if start
|
|
428
|
-
index = i + (start.is_a?(Numeric) ? start : 1)
|
|
429
|
-
break
|
|
430
|
-
end
|
|
431
|
-
index = 0
|
|
432
|
-
end
|
|
433
|
-
end
|
|
434
|
-
end
|
|
435
|
-
if index > 0
|
|
436
|
-
if args.empty?
|
|
437
|
-
args = dup
|
|
438
|
-
reset
|
|
439
|
-
else
|
|
440
|
-
args.each { |val| remove val }
|
|
441
|
-
end
|
|
442
|
-
args = temp[0...index] + args + temp[index..-1]
|
|
443
|
-
target.clear
|
|
444
|
-
end
|
|
445
|
-
merge args
|
|
446
|
-
self
|
|
447
|
-
end
|
|
448
|
-
|
|
449
|
-
def add_path(*args, force: true, double: false, **kwargs)
|
|
450
|
-
if args.empty?
|
|
451
|
-
args = select { |val| val.is_a?(String) }
|
|
452
|
-
args.map! { |val| path + val } if path
|
|
453
|
-
append(args, force: force, **kwargs)
|
|
454
|
-
else
|
|
455
|
-
add shell_quote(path ? path.join(*args) : File.join(*args), option: false, force: force, double: double)
|
|
456
|
-
end
|
|
457
|
-
self
|
|
458
|
-
end
|
|
459
|
-
|
|
460
|
-
def add_quote(*args, **kwargs)
|
|
461
|
-
args.compact!
|
|
462
|
-
merge(args.map! { |val| val == '--' || OptionPartition.opt?(val) ? val : shell_quote(val, **kwargs) })
|
|
463
|
-
self
|
|
464
|
-
end
|
|
465
|
-
|
|
466
|
-
def add_option(flag, val = nil, **kwargs)
|
|
467
|
-
add shell_option(flag, val, **kwargs)
|
|
468
|
-
self
|
|
469
|
-
end
|
|
470
|
-
|
|
471
|
-
def add_first(fallback = nil, prefix: nil, path: false, quote: false, reverse: false, expect: false, **kwargs)
|
|
472
|
-
val = (reverse ? pop : shift) || fallback
|
|
473
|
-
if val
|
|
474
|
-
val.delete_prefix!(prefix) if prefix
|
|
475
|
-
return self if block_given? && !(val = yield val).is_a?(String)
|
|
476
|
-
|
|
477
|
-
if path
|
|
478
|
-
add_path(val, **kwargs)
|
|
479
|
-
elsif quote
|
|
480
|
-
add_quote(val, **kwargs)
|
|
481
|
-
else
|
|
482
|
-
add val
|
|
483
|
-
end
|
|
484
|
-
elsif expect
|
|
485
|
-
raise(expect.is_a?(String) ? expect : 'no value provided')
|
|
486
|
-
end
|
|
487
|
-
self
|
|
488
|
-
end
|
|
489
|
-
|
|
490
|
-
def last(val = nil, &blk)
|
|
491
|
-
unless block_given?
|
|
492
|
-
case val
|
|
493
|
-
when NilClass
|
|
494
|
-
return extras.last
|
|
495
|
-
when Numeric
|
|
496
|
-
return extras.last(val)
|
|
497
|
-
when String, Array, Regexp
|
|
498
|
-
val = OptionPartition.send(:matchopts, val) unless val.is_a?(Regexp)
|
|
499
|
-
blk = proc { |s| s&.match?(val) }
|
|
500
|
-
else
|
|
501
|
-
raise TypeError, "unknown: #{val}"
|
|
502
|
-
end
|
|
503
|
-
end
|
|
504
|
-
ret = find_all(&blk)
|
|
505
|
-
unless ret.empty?
|
|
506
|
-
ret = case val
|
|
507
|
-
when NilClass
|
|
508
|
-
ret.first(1)
|
|
509
|
-
when Numeric
|
|
510
|
-
ret.first(val)
|
|
511
|
-
else
|
|
512
|
-
ret
|
|
513
|
-
end
|
|
514
|
-
ret.each do |opt|
|
|
515
|
-
delete opt
|
|
516
|
-
add opt
|
|
517
|
-
end
|
|
518
|
-
end
|
|
519
|
-
val.nil? ? ret.first : ret
|
|
520
|
-
end
|
|
521
|
-
|
|
522
|
-
def splice(*exclude, quote: true, delim: true, path: false, pattern: false, &blk)
|
|
523
|
-
found, other = if block_given?
|
|
524
|
-
partition(&blk)
|
|
525
|
-
elsif exclude.first.is_a?(Symbol)
|
|
526
|
-
partition(&exclude.first)
|
|
527
|
-
else
|
|
528
|
-
partition do |val|
|
|
529
|
-
next false if pattern && OptionPartition.pattern?(val)
|
|
530
|
-
|
|
531
|
-
exclude.none? { |pat| val.match?(Regexp.new(pat)) }
|
|
532
|
-
end
|
|
533
|
-
end
|
|
534
|
-
unless found.empty?
|
|
535
|
-
add '--' if delim
|
|
536
|
-
extras.clear
|
|
537
|
-
concat other
|
|
538
|
-
if path
|
|
539
|
-
found.each { |val| add_path(val) }
|
|
540
|
-
else
|
|
541
|
-
found.map! { |val| shell_quote(val) } if quote
|
|
542
|
-
merge found
|
|
543
|
-
end
|
|
544
|
-
end
|
|
545
|
-
self
|
|
546
|
-
end
|
|
547
|
-
|
|
548
|
-
def reset(errors: false)
|
|
549
|
-
extras.clear
|
|
550
|
-
found.clear
|
|
551
|
-
clear(errors: true) if errors
|
|
552
|
-
self
|
|
553
|
-
end
|
|
554
|
-
|
|
555
|
-
def append?(key, val = nil, type: nil, force: false, sep: '=', **kwargs)
|
|
556
|
-
return false unless force || !arg?(key)
|
|
557
|
-
|
|
558
|
-
val = yield self if block_given?
|
|
559
|
-
return false unless val
|
|
560
|
-
|
|
561
|
-
type ||= :quote if kwargs.empty?
|
|
562
|
-
add case type
|
|
563
|
-
when :quote
|
|
564
|
-
quote_option(key, val, sep: sep)
|
|
565
|
-
when :basic
|
|
566
|
-
basic_option(key, val, sep: sep)
|
|
567
|
-
else
|
|
568
|
-
shell_option(key, val, sep: sep, **kwargs)
|
|
569
|
-
end
|
|
570
|
-
true
|
|
571
|
-
end
|
|
572
|
-
|
|
573
|
-
def arg?(*args, **kwargs)
|
|
574
|
-
OptionPartition.arg?(target, *args, **kwargs)
|
|
24
|
+
super(data.compact)
|
|
575
25
|
end
|
|
576
26
|
|
|
577
|
-
def
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
|
|
585
|
-
|
|
586
|
-
add_first(path: true, reverse: !first)
|
|
587
|
-
end
|
|
588
|
-
else
|
|
589
|
-
each_with_index do |val, i|
|
|
590
|
-
next unless with_glob?(val, glob)
|
|
591
|
-
|
|
592
|
-
if add
|
|
593
|
-
remove_at i
|
|
594
|
-
add_path val
|
|
595
|
-
end
|
|
596
|
-
return true
|
|
597
|
-
end
|
|
598
|
-
false
|
|
27
|
+
def multiple=(val)
|
|
28
|
+
case val
|
|
29
|
+
when Enumerable
|
|
30
|
+
@multiple.concat(val.to_a.map(&:to_s))
|
|
31
|
+
when String, Symbol, Pathname
|
|
32
|
+
@multiple << val.to_s
|
|
33
|
+
when NilClass, FalseClass
|
|
34
|
+
@multiple.clear
|
|
599
35
|
end
|
|
600
36
|
end
|
|
601
37
|
|
|
602
|
-
def
|
|
603
|
-
|
|
604
|
-
concat list
|
|
605
|
-
self
|
|
606
|
-
end
|
|
38
|
+
def insert(*args)
|
|
39
|
+
replace Set.new(compact.insert(*args))
|
|
607
40
|
end
|
|
608
41
|
|
|
609
|
-
|
|
610
|
-
|
|
611
|
-
def nameonly(val)
|
|
612
|
-
val[OPT_VALUE, 1] || val
|
|
42
|
+
def slice(*args)
|
|
43
|
+
compact.slice(*args)
|
|
613
44
|
end
|
|
614
45
|
|
|
615
|
-
def
|
|
616
|
-
|
|
617
|
-
|
|
618
|
-
path.join(val).exist? || (glob && !path.glob(val).empty?)
|
|
619
|
-
end
|
|
620
|
-
|
|
621
|
-
def windows?
|
|
622
|
-
Rake::Win32.windows?
|
|
623
|
-
end
|
|
624
|
-
end
|
|
625
|
-
|
|
626
|
-
class JoinSet < Set
|
|
627
|
-
def self.to_s
|
|
628
|
-
super[/[^:]+\z/, 0]
|
|
46
|
+
def slice!(*args)
|
|
47
|
+
data = compact
|
|
48
|
+
data.slice!(*args).tap { replace Set.new(data) }
|
|
629
49
|
end
|
|
630
50
|
|
|
631
|
-
|
|
632
|
-
|
|
633
|
-
def initialize(data = [], delim: ' ')
|
|
634
|
-
super(data.compact)
|
|
635
|
-
@delim = delim
|
|
51
|
+
def compact
|
|
52
|
+
to_ary.map!(&:to_s).reject(&:empty?)
|
|
636
53
|
end
|
|
637
54
|
|
|
638
55
|
def last(val, pat)
|
|
@@ -641,7 +58,7 @@ module Squared
|
|
|
641
58
|
end
|
|
642
59
|
|
|
643
60
|
def pass(&blk)
|
|
644
|
-
ret =
|
|
61
|
+
ret = compact
|
|
645
62
|
@last&.each do |val, pat, key|
|
|
646
63
|
items = []
|
|
647
64
|
index = nil
|
|
@@ -662,6 +79,7 @@ module Squared
|
|
|
662
79
|
end
|
|
663
80
|
ret[items.last] = val
|
|
664
81
|
end
|
|
82
|
+
ret.concat(extras.map(&:to_s).reject(&:empty?)) unless extras.empty?
|
|
665
83
|
return ret unless block_given?
|
|
666
84
|
|
|
667
85
|
ret.reject(&blk)
|
|
@@ -683,18 +101,72 @@ module Squared
|
|
|
683
101
|
|
|
684
102
|
def temp(*args, &blk)
|
|
685
103
|
args.compact!
|
|
686
|
-
|
|
687
|
-
|
|
688
|
-
|
|
104
|
+
pass(&blk)
|
|
105
|
+
.concat(args)
|
|
106
|
+
.join(@delim)
|
|
689
107
|
end
|
|
690
108
|
|
|
691
109
|
def done
|
|
692
110
|
to_s.tap { clear }
|
|
693
111
|
end
|
|
694
112
|
|
|
113
|
+
def merge(enum)
|
|
114
|
+
if !extras.empty?
|
|
115
|
+
extras.concat(enum.to_a)
|
|
116
|
+
self
|
|
117
|
+
elsif (n = enum.find_index { |val| extras?(val) })
|
|
118
|
+
data = enum.to_a
|
|
119
|
+
@extras = if n == 0
|
|
120
|
+
data
|
|
121
|
+
else
|
|
122
|
+
super(data[0...n])
|
|
123
|
+
data[n..-1]
|
|
124
|
+
end
|
|
125
|
+
self
|
|
126
|
+
else
|
|
127
|
+
super
|
|
128
|
+
end
|
|
129
|
+
end
|
|
130
|
+
|
|
131
|
+
def <<(obj)
|
|
132
|
+
return super if extras.empty? && !extras?(obj)
|
|
133
|
+
|
|
134
|
+
unless !extras.include?(@partition) && include?(obj) && @uniq.match?(s = obj.to_s) && !multiple.include?(s)
|
|
135
|
+
extras << obj
|
|
136
|
+
end
|
|
137
|
+
self
|
|
138
|
+
end
|
|
139
|
+
|
|
140
|
+
def to_a
|
|
141
|
+
pass
|
|
142
|
+
end
|
|
143
|
+
|
|
695
144
|
def to_s
|
|
696
145
|
pass.join(@delim)
|
|
697
146
|
end
|
|
147
|
+
|
|
148
|
+
def to_enum(*args)
|
|
149
|
+
pass.to_enum(*args)
|
|
150
|
+
end
|
|
151
|
+
|
|
152
|
+
def to_json(*args)
|
|
153
|
+
pass.to_json(*args)
|
|
154
|
+
end
|
|
155
|
+
|
|
156
|
+
def to_yaml(*args)
|
|
157
|
+
pass.to_yaml(*args)
|
|
158
|
+
end
|
|
159
|
+
|
|
160
|
+
alias add :<<
|
|
161
|
+
alias add? :<<
|
|
162
|
+
alias push :<<
|
|
163
|
+
alias concat merge
|
|
164
|
+
|
|
165
|
+
private
|
|
166
|
+
|
|
167
|
+
def extras?(obj)
|
|
168
|
+
obj == @partition || (include?(obj) && (!@uniq.match?(s = obj.to_s) || multiple.include?(s)))
|
|
169
|
+
end
|
|
698
170
|
end
|
|
699
171
|
end
|
|
700
172
|
end
|