simple_form 3.1.0 → 5.0.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 +5 -5
- data/CHANGELOG.md +148 -0
- data/MIT-LICENSE +1 -1
- data/README.md +278 -68
- data/lib/generators/simple_form/install_generator.rb +1 -0
- data/lib/generators/simple_form/templates/README +3 -3
- data/lib/generators/simple_form/templates/_form.html.erb +2 -0
- data/lib/generators/simple_form/templates/_form.html.haml +2 -0
- data/lib/generators/simple_form/templates/_form.html.slim +1 -0
- data/lib/generators/simple_form/templates/config/initializers/simple_form.rb +19 -9
- data/lib/generators/simple_form/templates/config/initializers/simple_form_bootstrap.rb +367 -63
- data/lib/generators/simple_form/templates/config/initializers/simple_form_foundation.rb +23 -8
- data/lib/simple_form/action_view_extensions/builder.rb +1 -0
- data/lib/simple_form/action_view_extensions/form_helper.rb +4 -1
- data/lib/simple_form/components/errors.rb +15 -2
- data/lib/simple_form/components/hints.rb +1 -0
- data/lib/simple_form/components/html5.rb +15 -4
- data/lib/simple_form/components/label_input.rb +2 -1
- data/lib/simple_form/components/labels.rb +12 -5
- data/lib/simple_form/components/maxlength.rb +8 -4
- data/lib/simple_form/components/min_max.rb +1 -0
- data/lib/simple_form/components/minlength.rb +38 -0
- data/lib/simple_form/components/pattern.rb +1 -0
- data/lib/simple_form/components/placeholders.rb +2 -1
- data/lib/simple_form/components/readonly.rb +1 -0
- data/lib/simple_form/components.rb +2 -0
- data/lib/simple_form/error_notification.rb +1 -0
- data/lib/simple_form/form_builder.rb +117 -35
- data/lib/simple_form/helpers/autofocus.rb +1 -0
- data/lib/simple_form/helpers/disabled.rb +1 -0
- data/lib/simple_form/helpers/readonly.rb +1 -0
- data/lib/simple_form/helpers/required.rb +1 -0
- data/lib/simple_form/helpers/validators.rb +2 -1
- data/lib/simple_form/helpers.rb +1 -0
- data/lib/simple_form/i18n_cache.rb +1 -0
- data/lib/simple_form/inputs/base.rb +36 -12
- data/lib/simple_form/inputs/block_input.rb +1 -0
- data/lib/simple_form/inputs/boolean_input.rb +14 -3
- data/lib/simple_form/inputs/collection_check_boxes_input.rb +2 -1
- data/lib/simple_form/inputs/collection_input.rb +7 -5
- data/lib/simple_form/inputs/collection_radio_buttons_input.rb +3 -2
- data/lib/simple_form/inputs/collection_select_input.rb +1 -0
- data/lib/simple_form/inputs/color_input.rb +14 -0
- data/lib/simple_form/inputs/date_time_input.rb +13 -8
- data/lib/simple_form/inputs/file_input.rb +1 -0
- data/lib/simple_form/inputs/grouped_collection_select_input.rb +1 -0
- data/lib/simple_form/inputs/hidden_input.rb +1 -0
- data/lib/simple_form/inputs/numeric_input.rb +1 -0
- data/lib/simple_form/inputs/password_input.rb +2 -1
- data/lib/simple_form/inputs/priority_input.rb +1 -4
- data/lib/simple_form/inputs/range_input.rb +1 -0
- data/lib/simple_form/inputs/string_input.rb +3 -2
- data/lib/simple_form/inputs/text_input.rb +2 -1
- data/lib/simple_form/inputs.rb +2 -0
- data/lib/simple_form/map_type.rb +1 -0
- data/lib/simple_form/railtie.rb +1 -0
- data/lib/simple_form/tags.rb +7 -2
- data/lib/simple_form/version.rb +2 -1
- data/lib/simple_form/wrappers/builder.rb +1 -0
- data/lib/simple_form/wrappers/leaf.rb +2 -1
- data/lib/simple_form/wrappers/many.rb +1 -0
- data/lib/simple_form/wrappers/root.rb +2 -0
- data/lib/simple_form/wrappers/single.rb +2 -1
- data/lib/simple_form/wrappers.rb +1 -0
- data/lib/simple_form.rb +79 -14
- data/test/action_view_extensions/builder_test.rb +28 -9
- data/test/action_view_extensions/form_helper_test.rb +3 -2
- data/test/components/custom_components_test.rb +62 -0
- data/test/components/label_test.rb +33 -4
- data/test/form_builder/association_test.rb +33 -2
- data/test/form_builder/button_test.rb +1 -0
- data/test/form_builder/error_notification_test.rb +1 -0
- data/test/form_builder/error_test.rb +44 -9
- data/test/form_builder/general_test.rb +92 -20
- data/test/form_builder/hint_test.rb +6 -0
- data/test/form_builder/input_field_test.rb +76 -70
- data/test/form_builder/label_test.rb +27 -4
- data/test/form_builder/wrapper_test.rb +66 -14
- data/test/generators/simple_form_generator_test.rb +4 -3
- data/test/inputs/boolean_input_test.rb +35 -0
- data/test/inputs/collection_check_boxes_input_test.rb +38 -14
- data/test/inputs/collection_radio_buttons_input_test.rb +48 -24
- data/test/inputs/collection_select_input_test.rb +40 -39
- data/test/inputs/color_input_test.rb +10 -0
- data/test/inputs/datetime_input_test.rb +12 -8
- data/test/inputs/disabled_test.rb +14 -0
- data/test/inputs/discovery_test.rb +23 -0
- data/test/inputs/file_input_test.rb +1 -0
- data/test/inputs/general_test.rb +3 -2
- data/test/inputs/grouped_collection_select_input_test.rb +11 -10
- data/test/inputs/hidden_input_test.rb +1 -0
- data/test/inputs/numeric_input_test.rb +5 -1
- data/test/inputs/priority_input_test.rb +7 -6
- data/test/inputs/readonly_test.rb +1 -0
- data/test/inputs/required_test.rb +45 -0
- data/test/inputs/string_input_test.rb +18 -16
- data/test/inputs/text_input_test.rb +13 -0
- data/test/simple_form_test.rb +1 -0
- data/test/support/discovery_inputs.rb +8 -0
- data/test/support/misc_helpers.rb +44 -2
- data/test/support/mock_controller.rb +7 -1
- data/test/support/models.rb +105 -22
- data/test/test_helper.rb +14 -3
- metadata +42 -36
@@ -1,3 +1,4 @@
|
|
1
|
+
# frozen_string_literal: true
|
1
2
|
# encoding: UTF-8
|
2
3
|
require 'test_helper'
|
3
4
|
|
@@ -22,7 +23,7 @@ class CollectionSelectInputTest < ActionView::TestCase
|
|
22
23
|
end
|
23
24
|
|
24
25
|
test 'input allows overriding collection for select types' do
|
25
|
-
with_input_for @user, :name, :select, collection: [
|
26
|
+
with_input_for @user, :name, :select, collection: %w[Jose Carlos]
|
26
27
|
assert_select 'select.select#user_name'
|
27
28
|
assert_select 'select option', 'Jose'
|
28
29
|
assert_select 'select option', 'Carlos'
|
@@ -30,9 +31,9 @@ class CollectionSelectInputTest < ActionView::TestCase
|
|
30
31
|
|
31
32
|
test 'input does automatic collection translation for select types using defaults key' do
|
32
33
|
store_translations(:en, simple_form: { options: { defaults: {
|
33
|
-
gender: { male: 'Male', female: 'Female'}
|
34
|
+
gender: { male: 'Male', female: 'Female' }
|
34
35
|
} } }) do
|
35
|
-
with_input_for @user, :gender, :select, collection: [
|
36
|
+
with_input_for @user, :gender, :select, collection: %i[male female]
|
36
37
|
assert_select 'select.select#user_gender'
|
37
38
|
assert_select 'select option', 'Male'
|
38
39
|
assert_select 'select option', 'Female'
|
@@ -41,9 +42,9 @@ class CollectionSelectInputTest < ActionView::TestCase
|
|
41
42
|
|
42
43
|
test 'input does automatic collection translation for select types using specific object key' do
|
43
44
|
store_translations(:en, simple_form: { options: { user: {
|
44
|
-
gender: { male: 'Male', female: 'Female'}
|
45
|
+
gender: { male: 'Male', female: 'Female' }
|
45
46
|
} } }) do
|
46
|
-
with_input_for @user, :gender, :select, collection: [
|
47
|
+
with_input_for @user, :gender, :select, collection: %i[male female]
|
47
48
|
assert_select 'select.select#user_gender'
|
48
49
|
assert_select 'select option', 'Male'
|
49
50
|
assert_select 'select option', 'Female'
|
@@ -52,7 +53,7 @@ class CollectionSelectInputTest < ActionView::TestCase
|
|
52
53
|
|
53
54
|
test 'input marks the selected value by default' do
|
54
55
|
@user.name = "Carlos"
|
55
|
-
with_input_for @user, :name, :select, collection: [
|
56
|
+
with_input_for @user, :name, :select, collection: %w[Jose Carlos]
|
56
57
|
assert_select 'select option[selected=selected]', 'Carlos'
|
57
58
|
end
|
58
59
|
|
@@ -113,7 +114,7 @@ class CollectionSelectInputTest < ActionView::TestCase
|
|
113
114
|
|
114
115
|
test 'input translates include blank with a default' do
|
115
116
|
store_translations(:en, simple_form: { include_blanks: { defaults: {
|
116
|
-
age: 'Rather not say'
|
117
|
+
age: 'Rather not say'
|
117
118
|
} } }) do
|
118
119
|
with_input_for @user, :age, :select, collection: 18..30, include_blank: :translate
|
119
120
|
assert_select 'select option[value=""]', 'Rather not say'
|
@@ -182,7 +183,7 @@ class CollectionSelectInputTest < ActionView::TestCase
|
|
182
183
|
|
183
184
|
test 'input translates prompt with a default' do
|
184
185
|
store_translations(:en, simple_form: { prompts: { defaults: {
|
185
|
-
age: 'Select age:'
|
186
|
+
age: 'Select age:'
|
186
187
|
} } }) do
|
187
188
|
with_input_for @user, :age, :select, collection: 18..30, prompt: :translate
|
188
189
|
assert_select 'select option[value=""]', 'Select age:'
|
@@ -224,7 +225,7 @@ class CollectionSelectInputTest < ActionView::TestCase
|
|
224
225
|
end
|
225
226
|
|
226
227
|
test 'input disables the anothers components when the option is a object' do
|
227
|
-
with_input_for @user, :description, :select, collection: [
|
228
|
+
with_input_for @user, :description, :select, collection: %w[Jose Carlos], disabled: true
|
228
229
|
assert_no_select 'select option[value=Jose][disabled=disabled]', 'Jose'
|
229
230
|
assert_no_select 'select option[value=Carlos][disabled=disabled]', 'Carlos'
|
230
231
|
assert_select 'select[disabled=disabled]'
|
@@ -232,7 +233,7 @@ class CollectionSelectInputTest < ActionView::TestCase
|
|
232
233
|
end
|
233
234
|
|
234
235
|
test 'input does not disable the anothers components when the option is a object' do
|
235
|
-
with_input_for @user, :description, :select, collection: [
|
236
|
+
with_input_for @user, :description, :select, collection: %w[Jose Carlos], disabled: 'Jose'
|
236
237
|
assert_select 'select option[value=Jose][disabled=disabled]', 'Jose'
|
237
238
|
assert_no_select 'select option[value=Carlos][disabled=disabled]', 'Carlos'
|
238
239
|
assert_no_select 'select[disabled=disabled]'
|
@@ -241,126 +242,126 @@ class CollectionSelectInputTest < ActionView::TestCase
|
|
241
242
|
|
242
243
|
test 'input allows overriding label and value method using a lambda for collection selects' do
|
243
244
|
with_input_for @user, :name, :select,
|
244
|
-
collection: [
|
245
|
-
label_method:
|
246
|
-
value_method:
|
245
|
+
collection: %w[Jose Carlos],
|
246
|
+
label_method: ->(i) { i.upcase },
|
247
|
+
value_method: ->(i) { i.downcase }
|
247
248
|
assert_select 'select option[value=jose]', "JOSE"
|
248
249
|
assert_select 'select option[value=carlos]', "CARLOS"
|
249
250
|
end
|
250
251
|
|
251
252
|
test 'input allows overriding only label but not value method using a lambda for collection select' do
|
252
253
|
with_input_for @user, :name, :select,
|
253
|
-
collection: [
|
254
|
-
label_method:
|
254
|
+
collection: %w[Jose Carlos],
|
255
|
+
label_method: ->(i) { i.upcase }
|
255
256
|
assert_select 'select option[value=Jose]', "JOSE"
|
256
257
|
assert_select 'select option[value=Carlos]', "CARLOS"
|
257
258
|
end
|
258
259
|
|
259
260
|
test 'input allows overriding only value but not label method using a lambda for collection select' do
|
260
261
|
with_input_for @user, :name, :select,
|
261
|
-
collection: [
|
262
|
-
value_method:
|
262
|
+
collection: %w[Jose Carlos],
|
263
|
+
value_method: ->(i) { i.downcase }
|
263
264
|
assert_select 'select option[value=jose]', "Jose"
|
264
265
|
assert_select 'select option[value=carlos]', "Carlos"
|
265
266
|
end
|
266
267
|
|
267
268
|
test 'input allows symbols for collections' do
|
268
|
-
with_input_for @user, :name, :select, collection: [
|
269
|
+
with_input_for @user, :name, :select, collection: %i[jose carlos]
|
269
270
|
assert_select 'select.select#user_name'
|
270
271
|
assert_select 'select option[value=jose]', 'jose'
|
271
272
|
assert_select 'select option[value=carlos]', 'carlos'
|
272
273
|
end
|
273
274
|
|
274
275
|
test 'collection input with select type generates required html attribute only with blank option' do
|
275
|
-
with_input_for @user, :name, :select, include_blank: true, collection: [
|
276
|
+
with_input_for @user, :name, :select, include_blank: true, collection: %w[Jose Carlos]
|
276
277
|
assert_select 'select.required'
|
277
278
|
assert_select 'select[required]'
|
278
279
|
end
|
279
280
|
|
280
281
|
test 'collection input with select type generates required html attribute only with blank option or prompt' do
|
281
|
-
with_input_for @user, :name, :select, prompt: 'Name...', collection: [
|
282
|
+
with_input_for @user, :name, :select, prompt: 'Name...', collection: %w[Jose Carlos]
|
282
283
|
assert_select 'select.required'
|
283
284
|
assert_select 'select[required]'
|
284
285
|
end
|
285
286
|
|
286
287
|
test 'collection input with select type does not generate required html attribute without blank option' do
|
287
|
-
with_input_for @user, :name, :select, include_blank: false, collection: [
|
288
|
+
with_input_for @user, :name, :select, include_blank: false, collection: %w[Jose Carlos]
|
288
289
|
assert_select 'select.required'
|
289
290
|
assert_no_select 'select[required]'
|
290
291
|
assert_no_select 'select[aria-required=true]'
|
291
292
|
end
|
292
293
|
|
293
294
|
test 'collection input with select type with multiple attribute generates required html attribute without blank option' do
|
294
|
-
with_input_for @user, :name, :select, include_blank: false, input_html: { multiple: true }, collection: [
|
295
|
+
with_input_for @user, :name, :select, include_blank: false, input_html: { multiple: true }, collection: %w[Jose Carlos]
|
295
296
|
assert_select 'select.required'
|
296
297
|
assert_select 'select[required]'
|
297
298
|
end
|
298
299
|
|
299
300
|
test 'collection input with select type with multiple attribute generates required html attribute with blank option' do
|
300
|
-
with_input_for @user, :name, :select, include_blank: true, input_html: { multiple: true }, collection: [
|
301
|
+
with_input_for @user, :name, :select, include_blank: true, input_html: { multiple: true }, collection: %w[Jose Carlos]
|
301
302
|
assert_select 'select.required'
|
302
303
|
assert_select 'select[required]'
|
303
304
|
end
|
304
305
|
|
305
306
|
test 'with a blank option, a collection input of type select has an aria-required html attribute' do
|
306
|
-
with_input_for @user, :name, :select, include_blank: true, collection: [
|
307
|
+
with_input_for @user, :name, :select, include_blank: true, collection: %w[Jose Carlos]
|
307
308
|
assert_select 'select.required'
|
308
309
|
assert_select 'select[aria-required=true]'
|
309
310
|
end
|
310
311
|
|
311
312
|
test 'without a blank option, a collection input of type select does not have an aria-required html attribute' do
|
312
|
-
with_input_for @user, :name, :select, include_blank: false, collection: [
|
313
|
+
with_input_for @user, :name, :select, include_blank: false, collection: %w[Jose Carlos]
|
313
314
|
assert_select 'select.required'
|
314
315
|
assert_no_select 'select[aria-required]'
|
315
316
|
end
|
316
317
|
|
317
318
|
test 'without a blank option and with a multiple option, a collection input of type select has an aria-required html attribute' do
|
318
|
-
with_input_for @user, :name, :select, include_blank: false, input_html: { multiple: true }, collection: [
|
319
|
+
with_input_for @user, :name, :select, include_blank: false, input_html: { multiple: true }, collection: %w[Jose Carlos]
|
319
320
|
assert_select 'select.required'
|
320
321
|
assert_select 'select[aria-required=true]'
|
321
322
|
end
|
322
323
|
|
323
324
|
test 'with a blank option and a multiple option, a collection input of type select has an aria-required html attribute' do
|
324
|
-
with_input_for @user, :name, :select, include_blank: true, input_html: { multiple: true }, collection: [
|
325
|
+
with_input_for @user, :name, :select, include_blank: true, input_html: { multiple: true }, collection: %w[Jose Carlos]
|
325
326
|
assert_select 'select.required'
|
326
327
|
assert_select 'select[aria-required]'
|
327
328
|
end
|
328
329
|
|
329
330
|
test 'input allows disabled options with a lambda for collection select' do
|
330
|
-
with_input_for @user, :name, :select, collection: [
|
331
|
-
disabled:
|
331
|
+
with_input_for @user, :name, :select, collection: %w[Carlos Antonio],
|
332
|
+
disabled: ->(x) { x == "Carlos" }
|
332
333
|
assert_select 'select option[value=Carlos][disabled=disabled]', 'Carlos'
|
333
334
|
assert_select 'select option[value=Antonio]', 'Antonio'
|
334
335
|
assert_no_select 'select option[value=Antonio][disabled]'
|
335
336
|
end
|
336
337
|
|
337
338
|
test 'input allows disabled and label method with lambdas for collection select' do
|
338
|
-
with_input_for @user, :name, :select, collection: [
|
339
|
-
disabled:
|
339
|
+
with_input_for @user, :name, :select, collection: %w[Carlos Antonio],
|
340
|
+
disabled: ->(x) { x == "Carlos" }, label_method: ->(x) { x.upcase }
|
340
341
|
assert_select 'select option[value=Carlos][disabled=disabled]', 'CARLOS'
|
341
342
|
assert_select 'select option[value=Antonio]', 'ANTONIO'
|
342
343
|
assert_no_select 'select option[value=Antonio][disabled]'
|
343
344
|
end
|
344
345
|
|
345
346
|
test 'input allows a non lambda disabled option with lambda label method for collections' do
|
346
|
-
with_input_for @user, :name, :select, collection: [
|
347
|
-
disabled: "Carlos", label_method:
|
347
|
+
with_input_for @user, :name, :select, collection: %w[Carlos Antonio],
|
348
|
+
disabled: "Carlos", label_method: ->(x) { x.upcase }
|
348
349
|
assert_select 'select option[value=Carlos][disabled=disabled]', 'CARLOS'
|
349
350
|
assert_select 'select option[value=Antonio]', 'ANTONIO'
|
350
351
|
assert_no_select 'select option[value=Antonio][disabled]'
|
351
352
|
end
|
352
353
|
|
353
354
|
test 'input allows selected and label method with lambdas for collection select' do
|
354
|
-
with_input_for @user, :name, :select, collection: [
|
355
|
-
selected:
|
355
|
+
with_input_for @user, :name, :select, collection: %w[Carlos Antonio],
|
356
|
+
selected: ->(x) { x == "Carlos" }, label_method: ->(x) { x.upcase }
|
356
357
|
assert_select 'select option[value=Carlos][selected=selected]', 'CARLOS'
|
357
358
|
assert_select 'select option[value=Antonio]', 'ANTONIO'
|
358
359
|
assert_no_select 'select option[value=Antonio][selected]'
|
359
360
|
end
|
360
361
|
|
361
362
|
test 'input allows a non lambda selected option with lambda label method for collection select' do
|
362
|
-
with_input_for @user, :name, :select, collection: [
|
363
|
-
selected: "Carlos", label_method:
|
363
|
+
with_input_for @user, :name, :select, collection: %w[Carlos Antonio],
|
364
|
+
selected: "Carlos", label_method: ->(x) { x.upcase }
|
364
365
|
assert_select 'select option[value=Carlos][selected=selected]', 'CARLOS'
|
365
366
|
assert_select 'select option[value=Antonio]', 'ANTONIO'
|
366
367
|
assert_no_select 'select option[value=Antonio][selected]'
|
@@ -368,8 +369,8 @@ class CollectionSelectInputTest < ActionView::TestCase
|
|
368
369
|
|
369
370
|
test 'input does not override default selection through attribute value with label method as lambda for collection select' do
|
370
371
|
@user.name = "Carlos"
|
371
|
-
with_input_for @user, :name, :select, collection: [
|
372
|
-
label_method:
|
372
|
+
with_input_for @user, :name, :select, collection: %w[Carlos Antonio],
|
373
|
+
label_method: ->(x) { x.upcase }
|
373
374
|
assert_select 'select option[value=Carlos][selected=selected]', 'CARLOS'
|
374
375
|
assert_select 'select option[value=Antonio]', 'ANTONIO'
|
375
376
|
assert_no_select 'select option[value=Antonio][selected]'
|
@@ -0,0 +1,10 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'test_helper'
|
4
|
+
|
5
|
+
class ColorInputTest < ActionView::TestCase
|
6
|
+
test 'input generates a color field' do
|
7
|
+
with_input_for @user, :favorite_color, :color
|
8
|
+
assert_select 'input[type=color].color#user_favorite_color'
|
9
|
+
end
|
10
|
+
end
|
@@ -1,3 +1,4 @@
|
|
1
|
+
# frozen_string_literal: true
|
1
2
|
# encoding: UTF-8
|
2
3
|
require 'test_helper'
|
3
4
|
|
@@ -5,8 +6,7 @@ require 'test_helper'
|
|
5
6
|
class DateTimeInputWithHtml5Test < ActionView::TestCase
|
6
7
|
test 'input generates a datetime input for datetime attributes if HTML5 compatibility is explicitly enbled' do
|
7
8
|
with_input_for @user, :created_at, :datetime, html5: true
|
8
|
-
|
9
|
-
assert_select 'input[type="datetime"]'
|
9
|
+
assert_select 'input[type="datetime-local"]'
|
10
10
|
end
|
11
11
|
|
12
12
|
test 'input generates a datetime select for datetime attributes' do
|
@@ -75,8 +75,7 @@ class DateTimeInputWithoutHtml5Test < ActionView::TestCase
|
|
75
75
|
test 'input generates a datetime input for datetime attributes if HTML5 compatibility is explicitly enabled' do
|
76
76
|
swap_wrapper do
|
77
77
|
with_input_for @user, :created_at, :datetime, html5: true
|
78
|
-
|
79
|
-
assert_select 'input[type="datetime"]'
|
78
|
+
assert_select 'input[type="datetime-local"]'
|
80
79
|
end
|
81
80
|
end
|
82
81
|
|
@@ -142,26 +141,26 @@ class DateTimeInputWithoutHtml5Test < ActionView::TestCase
|
|
142
141
|
end
|
143
142
|
|
144
143
|
test 'label uses i18n to get target for date input type' do
|
145
|
-
store_translations(:en, date: { order: [
|
144
|
+
store_translations(:en, date: { order: %w[month day year] }) do
|
146
145
|
with_input_for :project, :created_at, :date, html5: false
|
147
146
|
assert_select 'label[for=project_created_at_2i]'
|
148
147
|
end
|
149
148
|
end
|
150
149
|
|
151
150
|
test 'label uses i18n to get target for datetime input type' do
|
152
|
-
store_translations(:en, date: { order: [
|
151
|
+
store_translations(:en, date: { order: %w[month day year] }) do
|
153
152
|
with_input_for :project, :created_at, :datetime, html5: false
|
154
153
|
assert_select 'label[for=project_created_at_2i]'
|
155
154
|
end
|
156
155
|
end
|
157
156
|
|
158
157
|
test 'label uses order to get target when date input type' do
|
159
|
-
with_input_for :project, :created_at, :date, order: [
|
158
|
+
with_input_for :project, :created_at, :date, order: %w[month year day], html5: false
|
160
159
|
assert_select 'label[for=project_created_at_2i]'
|
161
160
|
end
|
162
161
|
|
163
162
|
test 'label uses order to get target when datetime input type' do
|
164
|
-
with_input_for :project, :created_at, :datetime, order: [
|
163
|
+
with_input_for :project, :created_at, :datetime, order: %w[month year day], html5: false
|
165
164
|
assert_select 'label[for=project_created_at_2i]'
|
166
165
|
end
|
167
166
|
|
@@ -169,4 +168,9 @@ class DateTimeInputWithoutHtml5Test < ActionView::TestCase
|
|
169
168
|
with_input_for :project, :created_at, :time, html5: false
|
170
169
|
assert_select 'label[for=project_created_at_4i]'
|
171
170
|
end
|
171
|
+
|
172
|
+
test 'label points to attribute name if HTML5 compatibility is explicitly enabled' do
|
173
|
+
with_input_for :project, :created_at, :date, html5: true
|
174
|
+
assert_select 'label[for=project_created_at]'
|
175
|
+
end
|
172
176
|
end
|
@@ -1,3 +1,4 @@
|
|
1
|
+
# frozen_string_literal: true
|
1
2
|
require 'test_helper'
|
2
3
|
|
3
4
|
class DisabledTest < ActionView::TestCase
|
@@ -75,4 +76,17 @@ class DisabledTest < ActionView::TestCase
|
|
75
76
|
with_input_for @user, :created_at, :datetime
|
76
77
|
assert_no_select 'select.datetime.disabled[disabled]'
|
77
78
|
end
|
79
|
+
|
80
|
+
test 'input_field collection allows disabled select' do
|
81
|
+
with_input_field_for @user, :description, collection: ['foo', 'bar'], disabled: true
|
82
|
+
assert_select 'select[disabled]'
|
83
|
+
assert_no_select 'option[disabled]'
|
84
|
+
end
|
85
|
+
|
86
|
+
test 'input_field collection allows individual disabled options' do
|
87
|
+
with_input_field_for @user, :description, collection: ['foo', 'bar'], disabled: 'bar'
|
88
|
+
assert_no_select 'select[disabled]'
|
89
|
+
assert_no_select 'option[disabled][value=foo]'
|
90
|
+
assert_select 'option[disabled][value=bar]'
|
91
|
+
end
|
78
92
|
end
|
@@ -1,3 +1,4 @@
|
|
1
|
+
# frozen_string_literal: true
|
1
2
|
require 'test_helper'
|
2
3
|
|
3
4
|
class DiscoveryTest < ActionView::TestCase
|
@@ -14,6 +15,8 @@ class DiscoveryTest < ActionView::TestCase
|
|
14
15
|
Object.send :remove_const, :CustomizedInput
|
15
16
|
Object.send :remove_const, :DeprecatedInput
|
16
17
|
Object.send :remove_const, :CollectionSelectInput
|
18
|
+
Object.send :remove_const, :FileInput
|
19
|
+
CustomInputs.send :remove_const, :CustomizedInput
|
17
20
|
CustomInputs.send :remove_const, :PasswordInput
|
18
21
|
CustomInputs.send :remove_const, :NumericInput
|
19
22
|
end
|
@@ -107,6 +110,26 @@ class DiscoveryTest < ActionView::TestCase
|
|
107
110
|
end
|
108
111
|
end
|
109
112
|
|
113
|
+
test 'does not duplicate the html classes giving a extra class' do
|
114
|
+
discovery do
|
115
|
+
swap SimpleForm, input_class: 'custom-default-input-class' do
|
116
|
+
with_form_for @user, :active, as: :select
|
117
|
+
assert_select 'form select#user_active.select' do
|
118
|
+
# Make sure class list contains 'chosen' only once.
|
119
|
+
assert_select ":match('class', ?)", /^(?!.*\bchosen\b.*\bchosen\b).*\bchosen\b.*$/
|
120
|
+
end
|
121
|
+
end
|
122
|
+
end
|
123
|
+
end
|
124
|
+
|
125
|
+
test 'new inputs can override the default input_html_classes' do
|
126
|
+
discovery do
|
127
|
+
with_form_for @user, :avatar, as: :file
|
128
|
+
assert_no_select 'form input[type=file]#user_avatar.file.file-upload'
|
129
|
+
assert_select 'form input[type=file]#user_avatar.file-upload'
|
130
|
+
end
|
131
|
+
end
|
132
|
+
|
110
133
|
test 'inputs method without wrapper_options are deprecated' do
|
111
134
|
discovery do
|
112
135
|
assert_deprecated do
|
data/test/inputs/general_test.rb
CHANGED
@@ -1,3 +1,4 @@
|
|
1
|
+
# frozen_string_literal: true
|
1
2
|
# encoding: UTF-8
|
2
3
|
require 'test_helper'
|
3
4
|
|
@@ -119,12 +120,12 @@ class InputTest < ActionView::TestCase
|
|
119
120
|
end
|
120
121
|
|
121
122
|
test 'input as select with collection is generated properly when object is not present' do
|
122
|
-
with_input_for :project, :name, :select, collection: [
|
123
|
+
with_input_for :project, :name, :select, collection: %w[Jose Carlos]
|
123
124
|
assert_select 'select.select#project_name'
|
124
125
|
end
|
125
126
|
|
126
127
|
test 'input does not generate empty css class' do
|
127
|
-
swap SimpleForm, generate_additional_classes_for: [
|
128
|
+
swap SimpleForm, generate_additional_classes_for: %i[wrapper label] do
|
128
129
|
with_input_for :project, :name, :string
|
129
130
|
assert_no_select 'input#project_name[class]'
|
130
131
|
end
|
@@ -1,10 +1,11 @@
|
|
1
|
+
# frozen_string_literal: true
|
1
2
|
# encoding: UTF-8
|
2
3
|
require 'test_helper'
|
3
4
|
|
4
5
|
class GroupedCollectionSelectInputTest < ActionView::TestCase
|
5
6
|
test 'grouped collection accepts array collection form' do
|
6
7
|
with_input_for @user, :tag_ids, :grouped_select,
|
7
|
-
collection: [['Authors', [
|
8
|
+
collection: [['Authors', %w[Jose Carlos]], ['General', %w[Bob John]]],
|
8
9
|
group_method: :last
|
9
10
|
|
10
11
|
assert_select 'select.grouped_select#user_tag_ids' do
|
@@ -31,7 +32,7 @@ class GroupedCollectionSelectInputTest < ActionView::TestCase
|
|
31
32
|
|
32
33
|
test 'grouped collection accepts proc as collection' do
|
33
34
|
with_input_for @user, :tag_ids, :grouped_select,
|
34
|
-
collection:
|
35
|
+
collection: proc { [['Authors', %w[Jose Carlos]], ['General', %w[Bob John]]] },
|
35
36
|
group_method: :last
|
36
37
|
|
37
38
|
assert_select 'select.grouped_select#user_tag_ids' do
|
@@ -49,7 +50,7 @@ class GroupedCollectionSelectInputTest < ActionView::TestCase
|
|
49
50
|
|
50
51
|
test 'grouped collection accepts hash collection form' do
|
51
52
|
with_input_for @user, :tag_ids, :grouped_select,
|
52
|
-
collection: {
|
53
|
+
collection: { Authors: %w[Jose Carlos], General: %w[Bob John] },
|
53
54
|
group_method: :last
|
54
55
|
|
55
56
|
assert_select 'select.grouped_select#user_tag_ids' do
|
@@ -67,7 +68,7 @@ class GroupedCollectionSelectInputTest < ActionView::TestCase
|
|
67
68
|
|
68
69
|
test 'grouped collection accepts group_label_method option' do
|
69
70
|
with_input_for @user, :tag_ids, :grouped_select,
|
70
|
-
collection: { [
|
71
|
+
collection: { %w[Jose Carlos] => 'Authors' },
|
71
72
|
group_method: :first,
|
72
73
|
group_label_method: :last
|
73
74
|
|
@@ -80,7 +81,7 @@ class GroupedCollectionSelectInputTest < ActionView::TestCase
|
|
80
81
|
end
|
81
82
|
|
82
83
|
test 'grouped collection finds default label methods on the group objects' do
|
83
|
-
option_list = [
|
84
|
+
option_list = %w[Jose Carlos]
|
84
85
|
|
85
86
|
GroupedClass = Struct.new(:to_label, :options)
|
86
87
|
group = GroupedClass.new("Authors", option_list)
|
@@ -117,7 +118,7 @@ class GroupedCollectionSelectInputTest < ActionView::TestCase
|
|
117
118
|
|
118
119
|
test 'grouped collection accepts label and value methods options' do
|
119
120
|
with_input_for @user, :tag_ids, :grouped_select,
|
120
|
-
collection: {
|
121
|
+
collection: { Authors: %w[Jose Carlos] },
|
121
122
|
group_method: :last,
|
122
123
|
label_method: :upcase,
|
123
124
|
value_method: :downcase
|
@@ -132,10 +133,10 @@ class GroupedCollectionSelectInputTest < ActionView::TestCase
|
|
132
133
|
|
133
134
|
test 'grouped collection allows overriding label and value methods using a lambda' do
|
134
135
|
with_input_for @user, :tag_ids, :grouped_select,
|
135
|
-
collection: {
|
136
|
+
collection: { Authors: %w[Jose Carlos] },
|
136
137
|
group_method: :last,
|
137
|
-
label_method:
|
138
|
-
value_method:
|
138
|
+
label_method: ->(i) { i.upcase },
|
139
|
+
value_method: ->(i) { i.downcase }
|
139
140
|
|
140
141
|
assert_select 'select.grouped_select#user_tag_ids' do
|
141
142
|
assert_select 'optgroup[label=Authors]' do
|
@@ -148,7 +149,7 @@ class GroupedCollectionSelectInputTest < ActionView::TestCase
|
|
148
149
|
test 'grouped collection with associations' do
|
149
150
|
tag_groups = [
|
150
151
|
TagGroup.new(1, "Group of Tags", [Tag.new(1, "Tag 1"), Tag.new(2, "Tag 2")]),
|
151
|
-
TagGroup.new(2, "Other group", [Tag.new(3, "Tag 3"), Tag.new(4,"Tag 4")])
|
152
|
+
TagGroup.new(2, "Other group", [Tag.new(3, "Tag 3"), Tag.new(4, "Tag 4")])
|
152
153
|
]
|
153
154
|
|
154
155
|
with_input_for @user, :tag_ids, :grouped_select,
|
@@ -1,3 +1,4 @@
|
|
1
|
+
# frozen_string_literal: true
|
1
2
|
# encoding: UTF-8
|
2
3
|
require 'test_helper'
|
3
4
|
|
@@ -113,6 +114,9 @@ class NumericInputTest < ActionView::TestCase
|
|
113
114
|
|
114
115
|
with_input_for @validating_user, :age, :integer
|
115
116
|
assert_select 'input[step="1"]'
|
117
|
+
|
118
|
+
with_input_for @validating_user, :age, :integer, as: :decimal, input_html: { step: 0.5 }
|
119
|
+
assert_select 'input[step="0.5"]'
|
116
120
|
end
|
117
121
|
|
118
122
|
test 'numeric input does not generate placeholder by default' do
|
@@ -153,7 +157,7 @@ class NumericInputTest < ActionView::TestCase
|
|
153
157
|
end
|
154
158
|
end
|
155
159
|
|
156
|
-
[
|
160
|
+
%i[integer float decimal].each do |type|
|
157
161
|
test "#{type} input infers min value from attributes with greater than or equal validation" do
|
158
162
|
with_input_for @validating_user, :age, type
|
159
163
|
assert_select 'input[min="18"]'
|
@@ -1,3 +1,4 @@
|
|
1
|
+
# frozen_string_literal: true
|
1
2
|
# encoding: UTF-8
|
2
3
|
require 'test_helper'
|
3
4
|
|
@@ -5,14 +6,14 @@ class PriorityInputTest < ActionView::TestCase
|
|
5
6
|
test 'input generates a country select field' do
|
6
7
|
with_input_for @user, :country, :country
|
7
8
|
assert_select 'select#user_country'
|
8
|
-
assert_select 'select option[value=
|
9
|
+
assert_select 'select option[value=BR]', 'Brazil'
|
9
10
|
assert_no_select 'select option[value=""][disabled=disabled]'
|
10
11
|
end
|
11
12
|
|
12
13
|
test 'input generates a country select with SimpleForm default' do
|
13
14
|
swap SimpleForm, country_priority: [ 'Brazil' ] do
|
14
15
|
with_input_for @user, :country, :country
|
15
|
-
assert_select 'select option[value=""][disabled=disabled]'
|
16
|
+
assert_select 'select option[value="---------------"][disabled=disabled]'
|
16
17
|
end
|
17
18
|
end
|
18
19
|
|
@@ -35,15 +36,15 @@ class PriorityInputTest < ActionView::TestCase
|
|
35
36
|
assert_no_select 'select option[value=""]', /^$/
|
36
37
|
end
|
37
38
|
|
38
|
-
test 'priority input does
|
39
|
+
test 'priority input does generate select element with required html attribute' do
|
39
40
|
with_input_for @user, :country, :country
|
40
41
|
assert_select 'select.required'
|
41
|
-
|
42
|
+
assert_select 'select[required]'
|
42
43
|
end
|
43
44
|
|
44
|
-
test 'priority input does
|
45
|
+
test 'priority input does generate select element with aria-required html attribute' do
|
45
46
|
with_input_for @user, :country, :country
|
46
47
|
assert_select 'select.required'
|
47
|
-
|
48
|
+
assert_select 'select[aria-required]'
|
48
49
|
end
|
49
50
|
end
|
@@ -1,3 +1,4 @@
|
|
1
|
+
# frozen_string_literal: true
|
1
2
|
require 'test_helper'
|
2
3
|
|
3
4
|
class RequiredTest < ActionView::TestCase
|
@@ -34,6 +35,38 @@ class RequiredTest < ActionView::TestCase
|
|
34
35
|
with_input_for @user, :name, :string
|
35
36
|
assert_select 'input[type=text].required'
|
36
37
|
assert_no_select 'input[type=text][required]'
|
38
|
+
assert_no_select 'input[type=text][aria-required]'
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
test 'when not using browser validations, when required option is set to false, input does not generate required html attribute' do
|
43
|
+
swap SimpleForm, browser_validations: false do
|
44
|
+
with_input_for @user, :name, :string, required: false
|
45
|
+
assert_no_select 'input[type=text].required'
|
46
|
+
assert_no_select 'input[type=text][required]'
|
47
|
+
assert_no_select 'input[type=text][aria-required]'
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
51
|
+
test 'when not using browser validations, when required option is set to true, input generates required html attribute' do
|
52
|
+
swap SimpleForm, browser_validations: false do
|
53
|
+
with_input_for @user, :name, :string, required: true
|
54
|
+
assert_select 'input[type=text].required'
|
55
|
+
assert_select 'input[type=text][required]'
|
56
|
+
assert_select 'input[type=text][aria-required]'
|
57
|
+
end
|
58
|
+
end
|
59
|
+
|
60
|
+
test 'when not using browser validations, when required option is true in the wrapper, input does not generate required html attribute' do
|
61
|
+
swap SimpleForm, browser_validations: false do
|
62
|
+
swap_wrapper :default, self.custom_wrapper_with_required_input do
|
63
|
+
with_concat_form_for(@user) do |f|
|
64
|
+
concat f.input :name
|
65
|
+
end
|
66
|
+
assert_select 'input[type=text].required'
|
67
|
+
assert_no_select 'input[type=text][required]'
|
68
|
+
assert_no_select 'input[type=text][aria-required]'
|
69
|
+
end
|
37
70
|
end
|
38
71
|
end
|
39
72
|
|
@@ -110,4 +143,16 @@ class RequiredTest < ActionView::TestCase
|
|
110
143
|
assert_no_select 'input[required]'
|
111
144
|
assert_select 'input.optional#validating_user_phone_number'
|
112
145
|
end
|
146
|
+
|
147
|
+
test 'builder input does not generate required html attribute when option is set to false when it is set to true in wrapper' do
|
148
|
+
swap SimpleForm, browser_validations: true do
|
149
|
+
swap_wrapper :default, self.custom_wrapper_with_required_input do
|
150
|
+
with_concat_form_for(@user) do |f|
|
151
|
+
concat f.input :name, required: false
|
152
|
+
end
|
153
|
+
assert_no_select 'input[type=text][required]'
|
154
|
+
assert_no_select 'input[type=text][aria-required]'
|
155
|
+
end
|
156
|
+
end
|
157
|
+
end
|
113
158
|
end
|