validate-rb 0.1.0.alpha.1 → 1.0.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/lib/validate.rb +1 -0
- data/lib/validate/arguments.rb +29 -28
- data/lib/validate/ast.rb +17 -17
- data/lib/validate/compare.rb +49 -4
- data/lib/validate/constraint.rb +21 -7
- data/lib/validate/constraints.rb +175 -1
- data/lib/validate/constraints/validation_context.rb +25 -4
- data/lib/validate/errors.rb +3 -3
- data/lib/validate/version.rb +1 -1
- metadata +4 -4
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 2bac2b6ec6ca8d71becc3849cc26401c63a7939c2d9ee7618ccc022f5845080a
|
4
|
+
data.tar.gz: 995c743d5e16aa7a4239d0cd4e6eb500b6cd1541184eab44b7605c4f61494751
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 80bcb6b3ef21a26dd8d39f0dd4666b1185c65011a9dc3cc4e57af6cb9f6329abe7dc9a83fd8aa415e2490d920f7dbdd2b1e950c9838b93b879ca655888944ff0
|
7
|
+
data.tar.gz: d687a04ae9a0c0b8a40f3ec4f851583b0edbe2014003f25196b7463beded4c970d6060b0aa79b767e3bb84d46c777103410de5331292220ce026cdb5c08d9b22
|
data/lib/validate.rb
CHANGED
data/lib/validate/arguments.rb
CHANGED
@@ -3,32 +3,12 @@ module Validate
|
|
3
3
|
module ClassMethods
|
4
4
|
def method_added(method_name)
|
5
5
|
super
|
6
|
-
|
7
|
-
|
8
|
-
method = instance_method(method_name)
|
9
|
-
guard = ArgumentsGuard.new(method, @args.dup)
|
10
|
-
|
11
|
-
@methods_guard.__send__(:define_method, method_name) do |*args, &block|
|
12
|
-
guard.send(method_name, *args, &block)
|
13
|
-
super(*args, &block)
|
14
|
-
end
|
15
|
-
ensure
|
16
|
-
@args.clear
|
6
|
+
guard_method(instance_method(method_name), @methods_guard)
|
17
7
|
end
|
18
8
|
|
19
9
|
def singleton_method_added(method_name)
|
20
10
|
super
|
21
|
-
|
22
|
-
|
23
|
-
method = singleton_method(method_name)
|
24
|
-
guard = ArgumentsGuard.new(method, @args.dup)
|
25
|
-
|
26
|
-
@methods_guard.__send__(:define_singleton_method, method_name) do |*args, &block|
|
27
|
-
guard.send(method_name, *args, &block)
|
28
|
-
super(*args, &block)
|
29
|
-
end
|
30
|
-
ensure
|
31
|
-
@args.clear
|
11
|
+
guard_method(singleton_method(method_name), @singleton_methods_guard)
|
32
12
|
end
|
33
13
|
|
34
14
|
def arg(name, &body)
|
@@ -39,6 +19,24 @@ module Validate
|
|
39
19
|
@args[name] = Assertions.create(&body)
|
40
20
|
self
|
41
21
|
end
|
22
|
+
|
23
|
+
private
|
24
|
+
|
25
|
+
def guard_method(method, guard_module)
|
26
|
+
return if @args.empty?
|
27
|
+
guard = ArgumentsGuard.new(method, @args)
|
28
|
+
guard_module.__send__(:define_method, method.name) do |*args, **kwargs, &block|
|
29
|
+
if kwargs.empty?
|
30
|
+
guard.enforce!(*args, &block)
|
31
|
+
super(*args, &block)
|
32
|
+
else
|
33
|
+
guard.enforce!(*args, **kwargs, &block)
|
34
|
+
super(*args, **kwargs, &block)
|
35
|
+
end
|
36
|
+
end
|
37
|
+
ensure
|
38
|
+
@args = {}
|
39
|
+
end
|
42
40
|
end
|
43
41
|
|
44
42
|
def self.included(base)
|
@@ -46,6 +44,7 @@ module Validate
|
|
46
44
|
base.instance_exec do
|
47
45
|
@args = {}
|
48
46
|
prepend(@methods_guard = Module.new)
|
47
|
+
singleton_class.prepend(@singleton_methods_guard = Module.new)
|
49
48
|
end
|
50
49
|
end
|
51
50
|
|
@@ -73,17 +72,19 @@ module Validate
|
|
73
72
|
when :block
|
74
73
|
signature << "&#{name}"
|
75
74
|
else
|
76
|
-
raise Error::ArgumentError,
|
75
|
+
raise Error::ArgumentError,
|
76
|
+
"unsupported parameter type #{kind}"
|
77
77
|
end
|
78
78
|
next unless rules.include?(name)
|
79
79
|
|
80
|
-
assertions <<
|
80
|
+
assertions <<
|
81
|
+
"@rules[:#{name}].assert(#{name}, message: '#{name}') unless #{name}.eql?(DEFAULT_VALUE)"
|
81
82
|
end
|
82
83
|
|
83
|
-
singleton_class.class_eval(<<~RUBY, __FILE__, __LINE__
|
84
|
-
|
85
|
-
|
86
|
-
|
84
|
+
singleton_class.class_eval(<<~RUBY, __FILE__, __LINE__)
|
85
|
+
def enforce!(#{signature.join(', ')})
|
86
|
+
#{assertions.join("\n ")}
|
87
|
+
end
|
87
88
|
RUBY
|
88
89
|
|
89
90
|
@rules = rules
|
data/lib/validate/ast.rb
CHANGED
@@ -5,8 +5,8 @@ module Validate
|
|
5
5
|
module AST
|
6
6
|
def self.build(*args, &block)
|
7
7
|
Generator.new
|
8
|
-
|
9
|
-
|
8
|
+
.generate(*args, &block)
|
9
|
+
.freeze
|
10
10
|
end
|
11
11
|
|
12
12
|
class DefinitionContext
|
@@ -65,8 +65,8 @@ module Validate
|
|
65
65
|
|
66
66
|
def evaluate(ctx)
|
67
67
|
@constraints.each_value
|
68
|
-
|
69
|
-
|
68
|
+
.reject { |c| catch(:pending) { c.valid?(ctx.value, ctx) } }
|
69
|
+
.each { |c| ctx.add_violation(c) }
|
70
70
|
ctx
|
71
71
|
end
|
72
72
|
end
|
@@ -156,7 +156,7 @@ module Validate
|
|
156
156
|
args.map { |arg| [:value, arg] },
|
157
157
|
block,
|
158
158
|
::Kernel.caller
|
159
|
-
|
159
|
+
.reject { |line| line.include?(__FILE__) }
|
160
160
|
]
|
161
161
|
self
|
162
162
|
end
|
@@ -286,10 +286,10 @@ module Validate
|
|
286
286
|
|
287
287
|
def message
|
288
288
|
'both ' + @constraints
|
289
|
-
|
290
|
-
|
291
|
-
|
292
|
-
|
289
|
+
.size
|
290
|
+
.times
|
291
|
+
.map { |i| "[#{constraint_message(i)}]" }
|
292
|
+
.join(', and ')
|
293
293
|
end
|
294
294
|
end
|
295
295
|
|
@@ -327,10 +327,10 @@ module Validate
|
|
327
327
|
|
328
328
|
def message
|
329
329
|
'either ' + @constraints
|
330
|
-
|
331
|
-
|
332
|
-
|
333
|
-
|
330
|
+
.size
|
331
|
+
.times
|
332
|
+
.map { |i| "[#{constraint_message(i)}]" }
|
333
|
+
.join(', or ')
|
334
334
|
end
|
335
335
|
end
|
336
336
|
|
@@ -364,10 +364,10 @@ module Validate
|
|
364
364
|
return "not [#{constraint_message(0)}]" if @constraints.one?
|
365
365
|
|
366
366
|
'neither ' + @constraints
|
367
|
-
|
368
|
-
|
369
|
-
|
370
|
-
|
367
|
+
.size
|
368
|
+
.times
|
369
|
+
.map { |i| "[#{constraint_message(i)}]" }
|
370
|
+
.join(', nor ')
|
371
371
|
end
|
372
372
|
|
373
373
|
def inspect
|
data/lib/validate/compare.rb
CHANGED
@@ -2,16 +2,34 @@
|
|
2
2
|
|
3
3
|
module Validate
|
4
4
|
module Compare
|
5
|
-
|
5
|
+
module TransformUsing
|
6
|
+
def using(&transform_block)
|
7
|
+
@transform_block = transform_block
|
8
|
+
self
|
9
|
+
end
|
10
|
+
|
11
|
+
def <=>(other)
|
12
|
+
return super if @transform_block.nil?
|
13
|
+
|
14
|
+
super(@transform_block.call(other))
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
class WithAttributes
|
6
19
|
include Comparable
|
20
|
+
prepend TransformUsing
|
7
21
|
|
8
22
|
def initialize(attributes)
|
9
23
|
@attributes = attributes
|
10
24
|
end
|
11
25
|
|
12
26
|
def <=>(other)
|
13
|
-
@attributes.
|
14
|
-
|
27
|
+
@attributes.each do |attribute, value|
|
28
|
+
result = value <=> other.send(attribute)
|
29
|
+
return result unless result.zero?
|
30
|
+
end
|
31
|
+
|
32
|
+
0
|
15
33
|
end
|
16
34
|
|
17
35
|
def method_missing(symbol, *args)
|
@@ -23,12 +41,39 @@ module Validate
|
|
23
41
|
def respond_to_missing?(attribute, _ = false)
|
24
42
|
@attributes.include?(attribute)
|
25
43
|
end
|
44
|
+
|
45
|
+
def to_s
|
46
|
+
'<attributes ' + @attributes.map { |attribute, value| "#{attribute}: #{value}"}
|
47
|
+
.join(', ') + '>'
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
class ToValue
|
52
|
+
include Comparable
|
53
|
+
prepend TransformUsing
|
54
|
+
|
55
|
+
def initialize(value_block)
|
56
|
+
@value_block = value_block
|
57
|
+
end
|
58
|
+
|
59
|
+
def <=>(other)
|
60
|
+
@value_block.call <=> other
|
61
|
+
end
|
62
|
+
|
63
|
+
def to_s
|
64
|
+
'<dynamic value>'
|
65
|
+
end
|
26
66
|
end
|
27
67
|
|
28
68
|
module_function
|
29
69
|
|
30
70
|
def attributes(**attributes)
|
31
|
-
|
71
|
+
WithAttributes.new(attributes)
|
72
|
+
end
|
73
|
+
|
74
|
+
def to(value = nil, &value_block)
|
75
|
+
value_block ||= value.is_a?(Proc) ? value : proc { value }
|
76
|
+
ToValue.new(value_block)
|
32
77
|
end
|
33
78
|
end
|
34
79
|
end
|
data/lib/validate/constraint.rb
CHANGED
@@ -116,13 +116,27 @@ module Validate
|
|
116
116
|
expects_kwargs = true if kind == :keyrest
|
117
117
|
end
|
118
118
|
|
119
|
-
define_constraint_method(:initialize, initialize_block) do |*args,
|
120
|
-
|
121
|
-
|
122
|
-
|
123
|
-
|
119
|
+
define_constraint_method(:initialize, initialize_block) do |*args, &block|
|
120
|
+
if args.last.is_a?(Hash)
|
121
|
+
known_options, kwargs =
|
122
|
+
args.pop
|
123
|
+
.partition { |k, _| supported_options.include?(k) }
|
124
|
+
.map { |h| Hash[h] }
|
125
|
+
|
126
|
+
if !expects_kwargs && !kwargs.empty?
|
127
|
+
args << kwargs
|
128
|
+
kwargs = {}
|
129
|
+
end
|
124
130
|
|
125
|
-
|
131
|
+
if expects_kwargs
|
132
|
+
merged_options = {}.merge!(super(*args, **kwargs, &block), known_options)
|
133
|
+
else
|
134
|
+
args << kwargs unless kwargs.empty?
|
135
|
+
merged_options = {}.merge!(super(*args, &block), known_options)
|
136
|
+
end
|
137
|
+
else
|
138
|
+
merged_options = super(*args, &block)
|
139
|
+
end
|
126
140
|
|
127
141
|
options = supported_options.each_with_object({}) do |(n, opt), opts|
|
128
142
|
opts[n] = opt.get_or_default(merged_options)
|
@@ -130,7 +144,7 @@ module Validate
|
|
130
144
|
|
131
145
|
unless merged_options.empty?
|
132
146
|
raise Error::ArgumentError,
|
133
|
-
"
|
147
|
+
"unexpected options #{merged_options.inspect}"
|
134
148
|
end
|
135
149
|
|
136
150
|
@options = options.freeze
|
data/lib/validate/constraints.rb
CHANGED
@@ -20,7 +20,7 @@ module Validate
|
|
20
20
|
end
|
21
21
|
|
22
22
|
@reserved_names[name] = name
|
23
|
-
constraint_class = Constraint.create_class(name, defaults, &body)
|
23
|
+
constraint_class = Constraint.create_class(name, **defaults, &body)
|
24
24
|
Constraints.const_set(Helpers.camelize(name), constraint_class)
|
25
25
|
define_method(name, &constraint_class.method(:new))
|
26
26
|
module_function(name)
|
@@ -104,6 +104,40 @@ module Validate
|
|
104
104
|
key { "length_over_#{options[:min]}_under_#{options[:max]}" }
|
105
105
|
end
|
106
106
|
|
107
|
+
define(:bytesize, message: 'have byte length of %{constraint.describe_length}') do
|
108
|
+
option(:min) { respond_to(:>, message: 'min must respond to :>') }
|
109
|
+
option(:max) { respond_to(:<, message: 'max must respond to :<') }
|
110
|
+
|
111
|
+
initialize do |range = nil|
|
112
|
+
case range
|
113
|
+
when ::Range
|
114
|
+
{ min: range.min, max: range.max }
|
115
|
+
else
|
116
|
+
{ min: range, max: range }
|
117
|
+
end
|
118
|
+
end
|
119
|
+
evaluate do |value|
|
120
|
+
pass if value.nil?
|
121
|
+
fail unless value.respond_to?(:bytesize)
|
122
|
+
|
123
|
+
bytesize = value.bytesize
|
124
|
+
fail if (options[:min]&.> bytesize) || (options[:max]&.< bytesize)
|
125
|
+
end
|
126
|
+
|
127
|
+
def describe_length
|
128
|
+
if options[:max] == options[:min]
|
129
|
+
options[:max].to_s
|
130
|
+
elsif options[:max].nil?
|
131
|
+
"at least #{options[:min]}"
|
132
|
+
elsif options[:min].nil?
|
133
|
+
"at most #{options[:max]}"
|
134
|
+
else
|
135
|
+
"at least #{options[:min]} and at most #{options[:max]}"
|
136
|
+
end
|
137
|
+
end
|
138
|
+
key { "bytesize_over_#{options[:min]}_under_#{options[:max]}" }
|
139
|
+
end
|
140
|
+
|
107
141
|
define(:one_of, message: 'be %{constraint.describe_presence}') do
|
108
142
|
option(:values) do
|
109
143
|
respond_to(:include?, message: 'values must respond to :include?')
|
@@ -309,6 +343,146 @@ module Validate
|
|
309
343
|
end
|
310
344
|
end
|
311
345
|
|
346
|
+
define(:each_key, message: 'have keys') do
|
347
|
+
option(:constraints) do
|
348
|
+
not_nil(message: 'constraints are required')
|
349
|
+
is_a(AST::DefinitionContext, message: 'constraints must be a DefinitionContext')
|
350
|
+
end
|
351
|
+
|
352
|
+
initialize do |&block|
|
353
|
+
return {} if block.nil?
|
354
|
+
|
355
|
+
{ constraints: AST::DefinitionContext.create(&block) }
|
356
|
+
end
|
357
|
+
evaluate do |collection, ctx|
|
358
|
+
pass if collection.nil?
|
359
|
+
fail unless collection.respond_to?(:each_key)
|
360
|
+
|
361
|
+
constraints = options[:constraints]
|
362
|
+
collection.each_key do |key|
|
363
|
+
key_ctx = Constraints::ValidationContext.key(key)
|
364
|
+
constraints.evaluate(key_ctx)
|
365
|
+
ctx.merge(key_ctx) if key_ctx.has_violations?
|
366
|
+
end
|
367
|
+
end
|
368
|
+
end
|
369
|
+
|
370
|
+
define(:start_with, message: 'start with %{constraint.prefix}') do
|
371
|
+
option(:prefix) do
|
372
|
+
not_blank(message: 'prefix is required')
|
373
|
+
is_a(String, message: 'prefix must be a String')
|
374
|
+
end
|
375
|
+
|
376
|
+
initialize do |prefix = nil|
|
377
|
+
return {} if prefix.nil?
|
378
|
+
|
379
|
+
{ prefix: prefix }
|
380
|
+
end
|
381
|
+
evaluate do |value|
|
382
|
+
pass if value.nil?
|
383
|
+
fail unless value.respond_to?(:start_with?) && value.start_with?(options[:prefix])
|
384
|
+
end
|
385
|
+
key do
|
386
|
+
"start_with_#{options[:prefix]}"
|
387
|
+
end
|
388
|
+
end
|
389
|
+
|
390
|
+
define(:end_with, message: 'end with %{constraint.suffix}') do
|
391
|
+
option(:suffix) do
|
392
|
+
not_blank(message: 'suffix is required')
|
393
|
+
is_a(String, message: 'suffix must be a String')
|
394
|
+
end
|
395
|
+
|
396
|
+
initialize do |suffix = nil|
|
397
|
+
return {} if suffix.nil?
|
398
|
+
|
399
|
+
{ suffix: suffix }
|
400
|
+
end
|
401
|
+
evaluate do |value|
|
402
|
+
pass if value.nil?
|
403
|
+
fail unless value.respond_to?(:end_with?) && value.end_with?(options[:suffix])
|
404
|
+
end
|
405
|
+
key do
|
406
|
+
"end_with_#{options[:suffix]}"
|
407
|
+
end
|
408
|
+
end
|
409
|
+
|
410
|
+
define(:contain, message: 'contain %{constraint.substring}') do
|
411
|
+
option(:substring) do
|
412
|
+
not_blank(message: 'substring is required')
|
413
|
+
is_a(String, message: 'substring must be a String')
|
414
|
+
end
|
415
|
+
|
416
|
+
initialize do |substring = nil|
|
417
|
+
return {} if substring.nil?
|
418
|
+
|
419
|
+
{ substring: substring }
|
420
|
+
end
|
421
|
+
evaluate do |value|
|
422
|
+
pass if value.nil?
|
423
|
+
fail unless value.respond_to?(:include?) && value.include?(options[:substring])
|
424
|
+
end
|
425
|
+
key do
|
426
|
+
"contain_#{options[:substring]}"
|
427
|
+
end
|
428
|
+
end
|
429
|
+
|
430
|
+
define(:uuid, message: 'be a uuid') do
|
431
|
+
UUID_REGEXP = %r{\b\h{8}\b-\h{4}-\h{4}-\h{4}-\b\h{12}\b}
|
432
|
+
|
433
|
+
evaluate do |value|
|
434
|
+
pass if value.nil?
|
435
|
+
fail unless UUID_REGEXP.match?(value.to_s)
|
436
|
+
end
|
437
|
+
end
|
438
|
+
|
439
|
+
define(:hostname, message: 'be a hostname') do
|
440
|
+
HOSTNAME_REGEXP = URI::HOST
|
441
|
+
|
442
|
+
evaluate do |value|
|
443
|
+
pass if value.nil?
|
444
|
+
fail unless HOSTNAME_REGEXP.match?(value.to_s)
|
445
|
+
end
|
446
|
+
end
|
447
|
+
|
448
|
+
define(:uri, message: 'be a uri') do
|
449
|
+
option(:absolute, default: true) do
|
450
|
+
one_of([true, false], message: ':absolute must be true or false')
|
451
|
+
end
|
452
|
+
|
453
|
+
evaluate do |value|
|
454
|
+
pass if value.nil?
|
455
|
+
uri = begin
|
456
|
+
URI.parse(value)
|
457
|
+
rescue URI::Error
|
458
|
+
fail
|
459
|
+
end
|
460
|
+
fail unless options[:absolute] == uri.absolute?
|
461
|
+
end
|
462
|
+
end
|
463
|
+
|
464
|
+
define(:ip_address, message: 'be an ip address') do
|
465
|
+
option(:version, default: nil) do
|
466
|
+
one_of([:v4, :v6], message: 'must be a valid ip version')
|
467
|
+
end
|
468
|
+
|
469
|
+
initialize do |version = nil|
|
470
|
+
return {} if version.nil?
|
471
|
+
|
472
|
+
{ version: version }
|
473
|
+
end
|
474
|
+
evaluate do |value|
|
475
|
+
pass if value.nil?
|
476
|
+
addr = begin
|
477
|
+
IPAddr.new(value)
|
478
|
+
rescue IPAddr::Error
|
479
|
+
fail
|
480
|
+
end
|
481
|
+
version = options[:version]
|
482
|
+
fail unless version.nil? || addr.send(:"ip#{version}?")
|
483
|
+
end
|
484
|
+
end
|
485
|
+
|
312
486
|
define(
|
313
487
|
:unique,
|
314
488
|
message: 'have unique %{constraint.describe_unique_attribute}'
|
@@ -11,7 +11,12 @@ module Validate
|
|
11
11
|
new(value, Path.new, violations)
|
12
12
|
end
|
13
13
|
|
14
|
-
|
14
|
+
def self.key(key, violations = [])
|
15
|
+
new(key, Path.new([KeyPath.new(key)]), violations)
|
16
|
+
end
|
17
|
+
|
18
|
+
attr_reader :value, :violations
|
19
|
+
protected :violations
|
15
20
|
|
16
21
|
def initialize(value, path = Path.new, violations = [])
|
17
22
|
@value = value
|
@@ -61,8 +66,17 @@ module Validate
|
|
61
66
|
!@violations.empty?
|
62
67
|
end
|
63
68
|
|
64
|
-
def to_err
|
65
|
-
Error::ConstraintViolationError.new(@violations.freeze)
|
69
|
+
def to_err(backtrace = [])
|
70
|
+
err = Error::ConstraintViolationError.new(@violations.freeze)
|
71
|
+
err.set_backtrace(backtrace)
|
72
|
+
err
|
73
|
+
end
|
74
|
+
|
75
|
+
def merge(other)
|
76
|
+
other.violations.each do |violation|
|
77
|
+
@violations << Constraint::Violation.new(violation.value, @path.child(violation.path), violation.constraint)
|
78
|
+
end
|
79
|
+
self
|
66
80
|
end
|
67
81
|
|
68
82
|
private
|
@@ -87,7 +101,14 @@ module Validate
|
|
87
101
|
end
|
88
102
|
|
89
103
|
def child(path)
|
90
|
-
|
104
|
+
case path
|
105
|
+
when KeyPath, AttrPath
|
106
|
+
Path.new(@paths.dup << path)
|
107
|
+
when Path
|
108
|
+
Path.new(@paths.dup << path.to_a)
|
109
|
+
else
|
110
|
+
raise ArgumentError, 'invalid path'
|
111
|
+
end
|
91
112
|
end
|
92
113
|
|
93
114
|
def to_s
|
data/lib/validate/errors.rb
CHANGED
@@ -31,9 +31,9 @@ module Validate
|
|
31
31
|
|
32
32
|
def message
|
33
33
|
@violations.group_by(&:path)
|
34
|
-
|
35
|
-
|
36
|
-
|
34
|
+
.transform_values { |violations| violations.map(&:message) }
|
35
|
+
.map { |path, messages| "#{path}: #{messages.join(', ')}" }
|
36
|
+
.join("\n")
|
37
37
|
end
|
38
38
|
end
|
39
39
|
end
|
data/lib/validate/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: validate-rb
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 1.0.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Bulat Shakirzyanov
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2020-07-
|
11
|
+
date: 2020-07-29 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: aruba
|
@@ -150,9 +150,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
150
150
|
version: 2.3.0
|
151
151
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
152
152
|
requirements:
|
153
|
-
- - "
|
153
|
+
- - ">="
|
154
154
|
- !ruby/object:Gem::Version
|
155
|
-
version:
|
155
|
+
version: '0'
|
156
156
|
requirements: []
|
157
157
|
rubygems_version: 3.0.3
|
158
158
|
signing_key:
|