valligator 1.0.2 → 1.0.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/Gemfile +1 -2
- data/HISTORY.md +10 -2
- data/README.md +39 -29
- data/Rakefile +3 -1
- data/VERSION +1 -1
- data/lib/valligator.rb +81 -45
- data/lib/valligator_helper.rb +15 -1
- data/test/lib/valligator/errors_test.rb +82 -16
- data/test/lib/valligator/is_instance_of_test.rb +4 -4
- data/test/lib/valligator/speaks_test.rb +2 -2
- metadata +6 -6
- data/lib/version.rb +0 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 86beebd4198e35c0e7accf7e5ae49e8e100793f7
|
4
|
+
data.tar.gz: 3d1cf322859147e0c6e238cdc74b7d3a3a32f482
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 46e30c31a694e91f20d1488b32b619b08cd0e2aad583f7a6c20cf97d77d245c5f7299f60eccfb972e3ead9a0bdff20377949eae2c15b181de7e998b017b39799
|
7
|
+
data.tar.gz: 8a794b107f51b596f1bb3de90c280e3d1170db81ee9188b54a434f004fac43744028cc0ffcb46cb3d6718dd2d0388acb6570baa687d3932ec51443c19da74338
|
data/Gemfile
CHANGED
data/HISTORY.md
CHANGED
@@ -1,4 +1,12 @@
|
|
1
|
-
#### 1.0.
|
1
|
+
#### 1.0.3
|
2
|
+
- **is_instance_of** renamed to **is_kind_of**
|
3
|
+
- **is_not_instance_of** renamed to **is_not_kind_of**
|
4
|
+
- new helper method: Valligator::Helper#vh(Hash)
|
2
5
|
|
6
|
+
#### 1.0.2
|
3
7
|
- **is_instance_of** got alias **is_a**
|
4
|
-
- **is_not_instance_of** got alias **is_not_a**
|
8
|
+
- **is_not_instance_of** got alias **is_not_a**
|
9
|
+
|
10
|
+
#### 1.0.3
|
11
|
+
- **is_instance_of** renamed to **is_kind_of**
|
12
|
+
- **is_not_instance_of** renamed to **is_not_kind_of**
|
data/README.md
CHANGED
@@ -1,5 +1,4 @@
|
|
1
|
-
# Valligator
|
2
|
-
|
1
|
+
# Valligator [](https://travis-ci.org/konstantin-dzreev/valligator) [](https://rubygems.org/gems/valligator)
|
3
2
|
|
4
3
|
## Ruby objects validator
|
5
4
|
|
@@ -28,35 +27,48 @@ gem install valligator
|
|
28
27
|
|
29
28
|
## Statements
|
30
29
|
|
31
|
-
There are 3 validations (a.k.a. statements) that the Valligator supports:
|
30
|
+
There are 3 positive and 3 negative validations (a.k.a. statements) that the Valligator supports:
|
31
|
+
|
32
32
|
|
33
|
-
#### speaks
|
33
|
+
#### speaks, does_not_speak
|
34
34
|
|
35
35
|
```
|
36
36
|
testee.speaks(*methods)
|
37
37
|
testee.does_not_speak(*methods)
|
38
|
+
|
39
|
+
# a method to be tested can be included into the validation name:
|
40
|
+
testee.speaks_<method>
|
41
|
+
testee.does_not_speak_<method>
|
38
42
|
```
|
39
|
-
- _methods_
|
43
|
+
- _methods_ is a list of symbols
|
40
44
|
|
41
45
|
The validations passes when testee responds to all (or none in negative case) the methods from the list.
|
42
46
|
|
43
|
-
|
47
|
+
|
48
|
+
#### is_kind_of, is_not_kind_of
|
49
|
+
Aliases: **is_a** and **is_not_a**.
|
50
|
+
|
44
51
|
```
|
45
|
-
testee.
|
46
|
-
testee.
|
52
|
+
testee.is_kind_of(*classes)
|
53
|
+
testee.is_not_kind_of(*classes)
|
47
54
|
```
|
48
|
-
- _classes_ a list of ruby classes
|
55
|
+
- _classes_ is a list of ruby classes
|
49
56
|
|
50
57
|
The validations passes when testee is an instance of any class (or not an instance of all the classes in negative case).
|
51
58
|
|
52
|
-
**is_instance_of** and **is_not_instance_of** have aliases **is_a** and **is_not_a**
|
53
59
|
|
54
|
-
#### asserts,
|
60
|
+
#### asserts, asserts_not
|
61
|
+
Aliases: **is**, **has** and **is_not**, **does_not_have**. All of them are absolutely identical, you can use what ever sounds more grammatically correct: _is(:active?)_, _has(:apples)_, _asserts(:respond_to?, :foo)_, etc.
|
62
|
+
|
55
63
|
```
|
56
64
|
testee.asserts(method, *method_args, &block)
|
57
65
|
testee.asserts_not(method, *method_args, &block)
|
66
|
+
|
67
|
+
# a method to be tested can be included into the validation name:
|
68
|
+
testee.asserts_<method>(*method_args, &block)
|
69
|
+
testee.asserts_not_<method>(*method_args, &block)
|
58
70
|
```
|
59
|
-
- _method_ a method to be
|
71
|
+
- _method_ a method to be called on testee
|
60
72
|
- _method_args_ (optional) the method arguments
|
61
73
|
- _block_ (optional) a block to be invoked in the context of the _method_ response
|
62
74
|
|
@@ -75,9 +87,8 @@ If it does not sound clear, then it is something like this:
|
|
75
87
|
raise !!value.instance_eval { self == 10 }
|
76
88
|
```
|
77
89
|
|
78
|
-
I use _instance_eval_ so that the _value_ could be assessed as _self_, and one would not need to access it using standard block params definition
|
90
|
+
I use _instance_eval_ so that the _value_ could be assessed as _self_, and one would not need to access it using standard block params definition: {|value| value == 10 }.
|
79
91
|
|
80
|
-
**asserts** has two aliases: **is** and **has**. The negative form **asserts_not** also has its own clones: **is_not**, **does_not_have**. All the methods are absolutely identical, just use what ever sounds more grammatically correct: _is(:active?)_, _has(:apples)_, _asserts(:respond_to?, :foo)_, etc.
|
81
92
|
|
82
93
|
## Method chaining
|
83
94
|
|
@@ -89,25 +100,19 @@ Each statement, if it does not fail, returns an instance of the Valligator, so t
|
|
89
100
|
|
90
101
|
## Errors
|
91
102
|
|
92
|
-
When validation fails a Valligator::ValidationError is raised.
|
93
|
-
passed validations. If the validation above would fail on _is_a_ statement the error message wold look like:
|
103
|
+
When validation fails a Valligator::ValidationError is raised.
|
94
104
|
|
95
105
|
```
|
96
|
-
Valligator
|
97
|
-
|
98
|
-
|
99
|
-
but if it would fail on _has_ then the error would be
|
100
|
-
|
101
|
-
```
|
102
|
-
Valligator::ValidationError: at testee#1.is_a.is_not.has
|
106
|
+
Valligator.new(:foo).is_empty? #=>
|
107
|
+
Valligator::ValidationError: `testee#1': method `empty?' returned falsy value
|
103
108
|
```
|
104
109
|
|
105
110
|
You can provide a testee name when you instantiate a Valligator instance, and the name will be used in the error message instead of 'testee#x'
|
106
111
|
|
107
112
|
```
|
108
113
|
testee = Valligator.new('Very long string', 'Short', names: ['long', 'short'])
|
109
|
-
testee.is_a(String).has(:size){self > 10}
|
110
|
-
|
114
|
+
testee.is_a(String).has(:size){self > 10} #=>
|
115
|
+
Valligator::ValidationError: `short': method `size' returned falsy value
|
111
116
|
```
|
112
117
|
|
113
118
|
## Examples
|
@@ -126,15 +131,15 @@ Valligator.new(*testees).speaks(:to_s, :upcase) #=> OK
|
|
126
131
|
Validate that all testees have size == 3 and start with 'b' and they are Strings
|
127
132
|
```
|
128
133
|
testees = ['boo', 'bar', :baz]
|
129
|
-
Valligator.new(*testees).has(:size){self == 3}.has(:[], 0){self == 'b'}.is_a(String)
|
130
|
-
|
134
|
+
Valligator.new(*testees).has(:size){self == 3}.has(:[], 0){self == 'b'}.is_a(String) #=>
|
135
|
+
Valligator::ValidationError: `testee#3': should be Symbol
|
131
136
|
```
|
132
137
|
|
133
138
|
Validate that all hash values are Integers <= 2
|
134
139
|
```
|
135
140
|
h = { foo: 1, bar: 2, baz: 3 }
|
136
|
-
Valligator.new(*h.values, names: h.keys).is_a(Integer).asserts(:<= , 2)
|
137
|
-
|
141
|
+
Valligator.new(*h.values, names: h.keys).is_a(Integer).asserts(:<= , 2) #=>
|
142
|
+
Valligator::ValidationError: `baz': method `<=' returned falsy value
|
138
143
|
```
|
139
144
|
|
140
145
|
## More examples
|
@@ -245,6 +250,11 @@ end
|
|
245
250
|
rake test
|
246
251
|
```
|
247
252
|
|
253
|
+
## API contract
|
254
|
+
|
255
|
+
Until version 1.1.0 API contract is a subject to change
|
256
|
+
|
257
|
+
|
248
258
|
## License
|
249
259
|
|
250
260
|
[MIT](https://opensource.org/licenses/mit-license.php) <br/>
|
data/Rakefile
CHANGED
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
1.0.
|
1
|
+
1.0.3
|
data/lib/valligator.rb
CHANGED
@@ -1,7 +1,10 @@
|
|
1
|
+
require 'pathname'
|
1
2
|
require_relative 'valligator_helper'
|
2
3
|
|
3
4
|
class Valligator
|
4
|
-
|
5
|
+
VERSION = File.read(Pathname(__FILE__).dirname.join('../VERSION')).strip
|
6
|
+
|
7
|
+
Error = Class.new(StandardError)
|
5
8
|
ValidationError = Class.new(Error)
|
6
9
|
|
7
10
|
INFINITY = 1/0.0
|
@@ -19,7 +22,7 @@ class Valligator
|
|
19
22
|
#
|
20
23
|
# @example
|
21
24
|
# # validate that testee is an instance of String
|
22
|
-
# Valligator.new('foo').
|
25
|
+
# Valligator.new('foo').is_kind_of(String) #=> OK
|
23
26
|
#
|
24
27
|
# @example
|
25
28
|
# # validate that all testees respond to :to_s and :upcase methods
|
@@ -28,14 +31,14 @@ class Valligator
|
|
28
31
|
# @example
|
29
32
|
# # validate that all testees have size == 3 and start with 'b' and they are Strings
|
30
33
|
# testees = ['boo', 'bar', :baz]
|
31
|
-
# Valligator.new(*testees).has(:size){self == 3}.has(:[], 0){self == 'b'}.
|
32
|
-
# #=> Valligator::ValidationError: at `testee#3.has.has.
|
34
|
+
# Valligator.new(*testees).has(:size){self == 3}.has(:[], 0){self == 'b'}.is_kind_of(String)
|
35
|
+
# #=> Valligator::ValidationError: at `testee#3.has.has.is_kind_of'
|
33
36
|
#
|
34
37
|
# @example
|
35
38
|
# # validate that all hash values are Integers <= 2
|
36
39
|
# h = { foo: 1, bar: 2, baz: 3 }
|
37
|
-
# Valligator.new(*h.values, names: h.keys).
|
38
|
-
# #=> Valligator::ValidationError: at `baz.
|
40
|
+
# Valligator.new(*h.values, names: h.keys).is_kind_of(Integer).asserts(:<= , 2)
|
41
|
+
# #=> Valligator::ValidationError: at `baz.is_kind_of.asserts'
|
39
42
|
#
|
40
43
|
def initialize(*testees, names: nil)
|
41
44
|
@testees = testees
|
@@ -67,13 +70,13 @@ class Valligator
|
|
67
70
|
# @raise [Valligator::ValidationError]
|
68
71
|
#
|
69
72
|
# @example
|
70
|
-
# Valligator.new('foo').
|
71
|
-
# Valligator.new('foo').
|
73
|
+
# Valligator.new('foo').is_kind_of(Integer, String) #=> OK
|
74
|
+
# Valligator.new('foo').is_kind_of(Integer, Array) #=> Valligator::ValidationError
|
72
75
|
#
|
73
76
|
# @see #is_a
|
74
77
|
#
|
75
|
-
def
|
76
|
-
clone.
|
78
|
+
def is_kind_of(*classes)
|
79
|
+
clone._is_kind_of(__method__, *classes)
|
77
80
|
end
|
78
81
|
|
79
82
|
|
@@ -84,27 +87,27 @@ class Valligator
|
|
84
87
|
# @raise [Valligator::ValidationError]
|
85
88
|
#
|
86
89
|
# @example
|
87
|
-
# Valligator.new('foo').
|
88
|
-
# Valligator.new('foo').
|
90
|
+
# Valligator.new('foo').is_not_kind_of(Integer, String) #=> Valligator::ValidationError
|
91
|
+
# Valligator.new('foo').is_not_kind_of(Integer, Array) #=> OK
|
89
92
|
#
|
90
93
|
# @see #is_not_a
|
91
94
|
#
|
92
|
-
def
|
93
|
-
clone.
|
95
|
+
def is_not_kind_of(*classes)
|
96
|
+
clone._is_kind_of(__method__, *classes)
|
94
97
|
end
|
95
98
|
|
96
99
|
|
97
|
-
# Is an alias for {#
|
100
|
+
# Is an alias for {#is_kind_of} method
|
98
101
|
#
|
99
102
|
def is_a(*classes)
|
100
|
-
clone.
|
103
|
+
clone._is_kind_of(__method__, *classes)
|
101
104
|
end
|
102
105
|
|
103
106
|
|
104
|
-
# Is an alias for {#
|
107
|
+
# Is an alias for {#is_not_kind_of} method
|
105
108
|
#
|
106
109
|
def is_not_a(*classes)
|
107
|
-
clone.
|
110
|
+
clone._is_kind_of(__method__, *classes)
|
108
111
|
end
|
109
112
|
|
110
113
|
|
@@ -247,18 +250,6 @@ class Valligator
|
|
247
250
|
end
|
248
251
|
|
249
252
|
|
250
|
-
# Raises requested exception
|
251
|
-
#
|
252
|
-
# @param [Class] exception
|
253
|
-
# @param option [Integer] idx Testee index
|
254
|
-
# @param option [nil,String] msg Error explanation (when required)
|
255
|
-
#
|
256
|
-
def error(exception, idx=0, msg=nil)
|
257
|
-
msg += ' ' if msg
|
258
|
-
raise(exception, "%sat `%s.%s'" % [msg, name_by_idx(idx), @stack.join('.')])
|
259
|
-
end
|
260
|
-
|
261
|
-
|
262
253
|
# Calls the given block for each testee and each item from the list.
|
263
254
|
#
|
264
255
|
# @param optional list [Array]
|
@@ -292,10 +283,21 @@ class Valligator
|
|
292
283
|
|
293
284
|
|
294
285
|
#------------------------------------------
|
295
|
-
# Validations
|
286
|
+
# Validations and Errors
|
296
287
|
#------------------------------------------
|
297
288
|
|
298
289
|
|
290
|
+
# Raises ArgumentError exception
|
291
|
+
#
|
292
|
+
# @param [Class] exception
|
293
|
+
# @param [Integer] idx Testee index
|
294
|
+
# @param [nil,String] msg Error explanation (when required)
|
295
|
+
#
|
296
|
+
def argument_error(exception, idx, msg)
|
297
|
+
raise(exception, "%s at `%s.%s'" % [msg, name_by_idx(idx), @stack.join('.')])
|
298
|
+
end
|
299
|
+
|
300
|
+
|
299
301
|
# Validates number of arguments
|
300
302
|
#
|
301
303
|
# @param [Array<Object>] args
|
@@ -307,7 +309,7 @@ class Valligator
|
|
307
309
|
return if expected === args.size
|
308
310
|
|
309
311
|
expected == expected.first if expected.is_a?(Range) && expected.size == 1
|
310
|
-
|
312
|
+
argument_error(ArgumentError, 0, 'wrong number of arguments (%s for %s)' % [args.size, expected])
|
311
313
|
end
|
312
314
|
|
313
315
|
|
@@ -322,7 +324,7 @@ class Valligator
|
|
322
324
|
def validate_argument_type(classes, arg, arg_idx)
|
323
325
|
return if classes.any? { |klass| arg.is_a?(klass) }
|
324
326
|
classes = classes.map { |klass| klass.inspect }.join(' or ')
|
325
|
-
|
327
|
+
argument_error(ArgumentError, 0, 'wrong argument type (arg#%d is a %s instead of %s)' % [arg_idx, arg.class.name, classes])
|
326
328
|
end
|
327
329
|
|
328
330
|
|
@@ -338,19 +340,53 @@ class Valligator
|
|
338
340
|
return if object.respond_to?(method)
|
339
341
|
str = object.to_s
|
340
342
|
str = str[0..-1] + '...' if str.size > 20
|
341
|
-
|
343
|
+
argument_error(NoMethodError, idx, 'undefined method `%s\' for %s:%s' % [method, str, object.class.name])
|
344
|
+
end
|
345
|
+
|
346
|
+
|
347
|
+
# Raises ValidationError exception
|
348
|
+
#
|
349
|
+
# @param [Class] exception
|
350
|
+
# @param option [Integer] idx Testee index
|
351
|
+
# @param option [nil,String] msg Error explanation (when required)
|
352
|
+
#
|
353
|
+
def validation_error(idx, msg)
|
354
|
+
raise(ValidationError, "`%s': %s" % [name_by_idx(idx), msg])
|
355
|
+
end
|
356
|
+
|
357
|
+
|
358
|
+
def raise_is_kind_of_validation_error(equality, idx, classes)
|
359
|
+
validation_error(idx, "should not be %s" % [@testees[idx].class.name])
|
360
|
+
end
|
361
|
+
|
362
|
+
|
363
|
+
def raise_speaks_validation_error(equality, idx, method)
|
364
|
+
verb = equality ? "should" : "should not"
|
365
|
+
validation_error(idx, "%s respond to method `%s'" % [verb, method])
|
342
366
|
end
|
343
367
|
|
344
368
|
|
369
|
+
def raise_asserts_validation_error(equality, idx, method, args, block, error)
|
370
|
+
msg = "method `%s' " % method
|
371
|
+
if error
|
372
|
+
msg += 'failed: %s: %s' % [error.class.name, error.message]
|
373
|
+
else
|
374
|
+
msg += 'returned %s value' % (equality ? 'falsy' : 'truthy')
|
375
|
+
end
|
376
|
+
validation_error(idx, msg)
|
377
|
+
end
|
378
|
+
|
379
|
+
|
380
|
+
|
345
381
|
#------------------------------------------
|
346
382
|
# Statements
|
347
383
|
#------------------------------------------
|
348
384
|
|
349
385
|
|
350
386
|
# @private
|
351
|
-
# @see #
|
387
|
+
# @see #is_kind_of
|
352
388
|
#
|
353
|
-
def
|
389
|
+
def _is_kind_of(statement, *classes)
|
354
390
|
push(statement)
|
355
391
|
equality = !statement[/not/]
|
356
392
|
|
@@ -360,7 +396,10 @@ class Valligator
|
|
360
396
|
classes.each_with_index { |klass, idx| validate_argument_type([Class], klass, idx+1) }
|
361
397
|
|
362
398
|
each(*classes) { |testee, idx, klass| matches[idx] = true if testee.is_a?(klass) }
|
363
|
-
matches.each_with_index
|
399
|
+
matches.each_with_index do |match, idx|
|
400
|
+
next if matches[idx] == equality
|
401
|
+
raise_is_kind_of_validation_error(equality, idx, classes)
|
402
|
+
end
|
364
403
|
self
|
365
404
|
end
|
366
405
|
|
@@ -380,8 +419,7 @@ class Valligator
|
|
380
419
|
|
381
420
|
each(*methods) do |testee, idx, method|
|
382
421
|
next if testee.respond_to?(method) == equality
|
383
|
-
|
384
|
-
error(ValidationError, idx)
|
422
|
+
raise_speaks_validation_error(equality, idx, method)
|
385
423
|
end
|
386
424
|
self
|
387
425
|
end
|
@@ -396,15 +434,13 @@ class Valligator
|
|
396
434
|
|
397
435
|
each do |testee, idx|
|
398
436
|
validate_respond_to(testee, method, idx)
|
399
|
-
response = testee.__send__(method, *args)
|
400
437
|
begin
|
401
|
-
|
438
|
+
response = testee.__send__(method, *args)
|
402
439
|
response = response.instance_eval(&block) if block
|
403
|
-
rescue
|
404
|
-
|
405
|
-
error(ValidationError, idx)
|
440
|
+
rescue => e
|
441
|
+
response = !equality
|
406
442
|
end
|
407
|
-
|
443
|
+
raise_asserts_validation_error(equality, idx, method, args, block, e) if !!response != equality
|
408
444
|
end
|
409
445
|
self
|
410
446
|
end
|
data/lib/valligator_helper.rb
CHANGED
@@ -1,12 +1,26 @@
|
|
1
1
|
class Valligator
|
2
2
|
module Helper
|
3
3
|
|
4
|
+
# Returns a new Valligator instance
|
5
|
+
#
|
6
|
+
# @param [Array<Object>] testees One or more objects to be tested
|
7
|
+
# @param option [Array<String>] :names Testee names
|
8
|
+
# @return [Valligator]
|
9
|
+
#
|
4
10
|
def valligate(*testees, names: nil)
|
5
11
|
Valligator.new(*testees, names: names)
|
6
12
|
end
|
13
|
+
alias_method :v, :valligate
|
7
14
|
|
8
15
|
|
9
|
-
|
16
|
+
# Returns a new Valligator instance created from a hash, where hash values are testees and hash keys are their names.
|
17
|
+
#
|
18
|
+
# @param [Hash] hash
|
19
|
+
# @return [Valligator]
|
20
|
+
#
|
21
|
+
def vh(hash)
|
22
|
+
Valligator.new(*hash.values, names: hash.keys)
|
23
|
+
end
|
10
24
|
|
11
25
|
end
|
12
26
|
end
|
@@ -10,30 +10,96 @@ class TestErrors < Minitest::Test
|
|
10
10
|
end
|
11
11
|
|
12
12
|
|
13
|
-
|
14
|
-
|
15
|
-
|
13
|
+
#-------------------------------------
|
14
|
+
# is_kind_of
|
15
|
+
#-------------------------------------
|
16
|
+
|
17
|
+
|
18
|
+
def test__is_kind_of__error__single
|
19
|
+
expected = "`testee#1': should not be Symbol"
|
20
|
+
err = assert_raises(error) { v(:foo).is_kind_of(String) }
|
21
|
+
assert_equal expected, err.message
|
22
|
+
end
|
23
|
+
|
24
|
+
|
25
|
+
def test__is_kind_of__error__multiple
|
26
|
+
expected = "`testee#1': should not be Symbol"
|
27
|
+
err = assert_raises(error) { v(:foo).is_kind_of(String, Hash, Array) }
|
28
|
+
assert_equal expected, err.message
|
29
|
+
end
|
30
|
+
|
31
|
+
|
32
|
+
def test__is_not_kind_of__error__single
|
33
|
+
expected = "`testee#1': should not be Symbol"
|
34
|
+
err = assert_raises(error) { v(:foo).is_not_kind_of(Symbol) }
|
16
35
|
assert_equal expected, err.message
|
17
36
|
end
|
18
37
|
|
19
38
|
|
20
|
-
def
|
21
|
-
expected = "
|
22
|
-
err = assert_raises(error) { v(:foo,
|
39
|
+
def test__is_not_kind_of__error__multiple
|
40
|
+
expected = "`testee#1': should not be Symbol"
|
41
|
+
err = assert_raises(error) { v(:foo).is_not_kind_of(Symbol, Hash, Array) }
|
23
42
|
assert_equal expected, err.message
|
24
43
|
end
|
25
44
|
|
26
45
|
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
46
|
+
#-------------------------------------
|
47
|
+
# speaks
|
48
|
+
#-------------------------------------
|
49
|
+
|
50
|
+
|
51
|
+
def test__speaks__error
|
52
|
+
expected = "`testee#1': should respond to method `bar'"
|
53
|
+
err = assert_raises(error) { v(:foo).speaks(:bar) }
|
54
|
+
assert_equal expected, err.message
|
55
|
+
end
|
56
|
+
|
57
|
+
|
58
|
+
def test__does_not_speak__error
|
59
|
+
expected = "`testee#1': should not respond to method `to_s'"
|
60
|
+
err = assert_raises(error) { v(:foo).does_not_speak(:to_s) }
|
61
|
+
assert_equal expected, err.message
|
62
|
+
end
|
63
|
+
|
64
|
+
|
65
|
+
#-------------------------------------
|
66
|
+
# asserts
|
67
|
+
#-------------------------------------
|
68
|
+
|
69
|
+
|
70
|
+
def test__asserts__error__without_block
|
71
|
+
expected = "`testee#1': method `empty?' returned falsy value"
|
72
|
+
err = assert_raises(error) { v(:foo).asserts(:empty?) }
|
73
|
+
assert_equal expected, err.message
|
74
|
+
end
|
75
|
+
|
76
|
+
def test__asserts__error__with_block
|
77
|
+
expected = "`testee#1': method `size' returned falsy value"
|
78
|
+
err = assert_raises(error) { v(:foo).asserts(:size) { false } }
|
79
|
+
assert_equal expected, err.message
|
80
|
+
end
|
81
|
+
|
82
|
+
def test__asserts__error__with_block_and_exception
|
83
|
+
expected = "`testee#1': method `size' failed: ZeroDivisionError: divided by 0"
|
84
|
+
err = assert_raises(error) { v(:foo).asserts(:size) { 1/0 } }
|
85
|
+
assert_equal expected, err.message
|
86
|
+
end
|
87
|
+
|
88
|
+
def test__asserts_not__error__without_block
|
89
|
+
expected = "`testee#1': method `size' returned truthy value"
|
90
|
+
err = assert_raises(error) { v(:foo).asserts_not(:size) }
|
91
|
+
assert_equal expected, err.message
|
92
|
+
end
|
93
|
+
|
94
|
+
def test__asserts_not__error__with_block
|
95
|
+
expected = "`testee#1': method `empty?' returned truthy value"
|
96
|
+
err = assert_raises(error) { v(:foo).asserts_not(:empty?) { true } }
|
97
|
+
assert_equal expected, err.message
|
98
|
+
end
|
99
|
+
|
100
|
+
def test__assertsnot__error__with_block_and_exception
|
101
|
+
expected = "`testee#1': method `empty?' failed: ZeroDivisionError: divided by 0"
|
102
|
+
err = assert_raises(error) { v(:foo).asserts_not(:empty?) { 1/0 } }
|
37
103
|
assert_equal expected, err.message
|
38
104
|
end
|
39
105
|
|
@@ -8,8 +8,8 @@ class TestIsInstanceOf < Minitest::Test
|
|
8
8
|
Valligator::ValidationError
|
9
9
|
end
|
10
10
|
|
11
|
-
positive_statements = [:
|
12
|
-
negative_statements = [:
|
11
|
+
positive_statements = [:is_kind_of, :is_a]
|
12
|
+
negative_statements = [:is_not_kind_of, :is_not_a]
|
13
13
|
all_statements = positive_statements + negative_statements
|
14
14
|
|
15
15
|
all_statements.each do |method|
|
@@ -21,8 +21,8 @@ class TestIsInstanceOf < Minitest::Test
|
|
21
21
|
|
22
22
|
|
23
23
|
define_method 'test_that__%s__fails_on_wrong_argument_type' % method do
|
24
|
-
expected = "wrong argument type (arg#1 is a
|
25
|
-
err = assert_raises(ArgumentError) { v(:a).send(method,
|
24
|
+
expected = "wrong argument type (arg#1 is a NilClass instead of Class) at `testee#1.%s'" % method
|
25
|
+
err = assert_raises(ArgumentError) { v(:a).send(method, nil) }
|
26
26
|
assert_equal expected, err.message
|
27
27
|
end
|
28
28
|
end
|
@@ -17,8 +17,8 @@ class TestSpeaks < Minitest::Test
|
|
17
17
|
|
18
18
|
|
19
19
|
def test_that__speaks__fails_on_wrong_argument_type
|
20
|
-
expected = "wrong argument type (arg#1 is a
|
21
|
-
err = assert_raises(ArgumentError) { v(:a).speaks(
|
20
|
+
expected = "wrong argument type (arg#1 is a NilClass instead of Symbol) at `testee#1.speaks'"
|
21
|
+
err = assert_raises(ArgumentError) { v(:a).speaks(nil) }
|
22
22
|
assert_equal expected, err.message
|
23
23
|
end
|
24
24
|
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: valligator
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 1.0.
|
4
|
+
version: 1.0.3
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Konstantin Dzreev
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2017-
|
11
|
+
date: 2017-10-04 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: minitest
|
@@ -51,7 +51,6 @@ files:
|
|
51
51
|
- VERSION
|
52
52
|
- lib/valligator.rb
|
53
53
|
- lib/valligator_helper.rb
|
54
|
-
- lib/version.rb
|
55
54
|
- test/lib/valligator/asserts_test.rb
|
56
55
|
- test/lib/valligator/errors_test.rb
|
57
56
|
- test/lib/valligator/is_instance_of_test.rb
|
@@ -59,7 +58,8 @@ files:
|
|
59
58
|
- test/lib/valligator/speaks_test.rb
|
60
59
|
- test/test_helper.rb
|
61
60
|
homepage: https://github.com/konstantin-dzreev/valligator
|
62
|
-
licenses:
|
61
|
+
licenses:
|
62
|
+
- MIT
|
63
63
|
metadata: {}
|
64
64
|
post_install_message:
|
65
65
|
rdoc_options: []
|
@@ -67,9 +67,9 @@ require_paths:
|
|
67
67
|
- lib
|
68
68
|
required_ruby_version: !ruby/object:Gem::Requirement
|
69
69
|
requirements:
|
70
|
-
- - "
|
70
|
+
- - "~>"
|
71
71
|
- !ruby/object:Gem::Version
|
72
|
-
version: '0'
|
72
|
+
version: '2.0'
|
73
73
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
74
74
|
requirements:
|
75
75
|
- - ">="
|
data/lib/version.rb
DELETED