simple_form 1.4.2 → 1.5.0
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of simple_form might be problematic. Click here for more details.
- data/.gitignore +1 -0
- data/.travis.yml +9 -1
- data/CHANGELOG.rdoc +20 -0
- data/Gemfile +5 -4
- data/README.rdoc +2 -2
- data/Rakefile +1 -1
- data/lib/generators/simple_form/install_generator.rb +2 -6
- data/lib/generators/simple_form/templates/{simple_form.rb → config/initializers/simple_form.rb} +0 -0
- data/lib/generators/simple_form/templates/{en.yml → config/locales/simple_form.en.yml} +0 -0
- data/lib/simple_form.rb +1 -1
- data/lib/simple_form/action_view_extensions/builder.rb +12 -5
- data/lib/simple_form/action_view_extensions/form_helper.rb +13 -8
- data/lib/simple_form/components.rb +1 -1
- data/lib/simple_form/components/errors.rb +10 -2
- data/lib/simple_form/components/hints.rb +10 -0
- data/lib/simple_form/components/label_input.rb +5 -3
- data/lib/simple_form/components/labels.rb +10 -4
- data/lib/simple_form/components/placeholders.rb +10 -4
- data/lib/simple_form/error_notification.rb +1 -1
- data/lib/simple_form/form_builder.rb +10 -7
- data/lib/simple_form/helpers.rb +9 -0
- data/lib/simple_form/helpers/has_errors.rb +15 -0
- data/lib/simple_form/helpers/maxlength.rb +24 -0
- data/lib/simple_form/helpers/pattern.rb +28 -0
- data/lib/simple_form/helpers/required.rb +36 -0
- data/lib/simple_form/helpers/validators.rb +44 -0
- data/lib/simple_form/inputs.rb +5 -2
- data/lib/simple_form/inputs/base.rb +24 -47
- data/lib/simple_form/inputs/boolean_input.rb +1 -1
- data/lib/simple_form/inputs/collection_input.rb +1 -1
- data/lib/simple_form/inputs/date_time_input.rb +1 -1
- data/lib/simple_form/inputs/file_input.rb +9 -0
- data/lib/simple_form/inputs/hidden_input.rb +1 -1
- data/lib/simple_form/inputs/numeric_input.rb +20 -13
- data/lib/simple_form/inputs/password_input.rb +13 -0
- data/lib/simple_form/inputs/range_input.rb +16 -0
- data/lib/simple_form/inputs/string_input.rb +7 -24
- data/lib/simple_form/inputs/text_input.rb +12 -0
- data/lib/simple_form/version.rb +1 -1
- data/test/action_view_extensions/builder_test.rb +59 -0
- data/test/action_view_extensions/form_helper_test.rb +21 -0
- data/test/discovery_inputs.rb +2 -2
- data/test/form_builder_test.rb +54 -0
- data/test/inputs_test.rb +185 -20
- data/test/support/models.rb +23 -2
- data/test/test_helper.rb +1 -0
- metadata +17 -11
- data/Gemfile.lock +0 -54
- data/init.rb +0 -1
- data/lib/simple_form/has_errors.rb +0 -14
- data/lib/simple_form/inputs/mapping_input.rb +0 -29
@@ -47,6 +47,16 @@ class FormHelperTest < ActionView::TestCase
|
|
47
47
|
assert_select 'form.simple_form.user'
|
48
48
|
end
|
49
49
|
|
50
|
+
test 'simple form should not add object class to form if css_class is specified' do
|
51
|
+
concat(simple_form_for(:user, :html => {:class => nil}) do |f| end)
|
52
|
+
assert_no_select 'form.user'
|
53
|
+
end
|
54
|
+
|
55
|
+
test 'simple form should add custom class to form if css_class is specified' do
|
56
|
+
concat(simple_form_for(:user, :html => {:class => 'my_class'}) do |f| end)
|
57
|
+
assert_select 'form.my_class'
|
58
|
+
end
|
59
|
+
|
50
60
|
test 'pass options to simple form' do
|
51
61
|
concat(simple_form_for(:user, :url => '/account', :html => { :id => 'my_form' }) do |f| end)
|
52
62
|
assert_select 'form#my_form'
|
@@ -58,4 +68,15 @@ class FormHelperTest < ActionView::TestCase
|
|
58
68
|
assert f.instance_of?(SimpleForm::FormBuilder)
|
59
69
|
end)
|
60
70
|
end
|
71
|
+
|
72
|
+
test 'fields for with a hash like model yeilds an instance of FormBuilder' do
|
73
|
+
@hash_backed_author = HashBackedAuthor.new
|
74
|
+
|
75
|
+
concat(simple_fields_for(:author, @hash_backed_author) do |f|
|
76
|
+
assert f.instance_of?(SimpleForm::FormBuilder)
|
77
|
+
f.input :name
|
78
|
+
end)
|
79
|
+
|
80
|
+
assert_select "input[name='author[name]'][value='hash backed author']"
|
81
|
+
end
|
61
82
|
end
|
data/test/discovery_inputs.rb
CHANGED
data/test/form_builder_test.rb
CHANGED
@@ -338,6 +338,8 @@ class FormBuilderTest < ActionView::TestCase
|
|
338
338
|
assert_select 'input.optional#user_name'
|
339
339
|
end
|
340
340
|
|
341
|
+
# VALIDATORS :if :unless
|
342
|
+
|
341
343
|
test 'builder input should not be required when ActiveModel::Validations is included and if option is present' do
|
342
344
|
with_form_for @validating_user, :age
|
343
345
|
assert_no_select 'input.required'
|
@@ -352,7 +354,53 @@ class FormBuilderTest < ActionView::TestCase
|
|
352
354
|
assert_select 'input.optional#validating_user_amount'
|
353
355
|
end
|
354
356
|
|
357
|
+
# VALIDATORS :on
|
358
|
+
|
359
|
+
test 'builder input should be required when validation is on create and is not persisted' do
|
360
|
+
@validating_user.new_record!
|
361
|
+
with_form_for @validating_user, :action
|
362
|
+
assert_select 'input.required'
|
363
|
+
assert_select 'input[required]'
|
364
|
+
assert_select 'input.required[required]#validating_user_action'
|
365
|
+
end
|
366
|
+
|
367
|
+
test 'builder input should not be required when validation is on create and is persisted' do
|
368
|
+
with_form_for @validating_user, :action
|
369
|
+
assert_no_select 'input.required'
|
370
|
+
assert_no_select 'input[required]'
|
371
|
+
assert_select 'input.optional#validating_user_action'
|
372
|
+
end
|
373
|
+
|
374
|
+
test 'builder input should be required when validation is on save' do
|
375
|
+
with_form_for @validating_user, :credit_limit
|
376
|
+
assert_select 'input.required'
|
377
|
+
assert_select 'input[required]'
|
378
|
+
assert_select 'input.required[required]#validating_user_credit_limit'
|
379
|
+
|
380
|
+
@validating_user.new_record!
|
381
|
+
with_form_for @validating_user, :credit_limit
|
382
|
+
assert_select 'input.required'
|
383
|
+
assert_select 'input[required]'
|
384
|
+
assert_select 'input.required[required]#validating_user_credit_limit'
|
385
|
+
end
|
386
|
+
|
387
|
+
test 'builder input should be required when validation is on update and is persisted' do
|
388
|
+
with_form_for @validating_user, :phone_number
|
389
|
+
assert_select 'input.required'
|
390
|
+
assert_select 'input[required]'
|
391
|
+
assert_select 'input.required[required]#validating_user_phone_number'
|
392
|
+
end
|
393
|
+
|
394
|
+
test 'builder input should not be required when validation is on update and is not persisted' do
|
395
|
+
@validating_user.new_record!
|
396
|
+
with_form_for @validating_user, :phone_number
|
397
|
+
assert_no_select 'input.required'
|
398
|
+
assert_no_select 'input[required]'
|
399
|
+
assert_select 'input.optional#validating_user_phone_number'
|
400
|
+
end
|
401
|
+
|
355
402
|
# WRAPPERS
|
403
|
+
|
356
404
|
test 'builder support wrapping around an specific tag' do
|
357
405
|
swap SimpleForm, :wrapper_tag => :p do
|
358
406
|
with_form_for @user, :name
|
@@ -361,6 +409,12 @@ class FormBuilderTest < ActionView::TestCase
|
|
361
409
|
end
|
362
410
|
end
|
363
411
|
|
412
|
+
test 'builder support no wrapping when wrapper is false' do
|
413
|
+
with_form_for @user, :name, :wrapper => false
|
414
|
+
assert_select 'form > label[for=user_name]'
|
415
|
+
assert_select 'form > input#user_name.string'
|
416
|
+
end
|
417
|
+
|
364
418
|
test 'builder wrapping tag adds default css classes' do
|
365
419
|
swap SimpleForm, :wrapper_tag => :p do
|
366
420
|
with_form_for @user, :name
|
data/test/inputs_test.rb
CHANGED
@@ -141,9 +141,9 @@ class InputTest < ActionView::TestCase
|
|
141
141
|
assert_select "input#user_password.password[type=password][name='user[password]']"
|
142
142
|
end
|
143
143
|
|
144
|
-
test 'input should use
|
144
|
+
test 'input should not use size attribute for decimal attributes' do
|
145
145
|
with_input_for @user, :credit_limit, :decimal
|
146
|
-
|
146
|
+
assert_no_select 'input.decimal[size]'
|
147
147
|
end
|
148
148
|
|
149
149
|
test 'input should get maxlength from column definition for string attributes' do
|
@@ -151,6 +151,11 @@ class InputTest < ActionView::TestCase
|
|
151
151
|
assert_select 'input.string[maxlength=100]'
|
152
152
|
end
|
153
153
|
|
154
|
+
test 'input should not get maxlength from column without size definition for string attributes' do
|
155
|
+
with_input_for @user, :action, :string
|
156
|
+
assert_no_select 'input.string[maxlength]'
|
157
|
+
end
|
158
|
+
|
154
159
|
test 'input should get size from column definition for string attributes respecting maximum value' do
|
155
160
|
with_input_for @user, :name, :string
|
156
161
|
assert_select 'input.string[size=50]'
|
@@ -166,6 +171,11 @@ class InputTest < ActionView::TestCase
|
|
166
171
|
assert_select 'input.password[type=password][maxlength=100]'
|
167
172
|
end
|
168
173
|
|
174
|
+
test 'input should infer maxlength column definition from validation when present' do
|
175
|
+
with_input_for @validating_user, :name, :string
|
176
|
+
assert_select 'input.string[maxlength=25]'
|
177
|
+
end
|
178
|
+
|
169
179
|
test 'when not using HTML5, does not show maxlength attribute' do
|
170
180
|
swap SimpleForm, :html5 => false do
|
171
181
|
with_input_for @user, :password, :password
|
@@ -173,6 +183,13 @@ class InputTest < ActionView::TestCase
|
|
173
183
|
end
|
174
184
|
end
|
175
185
|
|
186
|
+
test 'when not using HTML5, does not show maxlength attribute with validating lenght attribute' do
|
187
|
+
swap SimpleForm, :html5 => false do
|
188
|
+
with_input_for @validating_user, :name, :string
|
189
|
+
assert_no_select 'input.string[maxlength]'
|
190
|
+
end
|
191
|
+
end
|
192
|
+
|
176
193
|
test 'input should not generate placeholder by default' do
|
177
194
|
with_input_for @user, :name, :string
|
178
195
|
assert_no_select 'input[placeholder]'
|
@@ -212,6 +229,22 @@ class InputTest < ActionView::TestCase
|
|
212
229
|
end
|
213
230
|
end
|
214
231
|
|
232
|
+
test 'input should infer pattern from attributes when pattern is true' do
|
233
|
+
with_input_for @other_validating_user, :country, :string, :pattern => true
|
234
|
+
assert_select 'input[pattern="\w+"]'
|
235
|
+
end
|
236
|
+
|
237
|
+
test 'input should use given pattern from attributes' do
|
238
|
+
with_input_for @other_validating_user, :country, :string, :pattern => "\\d+"
|
239
|
+
assert_select 'input[pattern="\d+"]'
|
240
|
+
end
|
241
|
+
|
242
|
+
test 'input should fail if pattern is true but no pattern exists' do
|
243
|
+
assert_raise RuntimeError do
|
244
|
+
with_input_for @other_validating_user, :name, :string, :pattern => true
|
245
|
+
end
|
246
|
+
end
|
247
|
+
|
215
248
|
# NumericInput
|
216
249
|
test 'input should generate an integer text field for integer attributes ' do
|
217
250
|
with_input_for @user, :age, :integer
|
@@ -345,16 +378,28 @@ class InputTest < ActionView::TestCase
|
|
345
378
|
end
|
346
379
|
end
|
347
380
|
|
381
|
+
[:integer, :float, :decimal].each do |type|
|
382
|
+
test "#{type} input should infer min value from attributes with greater than or equal validation" do
|
383
|
+
with_input_for @validating_user, :age, type
|
384
|
+
assert_select 'input[min=18]'
|
385
|
+
end
|
386
|
+
|
387
|
+
test "#{type} input should infer the max value from attributes with less than or equal to validation" do
|
388
|
+
with_input_for @validating_user, :age, type
|
389
|
+
assert_select 'input[max=99]'
|
390
|
+
end
|
391
|
+
end
|
392
|
+
|
348
393
|
# Numeric input but HTML5 disabled
|
349
|
-
test '
|
394
|
+
test 'when not using HTML5 input should not generate field with type number and use text instead' do
|
350
395
|
swap SimpleForm, :html5 => false do
|
351
396
|
with_input_for @user, :age, :integer
|
352
397
|
assert_no_select "input[type=number]"
|
353
|
-
|
398
|
+
assert_select "input#user_age[type=text]"
|
354
399
|
end
|
355
400
|
end
|
356
401
|
|
357
|
-
test 'when not using HTML5 input should not use min or max or step attributes' do
|
402
|
+
test 'when not using HTML5 input should not use min or max or step attributes for numeric type' do
|
358
403
|
swap SimpleForm, :html5 => false do
|
359
404
|
with_input_for @validating_user, :age, :integer
|
360
405
|
assert_no_select "input[min]"
|
@@ -363,15 +408,63 @@ class InputTest < ActionView::TestCase
|
|
363
408
|
end
|
364
409
|
end
|
365
410
|
|
366
|
-
|
367
|
-
|
368
|
-
|
369
|
-
|
411
|
+
# RangeInput
|
412
|
+
test 'range input generates a input type range, based on numeric input' do
|
413
|
+
with_input_for @user, :age, :range
|
414
|
+
assert_select "input#user_age.range[type=range]"
|
415
|
+
end
|
416
|
+
|
417
|
+
test 'range input does not generate placeholder' do
|
418
|
+
with_input_for @user, :age, :range, :placeholder => "Select your age"
|
419
|
+
assert_select "input[type=range]"
|
420
|
+
assert_no_select "input[placeholder]"
|
421
|
+
end
|
422
|
+
|
423
|
+
test 'range input allows givin min and max attributes' do
|
424
|
+
with_input_for @user, :age, :range, :input_html => { :min => 10, :max => 50 }
|
425
|
+
assert_select "input[type=range][min=10][max=50]"
|
426
|
+
end
|
427
|
+
|
428
|
+
test 'range input infers min and max attributes from validations' do
|
429
|
+
with_input_for @validating_user, :age, :range
|
430
|
+
assert_select "input[type=range][min=18][max=99]"
|
431
|
+
end
|
432
|
+
|
433
|
+
test 'range input add default step attribute' do
|
434
|
+
with_input_for @validating_user, :age, :range
|
435
|
+
assert_select "input[type=range][step=1]"
|
436
|
+
end
|
437
|
+
|
438
|
+
test 'range input allows givin a step through input html options' do
|
439
|
+
with_input_for @validating_user, :age, :range, :input_html => { :step => 2 }
|
440
|
+
assert_select "input[type=range][step=2]"
|
441
|
+
end
|
442
|
+
|
443
|
+
test 'range input should not generate min attribute by default' do
|
444
|
+
with_input_for @user, :age, :range
|
445
|
+
assert_no_select 'input[min]'
|
446
|
+
end
|
447
|
+
|
448
|
+
test 'range input should not generate max attribute by default' do
|
449
|
+
with_input_for @user, :age, :range
|
450
|
+
assert_no_select 'input[max]'
|
451
|
+
end
|
452
|
+
|
453
|
+
# RangeInput iwth HTML5 disabled
|
454
|
+
test 'when not using HTML5, range input does not generate field with range type, and use text instead' do
|
455
|
+
swap SimpleForm, :html5 => false do
|
456
|
+
with_input_for @user, :age, :range
|
457
|
+
assert_no_select "input[type=number]"
|
458
|
+
assert_select "input[type=text]"
|
370
459
|
end
|
460
|
+
end
|
371
461
|
|
372
|
-
|
373
|
-
|
374
|
-
|
462
|
+
test 'when not using HTML5, range input should not use min or max or step attributes' do
|
463
|
+
swap SimpleForm, :html5 => false do
|
464
|
+
with_input_for @validating_user, :age, :range
|
465
|
+
assert_no_select "input[min]"
|
466
|
+
assert_no_select "input[max]"
|
467
|
+
assert_no_select "input[step]"
|
375
468
|
end
|
376
469
|
end
|
377
470
|
|
@@ -393,6 +486,30 @@ class InputTest < ActionView::TestCase
|
|
393
486
|
assert_select 'textarea.text[placeholder=Put in some text]'
|
394
487
|
end
|
395
488
|
|
489
|
+
test 'input should get maxlength from column definition for text attributes' do
|
490
|
+
with_input_for @user, :description, :text
|
491
|
+
assert_select 'textarea.text[maxlength=200]'
|
492
|
+
end
|
493
|
+
|
494
|
+
test 'input should infer maxlength column definition from validation when present for text attributes' do
|
495
|
+
with_input_for @validating_user, :description, :text
|
496
|
+
assert_select 'textarea.text[maxlength=50]'
|
497
|
+
end
|
498
|
+
|
499
|
+
test 'when not using HTML5, does not show maxlength attribute for text attributes' do
|
500
|
+
swap SimpleForm, :html5 => false do
|
501
|
+
with_input_for @user, :description, :text
|
502
|
+
assert_no_select 'textarea.text[maxlength]'
|
503
|
+
end
|
504
|
+
end
|
505
|
+
|
506
|
+
test 'when not using HTML5, does not show maxlength attribute with validating lenght text attribute' do
|
507
|
+
swap SimpleForm, :html5 => false do
|
508
|
+
with_input_for @validating_user, :name, :string
|
509
|
+
assert_no_select 'input.string[maxlength]'
|
510
|
+
end
|
511
|
+
end
|
512
|
+
|
396
513
|
test 'input should generate a file field' do
|
397
514
|
with_input_for @user, :name, :file
|
398
515
|
assert_select 'input#user_name[type=file]'
|
@@ -403,14 +520,6 @@ class InputTest < ActionView::TestCase
|
|
403
520
|
assert_no_select 'input[placeholder]'
|
404
521
|
end
|
405
522
|
|
406
|
-
test 'mapping input should generate an error if type is not found' do
|
407
|
-
with_concat_form_for(@user) do |f|
|
408
|
-
assert_raise(RuntimeError, "Could not find method for nil") do
|
409
|
-
SimpleForm::Inputs::MappingInput.new(f, "unknown", nil, nil, {}).input
|
410
|
-
end
|
411
|
-
end
|
412
|
-
end
|
413
|
-
|
414
523
|
# HiddenInput
|
415
524
|
test 'input should generate a hidden field' do
|
416
525
|
with_input_for @user, :name, :hidden
|
@@ -674,6 +783,62 @@ class InputTest < ActionView::TestCase
|
|
674
783
|
assert_select 'select option[value=2]', 'Carlos'
|
675
784
|
end
|
676
785
|
|
786
|
+
test 'input should disable the anothers components when the option is a object' do
|
787
|
+
with_input_for @user, :description, :select, :collection => ["Jose", "Carlos"], :disabled => true
|
788
|
+
assert_no_select 'select option[value=Jose][disabled=disabled]', 'Jose'
|
789
|
+
assert_no_select 'select option[value=Carlos][disabled=disabled]', 'Carlos'
|
790
|
+
assert_select 'select[disabled=disabled]'
|
791
|
+
assert_select 'div.disabled'
|
792
|
+
end
|
793
|
+
|
794
|
+
test 'input should not disable the anothers components when the option is a object' do
|
795
|
+
with_input_for @user, :description, :select, :collection => ["Jose", "Carlos"], :disabled => 'Jose'
|
796
|
+
assert_select 'select option[value=Jose][disabled=disabled]', 'Jose'
|
797
|
+
assert_no_select 'select option[value=Carlos][disabled=disabled]', 'Carlos'
|
798
|
+
assert_no_select 'select[disabled=disabled]'
|
799
|
+
assert_no_select 'div.disabled'
|
800
|
+
end
|
801
|
+
|
802
|
+
test 'input should allow disabled options with a lambda for collection select' do
|
803
|
+
with_input_for @user, :name, :select, :collection => ["Carlos", "Antonio"],
|
804
|
+
:disabled => lambda { |x| x == "Carlos" }
|
805
|
+
assert_select 'select option[value=Carlos][disabled=disabled]', 'Carlos'
|
806
|
+
assert_select 'select option[value=Antonio]', 'Antonio'
|
807
|
+
assert_no_select 'select option[value=Antonio][disabled]'
|
808
|
+
end
|
809
|
+
|
810
|
+
test 'input should allow disabled and label method with lambdas for collection select' do
|
811
|
+
with_input_for @user, :name, :select, :collection => ["Carlos", "Antonio"],
|
812
|
+
:disabled => lambda { |x| x == "Carlos" }, :label_method => lambda { |x| x.upcase }
|
813
|
+
assert_select 'select option[value=Carlos][disabled=disabled]', 'CARLOS'
|
814
|
+
assert_select 'select option[value=Antonio]', 'ANTONIO'
|
815
|
+
assert_no_select 'select option[value=Antonio][disabled]'
|
816
|
+
end
|
817
|
+
|
818
|
+
test 'input should allow a non lambda disabled option with lambda label method for collections' do
|
819
|
+
with_input_for @user, :name, :select, :collection => ["Carlos", "Antonio"],
|
820
|
+
:disabled => "Carlos", :label_method => lambda { |x| x.upcase }
|
821
|
+
assert_select 'select option[value=Carlos][disabled=disabled]', 'CARLOS'
|
822
|
+
assert_select 'select option[value=Antonio]', 'ANTONIO'
|
823
|
+
assert_no_select 'select option[value=Antonio][disabled]'
|
824
|
+
end
|
825
|
+
|
826
|
+
test 'input should allow selected and label method with lambdas for collection select' do
|
827
|
+
with_input_for @user, :name, :select, :collection => ["Carlos", "Antonio"],
|
828
|
+
:selected => lambda { |x| x == "Carlos" }, :label_method => lambda { |x| x.upcase }
|
829
|
+
assert_select 'select option[value=Carlos][selected=selected]', 'CARLOS'
|
830
|
+
assert_select 'select option[value=Antonio]', 'ANTONIO'
|
831
|
+
assert_no_select 'select option[value=Antonio][selected]'
|
832
|
+
end
|
833
|
+
|
834
|
+
test 'input should allow a non lambda selected option with lambda label method for collection select' do
|
835
|
+
with_input_for @user, :name, :select, :collection => ["Carlos", "Antonio"],
|
836
|
+
:selected => "Carlos", :label_method => lambda { |x| x.upcase }
|
837
|
+
assert_select 'select option[value=Carlos][selected=selected]', 'CARLOS'
|
838
|
+
assert_select 'select option[value=Antonio]', 'ANTONIO'
|
839
|
+
assert_no_select 'select option[value=Antonio][selected]'
|
840
|
+
end
|
841
|
+
|
677
842
|
test 'input should allow overriding collection for radio types' do
|
678
843
|
with_input_for @user, :name, :radio, :collection => ['Jose', 'Carlos']
|
679
844
|
assert_select 'input[type=radio][value=Jose]'
|
data/test/support/models.rb
CHANGED
@@ -42,7 +42,7 @@ class User
|
|
42
42
|
:description, :created_at, :updated_at, :credit_limit, :password, :url,
|
43
43
|
:delivery_time, :born_at, :special_company_id, :country, :tags, :tag_ids,
|
44
44
|
:avatar, :home_picture, :email, :status, :residence_country, :phone_number,
|
45
|
-
:post_count, :lock_version, :amount, :attempts
|
45
|
+
:post_count, :lock_version, :amount, :attempts, :action
|
46
46
|
|
47
47
|
def initialize(options={})
|
48
48
|
options.each do |key, value|
|
@@ -67,7 +67,7 @@ class User
|
|
67
67
|
def column_for_attribute(attribute)
|
68
68
|
column_type, limit = case attribute.to_sym
|
69
69
|
when :name, :status, :password then [:string, 100]
|
70
|
-
when :description then :text
|
70
|
+
when :description then [:text, 200]
|
71
71
|
when :age then :integer
|
72
72
|
when :credit_limit then [:decimal, 15]
|
73
73
|
when :active then :boolean
|
@@ -79,6 +79,7 @@ class User
|
|
79
79
|
when :home_picture then :string
|
80
80
|
when :amount then :integer
|
81
81
|
when :attempts then :integer
|
82
|
+
when :action then :string
|
82
83
|
end
|
83
84
|
Column.new(attribute, column_type, limit)
|
84
85
|
end
|
@@ -129,6 +130,11 @@ class ValidatingUser < User
|
|
129
130
|
validates :company, :presence => true
|
130
131
|
validates :age, :presence => true, :if => Proc.new { |user| user.name }
|
131
132
|
validates :amount, :presence => true, :unless => Proc.new { |user| user.age }
|
133
|
+
|
134
|
+
validates :action, :presence => true, :on => :create
|
135
|
+
validates :credit_limit, :presence => true, :on => :save
|
136
|
+
validates :phone_number, :presence => true, :on => :update
|
137
|
+
|
132
138
|
validates_numericality_of :age,
|
133
139
|
:greater_than_or_equal_to => 18,
|
134
140
|
:less_than_or_equal_to => 99,
|
@@ -141,6 +147,8 @@ class ValidatingUser < User
|
|
141
147
|
:greater_than_or_equal_to => :min_attempts,
|
142
148
|
:less_than_or_equal_to => :max_attempts,
|
143
149
|
:only_integer => true
|
150
|
+
validates_length_of :name, :maximum => 25
|
151
|
+
validates_length_of :description, :maximum => 50
|
144
152
|
|
145
153
|
def min_amount
|
146
154
|
10
|
@@ -173,4 +181,17 @@ class OtherValidatingUser < User
|
|
173
181
|
:greater_than_or_equal_to => Proc.new { |user| user.age },
|
174
182
|
:less_than_or_equal_to => Proc.new { |user| user.age + 100},
|
175
183
|
:only_integer => true
|
184
|
+
|
185
|
+
validates_format_of :country, :with => /\w+/
|
186
|
+
end
|
187
|
+
|
188
|
+
class HashBackedAuthor < Hash
|
189
|
+
extend ActiveModel::Naming
|
190
|
+
include ActiveModel::Conversion
|
191
|
+
|
192
|
+
def persisted?; false; end
|
193
|
+
|
194
|
+
def name
|
195
|
+
'hash backed author'
|
196
|
+
end
|
176
197
|
end
|