reform 2.3.3 → 2.5.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.
Files changed (68) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +1 -1
  3. data/.travis.yml +0 -3
  4. data/CHANGES.md +9 -0
  5. data/Gemfile +1 -1
  6. data/LICENSE.txt +1 -1
  7. data/README.md +5 -5
  8. data/Rakefile +1 -12
  9. data/lib/reform/contract/validate.rb +1 -1
  10. data/lib/reform/form/dry.rb +47 -9
  11. data/lib/reform/validation/groups.rb +0 -1
  12. data/lib/reform/version.rb +1 -1
  13. data/test/call_test.rb +23 -0
  14. data/test/changed_test.rb +6 -6
  15. data/test/coercion_test.rb +17 -17
  16. data/test/{composition_new_api.rb → composition_test.rb} +27 -28
  17. data/test/{contract_new_api.rb → contract_test.rb} +8 -8
  18. data/test/default_test.rb +2 -2
  19. data/test/deserialize_test.rb +8 -8
  20. data/test/docs/validation_test.rb +134 -0
  21. data/test/{errors_new_api.rb → errors_test.rb} +41 -41
  22. data/test/feature_test.rb +2 -2
  23. data/test/fixtures/dry_error_messages.yml +64 -54
  24. data/test/{form_option_new_api.rb → form_option_test.rb} +1 -1
  25. data/test/{form_new_api.rb → form_test.rb} +3 -3
  26. data/test/from_test.rb +10 -10
  27. data/test/{inherit_new_api.rb → inherit_test.rb} +17 -17
  28. data/test/{module_new_api.rb → module_test.rb} +10 -10
  29. data/test/parse_option_test.rb +7 -7
  30. data/test/parse_pipeline_test.rb +1 -1
  31. data/test/{populate_new_api.rb → populate_test.rb} +112 -53
  32. data/test/populator_skip_test.rb +2 -2
  33. data/test/prepopulator_test.rb +15 -15
  34. data/test/read_only_test.rb +2 -2
  35. data/test/readable_test.rb +3 -3
  36. data/test/{reform_new_api.rb → reform_test.rb} +19 -19
  37. data/test/{save_new_api.rb → save_test.rb} +4 -4
  38. data/test/setup_test.rb +9 -9
  39. data/test/{skip_if_new_api.rb → skip_if_test.rb} +12 -12
  40. data/test/skip_setter_and_getter_test.rb +6 -6
  41. data/test/test_helper.rb +5 -6
  42. data/test/{validate_new_api.rb → validate_test.rb} +65 -78
  43. data/test/validation/{dry_validation_new_api.rb → dry_validation_test.rb} +124 -123
  44. data/test/validation/result_test.rb +14 -14
  45. data/test/virtual_test.rb +7 -7
  46. data/test/writeable_test.rb +8 -8
  47. metadata +35 -68
  48. data/Appraisals +0 -8
  49. data/gemfiles/0.13.0.gemfile +0 -8
  50. data/gemfiles/1.5.0.gemfile +0 -9
  51. data/lib/reform/form/dry/new_api.rb +0 -45
  52. data/lib/reform/form/dry/old_api.rb +0 -61
  53. data/test/call_new_api.rb +0 -23
  54. data/test/call_old_api.rb +0 -23
  55. data/test/composition_old_api.rb +0 -184
  56. data/test/contract_old_api.rb +0 -77
  57. data/test/errors_old_api.rb +0 -230
  58. data/test/fixtures/dry_new_api_error_messages.yml +0 -104
  59. data/test/form_old_api.rb +0 -57
  60. data/test/form_option_old_api.rb +0 -24
  61. data/test/inherit_old_api.rb +0 -105
  62. data/test/module_old_api.rb +0 -146
  63. data/test/populate_old_api.rb +0 -304
  64. data/test/reform_old_api.rb +0 -202
  65. data/test/save_old_api.rb +0 -101
  66. data/test/skip_if_old_api.rb +0 -92
  67. data/test/validate_old_api.rb +0 -410
  68. data/test/validation/dry_validation_old_api.rb +0 -772
@@ -46,32 +46,32 @@ class ContractTest < MiniTest::Spec
46
46
 
47
47
  # accept `property form: SongForm`.
48
48
  it do
49
- _(form.artist).must_be_instance_of ArtistForm
49
+ assert form.artist.is_a? ArtistForm
50
50
  end
51
51
 
52
52
  describe ".properties" do
53
53
  it "defines a property when called with one argument" do
54
- _(form).must_respond_to :duration
54
+ assert_respond_to form, :duration
55
55
  end
56
56
 
57
57
  it "defines several properties when called with multiple arguments" do
58
- _(form).must_respond_to :year
59
- _(form).must_respond_to :style
58
+ assert_respond_to form, :year
59
+ assert_respond_to form, :style
60
60
  end
61
61
 
62
62
  it "passes options to each property when options are provided" do
63
63
  readable = AlbumForm.new(album).options_for(:style)[:readable]
64
- _(readable).must_equal false
64
+ assert_equal readable, false
65
65
  end
66
66
 
67
67
  it "returns the list of defined properties" do
68
68
  returned_value = AlbumForm.properties(:hello, :world, virtual: true)
69
- _(returned_value).must_equal %i[hello world]
69
+ assert_equal returned_value, %i[hello world]
70
70
  end
71
71
  end
72
72
 
73
73
  describe "#options_for" do
74
- it { _(AlbumForm.options_for(:name).extend(Declarative::Inspect).inspect).must_equal "#<Disposable::Twin::Definition: @options={:private_name=>:name, :name=>\"name\"}>" }
75
- it { _(AlbumForm.new(album).options_for(:name).extend(Declarative::Inspect).inspect).must_equal "#<Disposable::Twin::Definition: @options={:private_name=>:name, :name=>\"name\"}>" }
74
+ it { assert_equal AlbumForm.options_for(:name).extend(Declarative::Inspect).inspect, "#<Disposable::Twin::Definition: @options={:private_name=>:name, :name=>\"name\"}>" }
75
+ it { assert_equal AlbumForm.new(album).options_for(:name).extend(Declarative::Inspect).inspect, "#<Disposable::Twin::Definition: @options={:private_name=>:name, :name=>\"name\"}>" }
76
76
  end
77
77
  end
data/test/default_test.rb CHANGED
@@ -16,7 +16,7 @@ class DefaultTest < Minitest::Spec
16
16
  it do
17
17
  form = AlbumForm.new(Album.new(nil, [Song.new]))
18
18
 
19
- _(form.name).must_equal "Wrong"
20
- _(form.songs[0].title).must_equal "It's Catching Up"
19
+ assert_equal form.name, "Wrong"
20
+ assert_equal form.songs[0].title, "It's Catching Up"
21
21
  end
22
22
  end
@@ -41,9 +41,9 @@ class DeserializeTest < MiniTest::Spec
41
41
 
42
42
  form.validate(json)
43
43
 
44
- _(form.title).must_equal "Apocalypse Soon"
45
- _(form.artist.name).must_equal "Mute"
46
- _(form.artist.model.object_id).must_equal artist_id
44
+ assert_equal form.title, "Apocalypse Soon"
45
+ assert_equal form.artist.name, "Mute"
46
+ assert_equal form.artist.model.object_id, artist_id
47
47
  end
48
48
 
49
49
  describe "infering the deserializer from another form should NOT copy its populators" do
@@ -62,7 +62,7 @@ class DeserializeTest < MiniTest::Spec
62
62
  form = CompilationForm.new(Album.new)
63
63
  form.validate("artist" => {"name" => "Horowitz"}) # the deserializer doesn't know symbols.
64
64
  form.sync
65
- _(form.artist.model).must_equal Artist.new("Horowitz", %{{"name"=>"Horowitz"}})
65
+ assert_equal form.artist.model, Artist.new("Horowitz", %{{"name"=>"Horowitz"}})
66
66
  end
67
67
  end
68
68
  end
@@ -91,11 +91,11 @@ class ValidateWithBlockTest < MiniTest::Spec
91
91
  options_from: :deserializer
92
92
  )
93
93
 
94
- _(form.validate(json) { |params|
94
+ assert form.validate(json) { |params|
95
95
  deserializer.new(form).from_json(params)
96
- }).must_equal true # with block must return result, too.
96
+ } # with block must return result, too.
97
97
 
98
- _(form.title).must_equal "Apocalypse Soon"
99
- _(form.artist.name).must_equal "Mute"
98
+ assert_equal form.title, "Apocalypse Soon"
99
+ assert_equal form.artist.name, "Mute"
100
100
  end
101
101
  end
@@ -0,0 +1,134 @@
1
+ require 'test_helper'
2
+ require 'reform/form/dry'
3
+
4
+ class DocsDryVTest < Minitest::Spec
5
+ #:basic
6
+ class AlbumForm < Reform::Form
7
+ feature Reform::Form::Dry
8
+
9
+ property :name
10
+
11
+ validation do
12
+ params do
13
+ required(:name).filled
14
+ end
15
+ end
16
+ end
17
+ #:basic end
18
+
19
+ it 'validates correctly' do
20
+ form = DocsDryVTest::AlbumForm.new(Album.new(nil, nil, nil))
21
+ result = form.call(name: nil)
22
+
23
+ refute result.success?
24
+ assert_equal({ name: ['must be filled'] }, form.errors.messages)
25
+ end
26
+ end
27
+
28
+ class DocsDryVWithRulesTest < Minitest::Spec
29
+ #:basic_with_rules
30
+ class AlbumForm < Reform::Form
31
+ feature Reform::Form::Dry
32
+
33
+ property :name
34
+
35
+ validation name: :default do
36
+ option :form
37
+
38
+ params do
39
+ required(:name).filled
40
+ end
41
+
42
+ rule(:name) do
43
+ key.failure('must be unique') if Album.where.not(id: form.model.id).where(name: value).exists?
44
+ end
45
+ end
46
+ end
47
+ #:basic_with_rules end
48
+
49
+ it 'validates correctly' do
50
+ Album = Struct.new(:name, :songs, :artist, :user)
51
+ form = DocsDryVWithRulesTest::AlbumForm.new(Album.new(nil, nil, nil, nil))
52
+ result = form.call(name: nil)
53
+
54
+ refute result.success?
55
+ assert_equal({ name: ['must be filled'] }, form.errors.messages)
56
+ end
57
+ end
58
+
59
+ class DryVWithNestedTest < Minitest::Spec
60
+ #:nested
61
+ class AlbumForm < Reform::Form
62
+ feature Reform::Form::Dry
63
+
64
+ property :name
65
+
66
+ validation do
67
+ params { required(:name).filled }
68
+ end
69
+
70
+ property :artist do
71
+ property :name
72
+
73
+ validation do
74
+ params { required(:name).filled }
75
+ end
76
+ end
77
+ end
78
+ #:nested end
79
+
80
+ it 'validates correctly' do
81
+ form = DryVWithNestedTest::AlbumForm.new(Album.new(nil, nil, Artist.new(nil)))
82
+ result = form.call(name: nil, artist: { name: '' })
83
+
84
+ refute result.success?
85
+ assert_equal({ name: ['must be filled'], 'artist.name': ['must be filled'] }, form.errors.messages)
86
+ end
87
+ end
88
+
89
+ class DryVValGroupTest < Minitest::Spec
90
+ class AlbumForm < Reform::Form
91
+ feature Reform::Form::Dry
92
+
93
+ property :name
94
+ property :artist
95
+ #:validation_groups
96
+ validation name: :default do
97
+ params { required(:name).filled }
98
+ end
99
+
100
+ validation name: :artist, if: :default do
101
+ params { required(:artist).filled }
102
+ end
103
+
104
+ validation name: :famous, after: :default do
105
+ params { optional(:artist) }
106
+
107
+ rule(:artist) do
108
+ if value
109
+ key.failure('only famous artist') unless value =~ /famous/
110
+ end
111
+ end
112
+ end
113
+ #:validation_groups end
114
+ end
115
+
116
+ it 'validates correctly' do
117
+ form = DryVValGroupTest::AlbumForm.new(Album.new(nil, nil, nil))
118
+ result = form.call(name: nil)
119
+
120
+ refute result.success?
121
+ assert_equal({ name: ['must be filled'] }, result.errors.messages)
122
+
123
+ result = form.call(name: 'Title')
124
+ refute result.success?
125
+ assert_equal({ artist: ['must be filled'] }, result.errors.messages)
126
+
127
+ result = form.call(name: 'Title', artist: 'Artist')
128
+ refute result.success?
129
+ assert_equal({ artist: ['only famous artist'] }, result.errors.messages)
130
+
131
+ result = form.call(name: 'Title', artist: 'Artist famous')
132
+ assert result.success?
133
+ end
134
+ end
@@ -37,7 +37,7 @@ class ErrorsTest < MiniTest::Spec
37
37
  # TODO: make band a required object.
38
38
 
39
39
  validation do
40
- config.messages.load_paths << "test/fixtures/dry_new_api_error_messages.yml"
40
+ config.messages.load_paths << "test/fixtures/dry_error_messages.yml"
41
41
 
42
42
  params { required(:name).filled }
43
43
 
@@ -72,22 +72,22 @@ class ErrorsTest < MiniTest::Spec
72
72
 
73
73
  describe "#validate with invalid array property" do
74
74
  it do
75
- _(form.validate(
75
+ refute form.validate(
76
76
  title: "Swimming Pool - EP",
77
77
  band: {
78
78
  name: "Marie Madeleine",
79
79
  label: {name: "Ekler'o'shocK"}
80
80
  },
81
81
  artists: [42, "Good Charlotte", 43]
82
- )).must_equal false
83
- _(form.errors.messages).must_equal(artists: {0 => ["must be a string"], 2 => ["must be a string"]})
84
- _(form.errors.size).must_equal(1)
82
+ )
83
+ assert_equal form.errors.messages, artists: {0 => ["must be a string"], 2 => ["must be a string"]}
84
+ assert_equal form.errors.size, 1
85
85
  end
86
86
  end
87
87
 
88
88
  describe "#errors without #validate" do
89
89
  it do
90
- _(form.errors.size).must_equal 0
90
+ assert_equal form.errors.size, 0
91
91
  end
92
92
  end
93
93
 
@@ -102,13 +102,13 @@ class ErrorsTest < MiniTest::Spec
102
102
  end
103
103
 
104
104
  it do
105
- _(form.errors.messages).must_equal(
105
+ assert_equal form.errors.messages,{
106
106
  title: ["must be filled"],
107
107
  "hit.title": ["must be filled"],
108
108
  "songs.title": ["must be filled"],
109
109
  "band.label.name": ["must be filled"],
110
110
  "producer.name": ["must be filled"]
111
- )
111
+ }
112
112
  end
113
113
 
114
114
  # it do
@@ -117,60 +117,60 @@ class ErrorsTest < MiniTest::Spec
117
117
  # end
118
118
 
119
119
  # nested forms keep their own Errors:
120
- it { _(form.producer.errors.messages).must_equal(name: ["must be filled"]) }
121
- it { _(form.hit.errors.messages).must_equal(title: ["must be filled"]) }
122
- it { _(form.songs[0].errors.messages).must_equal(title: ["must be filled"]) }
120
+ it { assert_equal form.producer.errors.messages, name: ["must be filled"] }
121
+ it { assert_equal form.hit.errors.messages, title: ["must be filled"] }
122
+ it { assert_equal form.songs[0].errors.messages, title: ["must be filled"] }
123
123
 
124
124
  it do
125
- _(form.errors.messages).must_equal(
125
+ assert_equal form.errors.messages, {
126
126
  title: ["must be filled"],
127
127
  "hit.title": ["must be filled"],
128
128
  "songs.title": ["must be filled"],
129
129
  "band.label.name": ["must be filled"],
130
130
  "producer.name": ["must be filled"]
131
- )
132
- _(form.errors.size).must_equal(5)
131
+ }
132
+ assert_equal form.errors.size, 5
133
133
  end
134
134
  end
135
135
 
136
136
  describe "#validate with main form invalid" do
137
137
  it do
138
- _(form.validate("title" => "", "band" => {"label" => {name: "Fat Wreck"}}, "producer" => nil)).must_equal false
139
- _(form.errors.messages).must_equal(title: ["must be filled"], producer: ["must be a hash"])
140
- _(form.errors.size).must_equal(2)
138
+ refute form.validate("title" => "", "band" => {"label" => {name: "Fat Wreck"}}, "producer" => nil)
139
+ assert_equal form.errors.messages, title: ["must be filled"], producer: ["must be a hash"]
140
+ assert_equal form.errors.size, 2
141
141
  end
142
142
  end
143
143
 
144
144
  describe "#validate with middle nested form invalid" do
145
145
  before { @result = form.validate("hit" => {"title" => ""}, "band" => {"label" => {name: "Fat Wreck"}}) }
146
146
 
147
- it { _(@result).must_equal false }
148
- it { _(form.errors.messages).must_equal("hit.title": ["must be filled"]) }
149
- it { _(form.errors.size).must_equal(1) }
147
+ it { refute @result }
148
+ it { assert_equal form.errors.messages, "hit.title": ["must be filled"] }
149
+ it { assert_equal form.errors.size, 1 }
150
150
  end
151
151
 
152
152
  describe "#validate with collection form invalid" do
153
153
  before { @result = form.validate("songs" => [{"title" => ""}], "band" => {"label" => {name: "Fat Wreck"}}) }
154
154
 
155
- it { _(@result).must_equal false }
156
- it { _(form.errors.messages).must_equal("songs.title": ["must be filled"]) }
157
- it { _(form.errors.size).must_equal(1) }
155
+ it { refute @result }
156
+ it { assert_equal form.errors.messages, "songs.title": ["must be filled"] }
157
+ it { assert_equal form.errors.size, 1 }
158
158
  end
159
159
 
160
160
  describe "#validate with collection and 2-level-nested invalid" do
161
161
  before { @result = form.validate("songs" => [{"title" => ""}], "band" => {"label" => {}}) }
162
162
 
163
- it { _(@result).must_equal false }
164
- it { _(form.errors.messages).must_equal("songs.title": ["must be filled"], "band.label.name": ["must be filled"]) }
165
- it { _(form.errors.size).must_equal(2) }
163
+ it { refute @result }
164
+ it { assert_equal form.errors.messages, "songs.title": ["must be filled"], "band.label.name": ["must be filled"] }
165
+ it { assert_equal form.errors.size, 2 }
166
166
  end
167
167
 
168
168
  describe "#validate with nested form using :base invalid" do
169
169
  it do
170
170
  result = form.validate("songs" => [{"title" => "Someday"}], "band" => {"name" => "Nickelback", "label" => {"name" => "Roadrunner Records"}})
171
- _(result).must_equal false
172
- _(form.errors.messages).must_equal("band.name": ["you're a bad person"])
173
- _(form.errors.size).must_equal(1)
171
+ refute result
172
+ assert_equal form.errors.messages, "band.name": ["you're a bad person"]
173
+ assert_equal form.errors.size, 1
174
174
  end
175
175
  end
176
176
 
@@ -178,17 +178,17 @@ class ErrorsTest < MiniTest::Spec
178
178
  let(:album_title) { nil }
179
179
  it do
180
180
  result = form.validate("songs" => [{"title" => "Someday"}], "band" => {"name" => "Nickelback", "label" => {"name" => "Roadrunner Records"}})
181
- _(result).must_equal false
182
- _(form.errors.messages).must_equal(title: ["must be filled"], "band.name": ["you're a bad person"])
181
+ refute result
182
+ assert_equal form.errors.messages, title: ["must be filled"], "band.name": ["you're a bad person"]
183
183
  # add a new custom error
184
184
  form.errors.add(:policy, "error_text")
185
- _(form.errors.messages).must_equal(title: ["must be filled"], "band.name": ["you're a bad person"], policy: ["error_text"])
185
+ assert_equal form.errors.messages, title: ["must be filled"], "band.name": ["you're a bad person"], policy: ["error_text"]
186
186
  # does not duplicate errors
187
187
  form.errors.add(:title, "must be filled")
188
- _(form.errors.messages).must_equal(title: ["must be filled"], "band.name": ["you're a bad person"], policy: ["error_text"])
188
+ assert_equal form.errors.messages, title: ["must be filled"], "band.name": ["you're a bad person"], policy: ["error_text"]
189
189
  # merge existing errors
190
190
  form.errors.add(:policy, "another error")
191
- _(form.errors.messages).must_equal(title: ["must be filled"], "band.name": ["you're a bad person"], policy: ["error_text", "another error"])
191
+ assert_equal form.errors.messages, title: ["must be filled"], "band.name": ["you're a bad person"], policy: ["error_text", "another error"]
192
192
  end
193
193
  end
194
194
 
@@ -202,14 +202,14 @@ class ErrorsTest < MiniTest::Spec
202
202
  )
203
203
  end
204
204
 
205
- it { _(@result).must_equal true }
206
- it { _(form.hit.title).must_equal "Sacrifice" }
207
- it { _(form.title).must_equal "Second Heat" }
208
- it { _(form.songs.first.title).must_equal "Heart Of A Lion" }
205
+ it { assert @result }
206
+ it { assert_equal form.hit.title, "Sacrifice" }
207
+ it { assert_equal form.title, "Second Heat" }
208
+ it { assert_equal form.songs.first.title, "Heart Of A Lion" }
209
209
  it do
210
210
  skip "WE DON'T NEED COUNT AND EMPTY? ON THE CORE ERRORS OBJECT"
211
- _(form.errors.size).must_equal(0)
212
- _(form.errors.empty?).must_equal(true)
211
+ assert_equal form.errors.size, 0
212
+ assert form.errors.empty
213
213
  end
214
214
  end
215
215
 
@@ -219,7 +219,7 @@ class ErrorsTest < MiniTest::Spec
219
219
  # to_s is aliased to messages
220
220
  it {
221
221
  skip "why do we need Errors#to_s ?"
222
- _(form.errors.to_s).must_equal "{:\"songs.title\"=>[\"must be filled\"], :\"band.label.name\"=>[\"must be filled\"]}"
222
+ assert_equal form.errors.to_s, "{:\"songs.title\"=>[\"must be filled\"], :\"band.label.name\"=>[\"must be filled\"]}"
223
223
  }
224
224
  end
225
225
  end
data/test/feature_test.rb CHANGED
@@ -45,8 +45,8 @@ class FeatureInheritanceTest < BaseTest
45
45
  let(:form) { AlbumForm.new(album) }
46
46
 
47
47
  it do
48
- _(form.date).must_equal "May 16"
49
- _(form.songs[0].date).must_equal "May 16"
48
+ assert_equal form.date, "May 16"
49
+ assert_equal form.songs[0].date, "May 16"
50
50
  end
51
51
 
52
52
  # it { subject.class.include?(Reform::Form::ActiveModel) }
@@ -1,94 +1,104 @@
1
1
  en:
2
- errors:
3
- array?: "must be an array"
2
+ dry_validation:
3
+ errors:
4
+ array?: "must be an array"
4
5
 
5
- empty?: "must be empty"
6
+ empty?: "must be empty"
6
7
 
7
- excludes?: "must not include %{value}"
8
+ excludes?: "must not include %{value}"
8
9
 
9
- excluded_from?:
10
- arg:
11
- default: "must not be one of: %{list}"
12
- range: "must not be one of: %{list_left} - %{list_right}"
10
+ excluded_from?:
11
+ arg:
12
+ default: "must not be one of: %{list}"
13
+ range: "must not be one of: %{list_left} - %{list_right}"
13
14
 
14
- eql?: "must be equal to %{left}"
15
+ eql?: "must be equal to %{left}"
15
16
 
16
- not_eql?: "must not be equal to %{left}"
17
+ not_eql?: "must not be equal to %{left}"
17
18
 
18
- filled?: "must be filled"
19
+ filled?: "must be filled"
19
20
 
20
- format?: "is in invalid format"
21
+ format?: "is in invalid format"
21
22
 
22
- number?: "must be a number"
23
+ number?: "must be a number"
23
24
 
24
- odd?: "must be odd"
25
+ odd?: "must be odd"
25
26
 
26
- even?: "must be even"
27
+ even?: "must be even"
27
28
 
28
- gt?: "must be greater than %{num}"
29
+ gt?: "must be greater than %{num}"
29
30
 
30
- gteq?: "must be greater than or equal to %{num}"
31
+ gteq?: "must be greater than or equal to %{num}"
31
32
 
32
- hash?: "must be a hash"
33
+ hash?: "must be a hash"
33
34
 
34
- included_in?:
35
- arg:
36
- default: "must be one of: %{list}"
37
- range: "must be one of: %{list_left} - %{list_right}"
35
+ included_in?:
36
+ arg:
37
+ default: "must be one of: %{list}"
38
+ range: "must be one of: %{list_left} - %{list_right}"
38
39
 
39
- includes?: "must include %{value}"
40
+ includes?: "must include %{value}"
40
41
 
41
- bool?: "must be boolean"
42
+ bool?: "must be boolean"
42
43
 
43
- true?: "must be true"
44
+ true?: "must be true"
44
45
 
45
- false?: "must be false"
46
+ false?: "must be false"
46
47
 
47
- int?: "must be an integer"
48
+ int?: "must be an integer"
48
49
 
49
- float?: "must be a float"
50
+ float?: "must be a float"
50
51
 
51
- decimal?: "must be a decimal"
52
+ decimal?: "must be a decimal"
52
53
 
53
- date?: "must be a date"
54
+ date?: "must be a date"
54
55
 
55
- date_time?: "must be a date time"
56
+ date_time?: "must be a date time"
56
57
 
57
- time?: "must be a time"
58
+ time?: "must be a time"
58
59
 
59
- key?: "is missing"
60
+ key?: "is missing"
60
61
 
61
- attr?: "is missing"
62
+ attr?: "is missing"
62
63
 
63
- lt?: "must be less than %{num}"
64
+ lt?: "must be less than %{num}"
64
65
 
65
- lteq?: "must be less than or equal to %{num}"
66
+ lteq?: "must be less than or equal to %{num}"
66
67
 
67
- max_size?: "size cannot be greater than %{num}"
68
+ max_size?: "size cannot be greater than %{num}"
68
69
 
69
- min_size?: "size cannot be less than %{num}"
70
+ min_size?: "size cannot be less than %{num}"
70
71
 
71
- none?: "cannot be defined"
72
+ none?: "cannot be defined"
72
73
 
73
- str?: "must be a string"
74
+ str?: "must be a string"
74
75
 
75
- type?: "must be %{type}"
76
+ type?: "must be %{type}"
76
77
 
77
- size?:
78
- arg:
79
- default: "size must be %{size}"
80
- range: "size must be within %{size_left} - %{size_right}"
78
+ size?:
79
+ arg:
80
+ default: "size must be %{size}"
81
+ range: "size must be within %{size_left} - %{size_right}"
81
82
 
82
- value:
83
- string:
84
- arg:
85
- default: "length must be %{size}"
86
- range: "length must be within %{size_left} - %{size_right}"
83
+ value:
84
+ string:
85
+ arg:
86
+ default: "length must be %{size}"
87
+ range: "length must be within %{size_left} - %{size_right}"
87
88
 
88
- good_musical_taste?: "you're a bad person"
89
89
 
90
- a_song?: "must have at least one enabled song"
91
- with_last_name?: "must have last name"
90
+
91
+ rules:
92
+ name:
93
+ good_musical_taste?: "you're a bad person"
94
+ title:
95
+ good_musical_taste?: "you're a bad person"
96
+ songs:
97
+ a_song?: "must have at least one enabled song"
98
+ artist:
99
+ with_last_name?: "must have last name"
100
+
92
101
  de:
93
- errors:
102
+ dry_validation:
103
+ errors:
94
104
  filled?: "muss abgefüllt sein"