attestor 2.1.0 → 2.2.0

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 0ed10bee06c2caea561384393fd3c3a09d8548aa
4
- data.tar.gz: 4a808081721ac3ce602ebcb26c1a733878189112
3
+ metadata.gz: a3c49413757098c3a6f07dc1148d09e0e5c5abe5
4
+ data.tar.gz: e28e906e513608a83ee9d43903a14d8c4887f23d
5
5
  SHA512:
6
- metadata.gz: f2ebc2cd9437e77946faf52f458fe719daa70a8cc9baeda2d33a16e31f5dfd34cdf3c9e588f4199f3e749e8bc29f9eee738936a7d70c688d620ad69d32b037b0
7
- data.tar.gz: 36c544456aa601a9b87bbd50568eb27253a866853b06081e714651e7acd37e2f6fdb622827bd55952c250f5cbbb1304f21b13a41d2d53ceb72321857c950b963
6
+ metadata.gz: 01204cc6953c5a0d06f65f0d568ea9259ab2e6a15d3e5945d353d67e4bfa14f40b1f822962939d3e7f6b1942a1fb7bb15354a72849cc4bc8a052e798ef43e791
7
+ data.tar.gz: dd468cf1fd35facc245a6e142e745282ed856d9c2eacce6ddecbff27d82d1c3fb1395f0d426bfbb644baac368e5c3c2db31cf053a4d2fbf1adf2770e9697c8bb
data/README.md CHANGED
@@ -170,6 +170,22 @@ class Transfer
170
170
  end
171
171
  ```
172
172
 
173
+ You can group validations that uses shared context:
174
+
175
+ ```ruby
176
+ class Transfer
177
+
178
+ # This is the same as:
179
+ #
180
+ # validate :consistent, only: :fair_trade
181
+ # validate :limited, only: :fair_trade
182
+ validations only: :fair_trade do
183
+ validate :consistent
184
+ validate :limited
185
+ end
186
+ end
187
+ ```
188
+
173
189
  Delegation
174
190
  ----------
175
191
 
@@ -13,6 +13,7 @@ require_relative "attestor/validations/validator"
13
13
  require_relative "attestor/validations/delegator"
14
14
  require_relative "attestor/validations/validators"
15
15
  require_relative "attestor/validations/message"
16
+ require_relative "attestor/validations/context"
16
17
 
17
18
  require_relative "attestor/policy/factory"
18
19
  require_relative "attestor/policy"
@@ -2,7 +2,7 @@
2
2
 
3
3
  module Attestor
4
4
 
5
- # API for policies that validates another objects
5
+ # API for policies that validate another objects
6
6
  module Policy
7
7
  # @!parse include Attestor::Validations
8
8
  # @!parse extend Attestor::Validations::ClassMethods
@@ -8,6 +8,8 @@ module Attestor
8
8
  include ::RSpec::Mocks::ExampleMethods
9
9
 
10
10
  # Mocks a valid object
11
+ #
12
+ # @return [RSpec::Mocks::Double]
11
13
  def valid_spy
12
14
  object = spy
13
15
  allow(object).to receive(:validate!)
@@ -16,7 +18,11 @@ module Attestor
16
18
  object
17
19
  end
18
20
 
19
- # Mocks an invalid object
21
+ # Mocks an invalid object with given error messages
22
+ #
23
+ # @param [String, Array<String>] messages
24
+ #
25
+ # @return [RSpec::Mocks::Double]
20
26
  def invalid_spy(messages = "invalid")
21
27
  object = spy
22
28
  error = InvalidError.new(object, messages)
@@ -111,6 +111,27 @@ module Attestor
111
111
  @validators = validators.add_delegator(*args, &block)
112
112
  end
113
113
 
114
+ # Groups validations assigned to shared context
115
+ #
116
+ # @example
117
+ # validations only: :foo do
118
+ # validates :bar
119
+ # validate { invalid :foo unless baz }
120
+ # end
121
+ #
122
+ # # this is equal to:
123
+ #
124
+ # validates :bar, only: :foo
125
+ # validate { invalid :foo unless baz }, only: :foo
126
+ #
127
+ # @param [Hash] options
128
+ # @param [Proc] block
129
+ #
130
+ # @return [undefined]
131
+ def validations(**options, &block)
132
+ Context.new(self, options).instance_eval(&block) if block_given?
133
+ end
134
+
114
135
  end # module ClassMethods
115
136
 
116
137
  # @private
@@ -0,0 +1,29 @@
1
+ # encoding: utf-8
2
+
3
+ module Attestor
4
+
5
+ module Validations
6
+
7
+ # @private
8
+ class Context
9
+
10
+ attr_accessor :klass, :options
11
+
12
+ def initialize(klass, options)
13
+ self.klass = klass
14
+ self.options = options
15
+ end
16
+
17
+ def validate(name = nil, &block)
18
+ klass.validate(name, options, &block)
19
+ end
20
+
21
+ def validates(name = nil, &block)
22
+ klass.validates(name, options, &block)
23
+ end
24
+
25
+ end # class Context
26
+
27
+ end # module Validations
28
+
29
+ end # module Attestor
@@ -4,6 +4,6 @@ module Attestor
4
4
 
5
5
  # The semantic version of the module.
6
6
  # @see http://semver.org/ Semantic versioning 2.0
7
- VERSION = "2.1.0".freeze
7
+ VERSION = "2.2.0".freeze
8
8
 
9
9
  end # module Attestor
@@ -0,0 +1,59 @@
1
+ # encoding: utf-8
2
+
3
+ describe Attestor::Validations::Context do
4
+
5
+ let(:klass) { double validate: nil, validates: nil }
6
+ let(:options) { { except: :foo, only: :bar } }
7
+ let(:name) { :baz }
8
+ let(:block) { proc { :foo } }
9
+ subject { described_class.new klass, options }
10
+
11
+ describe "#klass" do
12
+
13
+ it "is initialized" do
14
+ expect(subject.klass).to eq klass
15
+ end
16
+
17
+ end # describe #klass
18
+
19
+ describe "#options" do
20
+
21
+ it "is initialized" do
22
+ expect(subject.options).to eq options
23
+ end
24
+
25
+ end # describe #options
26
+
27
+ describe "#validate" do
28
+
29
+ it "is delegated to klass with name and options" do
30
+ expect(klass).to receive(:validate).with(name, **options)
31
+ subject.validate name
32
+ end
33
+
34
+ it "is delegated to klass with a block" do
35
+ expect(klass).to receive(:validate) do |*, &b|
36
+ expect(b).to eq block
37
+ end
38
+ subject.validate(&block)
39
+ end
40
+
41
+ end # describe #validate
42
+
43
+ describe "#validates" do
44
+
45
+ it "is delegated to klass with name and options" do
46
+ expect(klass).to receive(:validates).with(name, **options)
47
+ subject.validates name
48
+ end
49
+
50
+ it "is delegated to klass with a block" do
51
+ expect(klass).to receive(:validates) do |*, &b|
52
+ expect(b).to eq block
53
+ end
54
+ subject.validates(&block)
55
+ end
56
+
57
+ end # describe #validates
58
+
59
+ end # describe Attestor::Validations::Context
@@ -129,6 +129,39 @@ describe Attestor::Validations do
129
129
 
130
130
  end # describe .validates
131
131
 
132
+ describe ".validations" do
133
+
134
+ let(:options) { { only: :bar, except: :baz } }
135
+ let(:context_class) { Attestor::Validations::Context }
136
+ let(:context) { double validate: nil, validates: nil }
137
+ before { allow(context_class).to receive(:new) { context } }
138
+
139
+ context "with a block" do
140
+
141
+ after { test_class.validations(options) { validate :foo } }
142
+
143
+ it "initializes a context group" do
144
+ expect(context_class).to receive(:new).with(test_class, options)
145
+ end
146
+
147
+ it "calls the block in a context's scope" do
148
+ expect(context).to receive(:validate).with(:foo)
149
+ end
150
+
151
+ end # context
152
+
153
+ context "without a block" do
154
+
155
+ after { test_class.validations(options) }
156
+
157
+ it "does nothing" do
158
+ expect(context_class).not_to receive(:new)
159
+ end
160
+
161
+ end # context
162
+
163
+ end # describe .validations
164
+
132
165
  describe "#invalid" do
133
166
 
134
167
  shared_examples "raising an error" do |name, options = {}|
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: attestor
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.1.0
4
+ version: 2.2.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Andrew Kozin
@@ -14,28 +14,28 @@ dependencies:
14
14
  name: extlib
15
15
  requirement: !ruby/object:Gem::Requirement
16
16
  requirements:
17
- - - "~>"
17
+ - - ~>
18
18
  - !ruby/object:Gem::Version
19
19
  version: '0.9'
20
20
  type: :runtime
21
21
  prerelease: false
22
22
  version_requirements: !ruby/object:Gem::Requirement
23
23
  requirements:
24
- - - "~>"
24
+ - - ~>
25
25
  - !ruby/object:Gem::Version
26
26
  version: '0.9'
27
27
  - !ruby/object:Gem::Dependency
28
28
  name: hexx-rspec
29
29
  requirement: !ruby/object:Gem::Requirement
30
30
  requirements:
31
- - - "~>"
31
+ - - ~>
32
32
  - !ruby/object:Gem::Version
33
33
  version: '0.4'
34
34
  type: :development
35
35
  prerelease: false
36
36
  version_requirements: !ruby/object:Gem::Requirement
37
37
  requirements:
38
- - - "~>"
38
+ - - ~>
39
39
  - !ruby/object:Gem::Version
40
40
  version: '0.4'
41
41
  description: Validations for immutable Ruby objects
@@ -46,13 +46,13 @@ extra_rdoc_files:
46
46
  - README.md
47
47
  - LICENSE
48
48
  files:
49
- - ".coveralls.yml"
50
- - ".gitignore"
51
- - ".metrics"
52
- - ".rspec"
53
- - ".rubocop.yml"
54
- - ".travis.yml"
55
- - ".yardopts"
49
+ - .coveralls.yml
50
+ - .gitignore
51
+ - .metrics
52
+ - .rspec
53
+ - .rubocop.yml
54
+ - .travis.yml
55
+ - .yardopts
56
56
  - Gemfile
57
57
  - Guardfile
58
58
  - LICENSE
@@ -83,6 +83,7 @@ files:
83
83
  - lib/attestor/report.rb
84
84
  - lib/attestor/rspec.rb
85
85
  - lib/attestor/validations.rb
86
+ - lib/attestor/validations/context.rb
86
87
  - lib/attestor/validations/delegator.rb
87
88
  - lib/attestor/validations/message.rb
88
89
  - lib/attestor/validations/reporter.rb
@@ -103,6 +104,7 @@ files:
103
104
  - spec/tests/policy_spec.rb
104
105
  - spec/tests/report_spec.rb
105
106
  - spec/tests/rspec_spec.rb
107
+ - spec/tests/validations/context_spec.rb
106
108
  - spec/tests/validations/delegator_spec.rb
107
109
  - spec/tests/validations/message_spec.rb
108
110
  - spec/tests/validations/reporter_spec.rb
@@ -119,12 +121,12 @@ require_paths:
119
121
  - lib
120
122
  required_ruby_version: !ruby/object:Gem::Requirement
121
123
  requirements:
122
- - - "~>"
124
+ - - ~>
123
125
  - !ruby/object:Gem::Version
124
126
  version: '2.0'
125
127
  required_rubygems_version: !ruby/object:Gem::Requirement
126
128
  requirements:
127
- - - ">="
129
+ - - '>='
128
130
  - !ruby/object:Gem::Version
129
131
  version: '0'
130
132
  requirements: []
@@ -139,6 +141,7 @@ test_files:
139
141
  - spec/tests/invalid_error_spec.rb
140
142
  - spec/tests/validations_spec.rb
141
143
  - spec/tests/report_spec.rb
144
+ - spec/tests/validations/context_spec.rb
142
145
  - spec/tests/validations/message_spec.rb
143
146
  - spec/tests/validations/validator_spec.rb
144
147
  - spec/tests/validations/reporter_spec.rb