domain_model 0.1.4 → 0.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.
data/Gemfile CHANGED
@@ -1,4 +1,2 @@
1
1
  source 'https://rubygems.org'
2
-
3
- # Specify your gem's dependencies in model.gemspec
4
2
  gemspec
data/domain_model.gemspec CHANGED
@@ -18,7 +18,7 @@ Gem::Specification.new do |spec|
18
18
  spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
19
19
  spec.require_paths = ["lib"]
20
20
 
21
- spec.add_development_dependency "bundler", "~> 1.3"
22
21
  spec.add_development_dependency "rake"
23
- spec.add_development_dependency "rspec", "~> 2.14"
22
+ spec.add_development_dependency "bundler", "~> 1.3"
23
+ spec.add_development_dependency "rspec", "~> 3.0"
24
24
  end
@@ -1,3 +1,3 @@
1
1
  module DomainModel
2
- VERSION = "0.1.4"
2
+ VERSION = "0.2.0"
3
3
  end
data/lib/domain_model.rb CHANGED
@@ -23,6 +23,30 @@ module DomainModel
23
23
  errors
24
24
  end
25
25
 
26
+ def flat_errors
27
+ errors = self.errors
28
+
29
+ self.class.fields.each do |field|
30
+ next unless field.validate?
31
+
32
+ value = self.send(field.name)
33
+
34
+ if !field.collection? && value.is_a?(DomainModel)
35
+ value.flat_errors.each { |k, v| errors.add(:"#{field.name}.#{k}", v) }
36
+ end
37
+
38
+ if field.collection? && value.is_a?(Enumerable)
39
+ value.each_with_index do |element, index|
40
+ if element.is_a?(DomainModel)
41
+ element.flat_errors.each { |k, v| errors.add(:"#{field.name}[#{index}].#{k}", v) }
42
+ end
43
+ end
44
+ end
45
+ end
46
+
47
+ errors
48
+ end
49
+
26
50
  def valid?
27
51
  errors.empty?
28
52
  end
@@ -161,23 +185,36 @@ module DomainModel
161
185
  end
162
186
 
163
187
  class ModelErrors
188
+ include Enumerable
189
+
164
190
  def initialize
165
191
  @hash = Hash.new
166
192
  end
167
193
 
168
194
  def add(field_name, error)
195
+ errors = Array(error)
196
+
197
+ return if errors.empty?
198
+
169
199
  @hash[field_name] ||= []
170
200
  @hash[field_name] += Array(error)
171
201
  end
172
202
 
173
203
  def [](field_name)
174
204
  @hash[field_name] || []
175
-
176
205
  end
177
206
 
178
207
  def empty?
179
208
  @hash.values.flatten.empty?
180
209
  end
210
+
211
+ def each(&block)
212
+ @hash.each(&block)
213
+ end
214
+
215
+ def fields
216
+ @hash.keys
217
+ end
181
218
  end
182
219
 
183
220
  class FieldErrors
@@ -201,6 +201,21 @@ describe DomainModel do
201
201
  expect(Client.new.errors).to be_empty
202
202
  end
203
203
 
204
+ it "does not include fields with no errors" do
205
+ define { field :field }
206
+ client = Client.new(:field => :wrong)
207
+
208
+ expect(client.errors.fields).to eq([])
209
+ end
210
+
211
+ it "is enumerable" do
212
+ define { field :field, :required => true }
213
+ client = Client.new
214
+
215
+ expect(client.errors.is_a?(Enumerable)).to eq(true)
216
+ expect(client.errors.entries).to eq([[:field, ["cannot be nil"]]])
217
+ end
218
+
204
219
  it "includes errors for incorrect types" do
205
220
  define { field :field, :type => String }
206
221
  client = Client.new(:field => :wrong)
@@ -351,6 +366,73 @@ describe DomainModel do
351
366
  end
352
367
  end
353
368
 
369
+ describe ".flat_errors" do
370
+ describe "associated DomainModels" do
371
+ subject do
372
+ name_class = Class.new do
373
+ include DomainModel
374
+
375
+ field :first, :required => true
376
+ field :last, :required => true
377
+ end
378
+
379
+ person_class = Class.new do
380
+ include DomainModel
381
+
382
+ field :name, :validate => true, :type => name_class
383
+ field :friends_names, :validate => true, :collection => true, :type => name_class
384
+ end
385
+
386
+ person_class.new({
387
+ :name => name_class.new,
388
+ :friends_names => [name_class.new]
389
+ })
390
+ end
391
+
392
+ it "includes associated models errors for scalar fields" do
393
+ expect(subject.flat_errors[:"name.first"]).to eq(["cannot be nil"])
394
+ end
395
+
396
+ it "includes associated models errors for collection fields" do
397
+ expect(subject.flat_errors[:"friends_names[0].first"]).to eq(["cannot be nil"])
398
+ end
399
+
400
+ it "does not raise exceptions if a scalar field not a DomainModel" do
401
+ subject.name = "WRONG"
402
+ expect { subject.flat_errors }.not_to raise_error
403
+ end
404
+
405
+ it "does not raise expections if a colleciton field is non-enumerable" do
406
+ subject.friends_names = 5
407
+ expect { subject.flat_errors }.not_to raise_error
408
+ end
409
+
410
+
411
+ it "does not raise expetions if an element of a Collection is not a DomainModel" do
412
+ subject.friends_names = ["WRONG"]
413
+ expect { subject.flat_errors }.not_to raise_error
414
+ end
415
+ end
416
+
417
+ it "does not attempt to retrieve errors from associated non-DomainModels" do
418
+ name_class = Class.new do
419
+ # Not a DomainModel
420
+ def valid?
421
+ false
422
+ end
423
+ end
424
+
425
+ person_class = Class.new do
426
+ include DomainModel
427
+
428
+ field :name, :validate => true, :type => name_class
429
+ end
430
+
431
+ person = person_class.new(:name => name_class.new)
432
+ expect(person.errors.fields).to eq([:name])
433
+ end
434
+ end
435
+
354
436
  describe "#==" do
355
437
  before { define { field :field } }
356
438
 
metadata CHANGED
@@ -1,57 +1,64 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: domain_model
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.4
4
+ version: 0.2.0
5
+ prerelease:
5
6
  platform: ruby
6
7
  authors:
7
8
  - Rafer Hazen
8
9
  autorequire:
9
10
  bindir: bin
10
11
  cert_chain: []
11
- date: 2014-09-19 00:00:00.000000000 Z
12
+ date: 2015-02-11 00:00:00.000000000 Z
12
13
  dependencies:
13
14
  - !ruby/object:Gem::Dependency
14
- name: bundler
15
+ name: rake
15
16
  requirement: !ruby/object:Gem::Requirement
17
+ none: false
16
18
  requirements:
17
- - - ~>
19
+ - - ! '>='
18
20
  - !ruby/object:Gem::Version
19
- version: '1.3'
21
+ version: '0'
20
22
  type: :development
21
23
  prerelease: false
22
24
  version_requirements: !ruby/object:Gem::Requirement
25
+ none: false
23
26
  requirements:
24
- - - ~>
27
+ - - ! '>='
25
28
  - !ruby/object:Gem::Version
26
- version: '1.3'
29
+ version: '0'
27
30
  - !ruby/object:Gem::Dependency
28
- name: rake
31
+ name: bundler
29
32
  requirement: !ruby/object:Gem::Requirement
33
+ none: false
30
34
  requirements:
31
- - - ! '>='
35
+ - - ~>
32
36
  - !ruby/object:Gem::Version
33
- version: '0'
37
+ version: '1.3'
34
38
  type: :development
35
39
  prerelease: false
36
40
  version_requirements: !ruby/object:Gem::Requirement
41
+ none: false
37
42
  requirements:
38
- - - ! '>='
43
+ - - ~>
39
44
  - !ruby/object:Gem::Version
40
- version: '0'
45
+ version: '1.3'
41
46
  - !ruby/object:Gem::Dependency
42
47
  name: rspec
43
48
  requirement: !ruby/object:Gem::Requirement
49
+ none: false
44
50
  requirements:
45
51
  - - ~>
46
52
  - !ruby/object:Gem::Version
47
- version: '2.14'
53
+ version: '3.0'
48
54
  type: :development
49
55
  prerelease: false
50
56
  version_requirements: !ruby/object:Gem::Requirement
57
+ none: false
51
58
  requirements:
52
59
  - - ~>
53
60
  - !ruby/object:Gem::Version
54
- version: '2.14'
61
+ version: '3.0'
55
62
  description: Minimal framework for definition of (optionally) type-aware domain models
56
63
  email:
57
64
  - rafer@ralua.com
@@ -72,26 +79,27 @@ files:
72
79
  homepage: ''
73
80
  licenses:
74
81
  - MIT
75
- metadata: {}
76
82
  post_install_message:
77
83
  rdoc_options: []
78
84
  require_paths:
79
85
  - lib
80
86
  required_ruby_version: !ruby/object:Gem::Requirement
87
+ none: false
81
88
  requirements:
82
89
  - - ! '>='
83
90
  - !ruby/object:Gem::Version
84
91
  version: '0'
85
92
  required_rubygems_version: !ruby/object:Gem::Requirement
93
+ none: false
86
94
  requirements:
87
95
  - - ! '>='
88
96
  - !ruby/object:Gem::Version
89
97
  version: '0'
90
98
  requirements: []
91
99
  rubyforge_project:
92
- rubygems_version: 2.3.0
100
+ rubygems_version: 1.8.23.2
93
101
  signing_key:
94
- specification_version: 4
102
+ specification_version: 3
95
103
  summary: Minimal framework for definition of (optionally) type-aware domain models
96
104
  test_files:
97
105
  - spec/domain_model_spec.rb
checksums.yaml DELETED
@@ -1,15 +0,0 @@
1
- ---
2
- !binary "U0hBMQ==":
3
- metadata.gz: !binary |-
4
- OGVkNWYxNzY4NDEyOThhMDM3NDY5MDM5YmQzNGRmNDFjYjBmYTcwMA==
5
- data.tar.gz: !binary |-
6
- MjQxZWFkZmZjZmY5ZmI3N2RkNWM2M2I3Y2YzODAyMGNhMGNlZjU3Ng==
7
- SHA512:
8
- metadata.gz: !binary |-
9
- ODNlMDk1Y2M5NTlhOTZhODM1NDE2MDg4NmYzMTA4ODU1YTM2ZjVhODJmY2Fi
10
- MTBlMGJjNjZmMDY4NzRjZWMxZmEzZDE2N2Y4ODgyZDc0MmU4N2RjNTlkZWZj
11
- NTZlMTFhNjMyMmE1NTQ3ZjljZTE4MzAzZDRjMGI1NjQ4ZjkwMTM=
12
- data.tar.gz: !binary |-
13
- MTg1ZjJhODQwYWVhZDc2ZjUwYmRjNzY3MjM0ZTE5MzAyYTU1ZjY1NWI1ZTZh
14
- MDRkMGI4YTEyZDczYWVmZDNmZWUxZjE1YzBkZTQ3NWZhZmY3ZmU4MDYzZjI3
15
- ODE4YmI3MmJiMWM5ZDhiMDc3ZjJhMjQzZjJiZDY4MTM5MWQ1ZGM=