simple_form 3.2.1 → 3.3.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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +15 -1
- data/MIT-LICENSE +1 -1
- data/README.md +19 -15
- data/lib/generators/simple_form/templates/config/initializers/simple_form_bootstrap.rb +0 -0
- data/lib/simple_form.rb +0 -4
- data/lib/simple_form/action_view_extensions/form_helper.rb +3 -1
- data/lib/simple_form/components/html5.rb +12 -2
- data/lib/simple_form/components/maxlength.rb +17 -4
- data/lib/simple_form/form_builder.rb +12 -5
- data/lib/simple_form/inputs/base.rb +9 -4
- data/lib/simple_form/inputs/boolean_input.rb +5 -0
- data/lib/simple_form/version.rb +1 -1
- data/test/form_builder/error_test.rb +24 -1
- data/test/form_builder/general_test.rb +5 -1
- data/test/form_builder/input_field_test.rb +6 -0
- data/test/form_builder/label_test.rb +7 -0
- data/test/form_builder/wrapper_test.rb +32 -0
- data/test/inputs/boolean_input_test.rb +8 -0
- data/test/inputs/datetime_input_test.rb +10 -2
- data/test/inputs/discovery_test.rb +1 -0
- data/test/inputs/numeric_input_test.rb +3 -0
- data/test/inputs/priority_input_test.rb +10 -2
- data/test/inputs/required_test.rb +32 -0
- data/test/inputs/string_input_test.rb +5 -3
- data/test/support/misc_helpers.rb +14 -0
- data/test/support/models.rb +30 -5
- metadata +3 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: c12e271b03625f2cca73aaf99d1229e212d549b5
|
4
|
+
data.tar.gz: baa9c72a065dda6000b52852edaafc5f60e38a30
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 625bb4d60627789d65f73dcc2d5aafc7159cb9b66c12a911b6e0ef832075cf3b330d2636b97aa17f8f93037ef2d917b03cf2926ead2b6091a389fd6e3ed22b43
|
7
|
+
data.tar.gz: 139633282c1518a82841c62cedf6451a983a5058ed6d865f6a295874dac8e9156932b95490e4d3dada97d85c685c9c687a7a25bb926bcd75f3aef00252e33f4b
|
data/CHANGELOG.md
CHANGED
@@ -1,6 +1,20 @@
|
|
1
|
+
## Unreleased
|
2
|
+
|
3
|
+
## 3.3.0
|
4
|
+
|
5
|
+
### enhancements
|
6
|
+
* Add the `aria-invalid` attribute on inputs with errors.
|
7
|
+
* Added support for the new `ActiveModel::Type` API over Active Record's
|
8
|
+
column objects.
|
9
|
+
|
10
|
+
### bug fix
|
11
|
+
* Fix `merge_wrapper_options` to correctly merge options with duplicated keys. [@herminiotorres](https://github.com/herminiotorres)
|
12
|
+
Closes [#1278](https://github.com/plataformatec/simple_form/issues/1278).
|
13
|
+
|
1
14
|
## 3.2.1
|
2
15
|
|
3
|
-
|
16
|
+
### enhancements
|
17
|
+
* Updated gem dependency to support Rails 5.0.x.
|
4
18
|
|
5
19
|
## 3.2.0
|
6
20
|
|
data/MIT-LICENSE
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
Copyright (c) 2009-
|
1
|
+
Copyright (c) 2009-2016 Plataformatec http://plataformatec.com.br/
|
2
2
|
|
3
3
|
Permission is hereby granted, free of charge, to any person obtaining
|
4
4
|
a copy of this software and associated documentation files (the
|
data/README.md
CHANGED
@@ -164,8 +164,9 @@ any html attribute to that wrapper as well using the `:wrapper_html` option, lik
|
|
164
164
|
|
165
165
|
Required fields are marked with an * prepended to their labels.
|
166
166
|
|
167
|
-
By default all inputs are required. When the form object
|
168
|
-
|
167
|
+
By default all inputs are required. When the form object includes `ActiveModel::Validations`
|
168
|
+
(which, for example, happens with Active Record models), fields are required only when there is `presence` validation.
|
169
|
+
Otherwise, **Simple Form** will mark fields as optional. For performance reasons, this
|
169
170
|
detection is skipped on validations that make use of conditional options, such as `:if` and `:unless`.
|
170
171
|
|
171
172
|
And of course, the `required` property of any input can be overwritten as needed:
|
@@ -323,14 +324,17 @@ Collection inputs accept two other options beside collections:
|
|
323
324
|
|
324
325
|
Those methods are useful to manipulate the given collection. Both of these options also accept
|
325
326
|
lambda/procs in case you want to calculate the value or label in a special way eg. custom
|
326
|
-
translation.
|
327
|
-
|
327
|
+
translation. You can also define a `to_label` method on your model as **Simple Form** will search for
|
328
|
+
and use `:to_label` as a `:label_method` first if it is found. All other options given are sent
|
329
|
+
straight to the underlying helper. For example, you can give prompt as:
|
328
330
|
|
329
331
|
```ruby
|
330
332
|
f.input :age, collection: 18..60, prompt: "Select your age", selected: 21
|
331
333
|
```
|
332
334
|
Extra options are passed into helper [`collection_select`](http://api.rubyonrails.org/classes/ActionView/Helpers/FormOptionsHelper.html#method-i-collection_select).
|
333
335
|
|
336
|
+
You may also find it useful to explicitly pass a value to the optional `:selected`, especially if passing a collection of nested objects.
|
337
|
+
|
334
338
|
It is also possible to create grouped collection selects, that will use the html *optgroup* tags, like this:
|
335
339
|
|
336
340
|
```ruby
|
@@ -679,7 +683,7 @@ en:
|
|
679
683
|
age: 'Rather not say'
|
680
684
|
prompts:
|
681
685
|
user:
|
682
|
-
|
686
|
+
role: 'Select your role'
|
683
687
|
```
|
684
688
|
|
685
689
|
And your forms will use this information to render the components for you.
|
@@ -734,16 +738,16 @@ For `:prompt` and `:include_blank` the I18n lookup is optional and to enable it
|
|
734
738
|
`:translate` as value.
|
735
739
|
|
736
740
|
```ruby
|
737
|
-
f.input :
|
741
|
+
f.input :role, prompt: :translate
|
738
742
|
```
|
739
743
|
|
740
744
|
**Simple Form** also has support for translating options in collection helpers. For instance, given a
|
741
|
-
User with a `:
|
742
|
-
that would post either `
|
745
|
+
User with a `:role` attribute, you might want to create a select box showing translated labels
|
746
|
+
that would post either `:admin` or `:editor` as value. With **Simple Form** you could create an input
|
743
747
|
like this:
|
744
748
|
|
745
749
|
```ruby
|
746
|
-
f.input :
|
750
|
+
f.input :role, collection: [:admin, :editor]
|
747
751
|
```
|
748
752
|
|
749
753
|
And **Simple Form** will try a lookup like this in your locale file, to find the right labels to show:
|
@@ -753,9 +757,9 @@ en:
|
|
753
757
|
simple_form:
|
754
758
|
options:
|
755
759
|
user:
|
756
|
-
|
757
|
-
|
758
|
-
|
760
|
+
role:
|
761
|
+
admin: 'Administrator'
|
762
|
+
editor: 'Editor'
|
759
763
|
```
|
760
764
|
|
761
765
|
You can also use the `defaults` key as you would do with labels, hints and placeholders. It is
|
@@ -982,8 +986,8 @@ required attribute to force a value into an input and will prevent form submissi
|
|
982
986
|
Depending on the design of the application this may or may not be desired. In many cases it can
|
983
987
|
break existing UI's.
|
984
988
|
|
985
|
-
It is possible to disable all HTML 5 extensions in **Simple Form** removing the `html5`
|
986
|
-
from the wrapper used to render the inputs.
|
989
|
+
It is possible to disable all HTML 5 extensions in **Simple Form** by removing the `html5`
|
990
|
+
component from the wrapper used to render the inputs.
|
987
991
|
|
988
992
|
For example, change:
|
989
993
|
|
@@ -1072,7 +1076,7 @@ https://github.com/plataformatec/simple_form/issues
|
|
1072
1076
|
|
1073
1077
|
## License
|
1074
1078
|
|
1075
|
-
MIT License. Copyright 2009-
|
1079
|
+
MIT License. Copyright 2009-2016 Plataformatec. http://plataformatec.com.br
|
1076
1080
|
|
1077
1081
|
You are not granted rights or licenses to the trademarks of the Plataformatec, including without
|
1078
1082
|
limitation the Simple Form name or logo.
|
File without changes
|
data/lib/simple_form.rb
CHANGED
@@ -152,10 +152,6 @@ See https://github.com/plataformatec/simple_form/pull/997 for more information.
|
|
152
152
|
mattr_accessor :country_priority
|
153
153
|
@@country_priority = nil
|
154
154
|
|
155
|
-
# DEPRECATED: Maximum size allowed for inputs.
|
156
|
-
mattr_accessor :default_input_size
|
157
|
-
@@default_input_size = nil
|
158
|
-
|
159
155
|
# When off, do not use translations in labels. Disabling translation in
|
160
156
|
# hints and placeholders can be done manually in the wrapper API.
|
161
157
|
mattr_accessor :translate_labels
|
@@ -8,8 +8,10 @@ module SimpleForm
|
|
8
8
|
def html5(wrapper_options = nil)
|
9
9
|
@html5 = true
|
10
10
|
|
11
|
-
input_html_options[:required] =
|
12
|
-
input_html_options[:'aria-required'] =
|
11
|
+
input_html_options[:required] = input_html_required_option
|
12
|
+
input_html_options[:'aria-required'] = input_html_aria_required_option
|
13
|
+
|
14
|
+
input_html_options[:'aria-invalid'] = has_errors? || nil
|
13
15
|
|
14
16
|
nil
|
15
17
|
end
|
@@ -18,6 +20,14 @@ module SimpleForm
|
|
18
20
|
@html5
|
19
21
|
end
|
20
22
|
|
23
|
+
def input_html_required_option
|
24
|
+
!options[:required].nil? ? required_field? : has_required?
|
25
|
+
end
|
26
|
+
|
27
|
+
def input_html_aria_required_option
|
28
|
+
!options[:required].nil? ? (required_field? || nil) : (has_required? || nil)
|
29
|
+
end
|
30
|
+
|
21
31
|
def has_required?
|
22
32
|
# We need to check browser_validations because
|
23
33
|
# some browsers are still checking required even
|
@@ -15,10 +15,7 @@ module SimpleForm
|
|
15
15
|
maxlength
|
16
16
|
else
|
17
17
|
length_validator = find_length_validator
|
18
|
-
|
19
|
-
if length_validator && !has_tokenizer?(length_validator)
|
20
|
-
length_validator.options[:is] || length_validator.options[:maximum]
|
21
|
-
end
|
18
|
+
maximum_length_value_from(length_validator)
|
22
19
|
end
|
23
20
|
end
|
24
21
|
|
@@ -29,6 +26,22 @@ module SimpleForm
|
|
29
26
|
def has_tokenizer?(length_validator)
|
30
27
|
length_validator.options[:tokenizer]
|
31
28
|
end
|
29
|
+
|
30
|
+
# Use validation with tokenizer if version of Rails is less than 5,
|
31
|
+
# if not validate without the tokenizer, if version is greater than Rails 4.
|
32
|
+
if ActionPack::VERSION::STRING < '5'
|
33
|
+
def maximum_length_value_from(length_validator)
|
34
|
+
if length_validator && !has_tokenizer?(length_validator)
|
35
|
+
length_validator.options[:is] || length_validator.options[:maximum]
|
36
|
+
end
|
37
|
+
end
|
38
|
+
elsif ActionPack::VERSION::STRING >= '5'
|
39
|
+
def maximum_length_value_from(length_validator)
|
40
|
+
if length_validator
|
41
|
+
length_validator.options[:is] || length_validator.options[:maximum]
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
32
45
|
end
|
33
46
|
end
|
34
47
|
end
|
@@ -48,6 +48,11 @@ module SimpleForm
|
|
48
48
|
# label + input + hint (when defined) + errors (when exists), and all can
|
49
49
|
# be configured inside a wrapper html.
|
50
50
|
#
|
51
|
+
# If a block is given, the contents of the block will replace the input
|
52
|
+
# field that would otherwise be generated automatically. The content will
|
53
|
+
# be given a label and wrapper div to make it consistent with the other
|
54
|
+
# elements in the form.
|
55
|
+
#
|
51
56
|
# == Examples
|
52
57
|
#
|
53
58
|
# # Imagine @user has error "can't be blank" on name
|
@@ -135,7 +140,7 @@ module SimpleForm
|
|
135
140
|
components = (wrapper.components.map(&:namespace) & ATTRIBUTE_COMPONENTS)
|
136
141
|
|
137
142
|
options = options.dup
|
138
|
-
options[:input_html] = options.except(:as, :boolean_style, :collection, :label_method, :value_method, *components)
|
143
|
+
options[:input_html] = options.except(:as, :boolean_style, :collection, :label_method, :value_method, :prompt, *components)
|
139
144
|
options = @defaults.deep_dup.deep_merge(options) if @defaults
|
140
145
|
|
141
146
|
input = find_input(attribute_name, options)
|
@@ -285,7 +290,7 @@ module SimpleForm
|
|
285
290
|
#
|
286
291
|
# f.label :name # Do I18n lookup
|
287
292
|
# f.label :name, "Name" # Same behavior as Rails, do not add required tag
|
288
|
-
# f.label :name, label: "Name"
|
293
|
+
# f.label :name, label: "Name" # Same as above, but adds required tag
|
289
294
|
#
|
290
295
|
# f.label :name, required: false
|
291
296
|
# f.label :name, id: "cool_label"
|
@@ -294,7 +299,7 @@ module SimpleForm
|
|
294
299
|
return super if args.first.is_a?(String) || block_given?
|
295
300
|
|
296
301
|
options = args.extract_options!.dup
|
297
|
-
options[:label_html] = options.except(:label, :required, :as)
|
302
|
+
options[:label_html] = options.except(:label, :label_text, :required, :as)
|
298
303
|
|
299
304
|
column = find_attribute_column(attribute_name)
|
300
305
|
input_type = default_input_type(attribute_name, column, options)
|
@@ -505,7 +510,7 @@ module SimpleForm
|
|
505
510
|
end
|
506
511
|
|
507
512
|
# Attempt to guess the better input type given the defined options. By
|
508
|
-
# default
|
513
|
+
# default always fallback to the user :as option, or to a :select when a
|
509
514
|
# collection is given.
|
510
515
|
def default_input_type(attribute_name, column, options)
|
511
516
|
return options[:as].to_sym if options[:as]
|
@@ -544,7 +549,9 @@ module SimpleForm
|
|
544
549
|
end
|
545
550
|
|
546
551
|
def find_attribute_column(attribute_name)
|
547
|
-
if @object.respond_to?(:
|
552
|
+
if @object.respond_to?(:type_for_attribute) && @object.has_attribute?(attribute_name)
|
553
|
+
@object.type_for_attribute(attribute_name)
|
554
|
+
elsif @object.respond_to?(:column_for_attribute) && @object.has_attribute?(attribute_name)
|
548
555
|
@object.column_for_attribute(attribute_name)
|
549
556
|
end
|
550
557
|
end
|
@@ -115,7 +115,7 @@ module SimpleForm
|
|
115
115
|
end
|
116
116
|
|
117
117
|
def decimal_or_float?
|
118
|
-
column.
|
118
|
+
column.type == :float || column.type == :decimal
|
119
119
|
end
|
120
120
|
|
121
121
|
def nested_boolean_style?
|
@@ -189,9 +189,14 @@ module SimpleForm
|
|
189
189
|
|
190
190
|
def merge_wrapper_options(options, wrapper_options)
|
191
191
|
if wrapper_options
|
192
|
-
|
193
|
-
|
194
|
-
|
192
|
+
wrapper_options.merge(options) do |key, oldval, newval|
|
193
|
+
case key.to_s
|
194
|
+
when "class"
|
195
|
+
Array(oldval) + Array(newval)
|
196
|
+
when "data", "aria"
|
197
|
+
oldval.merge(newval)
|
198
|
+
else
|
199
|
+
newval
|
195
200
|
end
|
196
201
|
end
|
197
202
|
else
|
@@ -55,6 +55,7 @@ module SimpleForm
|
|
55
55
|
# we need the hidden field to be *outside* the label (otherwise it
|
56
56
|
# generates invalid html - html5 only).
|
57
57
|
def build_hidden_field_for_checkbox
|
58
|
+
return "" unless include_hidden?
|
58
59
|
options = { value: unchecked_value, id: nil, disabled: input_html_options[:disabled] }
|
59
60
|
options[:name] = input_html_options[:name] if input_html_options.has_key?(:name)
|
60
61
|
|
@@ -81,6 +82,10 @@ module SimpleForm
|
|
81
82
|
false
|
82
83
|
end
|
83
84
|
|
85
|
+
def include_hidden?
|
86
|
+
options.fetch(:include_hidden, true)
|
87
|
+
end
|
88
|
+
|
84
89
|
def checked_value
|
85
90
|
options.fetch(:checked_value, '1')
|
86
91
|
end
|
data/lib/simple_form/version.rb
CHANGED
@@ -94,13 +94,36 @@ class ErrorTest < ActionView::TestCase
|
|
94
94
|
assert_no_select 'span.error b', 'markup'
|
95
95
|
end
|
96
96
|
|
97
|
-
|
98
97
|
test 'error generates an error message with raw HTML tags' do
|
99
98
|
with_error_for @user, :name, error_prefix: '<b>Name</b>'.html_safe
|
100
99
|
assert_select 'span.error', "Name cannot be blank"
|
101
100
|
assert_select 'span.error b', "Name"
|
102
101
|
end
|
103
102
|
|
103
|
+
test 'error adds aria-invalid attribute to inputs' do
|
104
|
+
with_form_for @user, :name, error: true
|
105
|
+
assert_select "input#user_name[name='user[name]'][aria-invalid='true']"
|
106
|
+
|
107
|
+
with_form_for @user, :name, as: :text, error: true
|
108
|
+
assert_select "textarea#user_name[name='user[name]'][aria-invalid='true']"
|
109
|
+
|
110
|
+
@user.errors.add(:active, 'must select one')
|
111
|
+
with_form_for @user, :active, as: :radio_buttons
|
112
|
+
assert_select "input#user_active_true[type=radio][name='user[active]'][aria-invalid='true']"
|
113
|
+
assert_select "input#user_active_false[type=radio][name='user[active]'][aria-invalid='true']"
|
114
|
+
|
115
|
+
with_form_for @user, :active, as: :check_boxes
|
116
|
+
assert_select "input#user_active_true[type=checkbox][aria-invalid='true']"
|
117
|
+
assert_select "input#user_active_false[type=checkbox][aria-invalid='true']"
|
118
|
+
|
119
|
+
with_form_for @user, :company_id, as: :select, error: true
|
120
|
+
assert_select "select#user_company_id[aria-invalid='true']"
|
121
|
+
|
122
|
+
@user.errors.add(:password, 'must not be blank')
|
123
|
+
with_form_for @user, :password
|
124
|
+
assert_select "input#user_password[type=password][aria-invalid='true']"
|
125
|
+
end
|
126
|
+
|
104
127
|
# FULL ERRORS
|
105
128
|
|
106
129
|
test 'full error generates a full error tag for the attribute' do
|
@@ -139,7 +139,11 @@ class FormBuilderTest < ActionView::TestCase
|
|
139
139
|
|
140
140
|
test 'builder generates uuid fields for uuid columns' do
|
141
141
|
with_form_for @user, :uuid
|
142
|
-
|
142
|
+
if defined? ActiveModel::Type
|
143
|
+
assert_select 'form input#user_uuid.string.string'
|
144
|
+
else
|
145
|
+
assert_select 'form input#user_uuid.string.uuid'
|
146
|
+
end
|
143
147
|
end
|
144
148
|
|
145
149
|
test 'builder generates password fields for columns that matches password' do
|
@@ -121,6 +121,12 @@ class InputFieldTest < ActionView::TestCase
|
|
121
121
|
assert_no_select 'input.boolean[boolean_style]'
|
122
122
|
end
|
123
123
|
|
124
|
+
test 'build input_field does not treat "prompt" as a HTML attribute' do
|
125
|
+
with_input_field_for @user, :attempts, collection: [1,2,3,4,5], prompt: :translate
|
126
|
+
|
127
|
+
assert_no_select 'select[prompt]'
|
128
|
+
end
|
129
|
+
|
124
130
|
test 'build input_field without pattern component use the pattern string' do
|
125
131
|
swap_wrapper :default, custom_wrapper_with_html5_components do
|
126
132
|
with_input_field_for @user, :name, pattern: '\w+'
|
@@ -120,4 +120,11 @@ class LabelTest < ActionView::TestCase
|
|
120
120
|
assert_select 'label[for=user_time_zone]', 'Time Zone:'
|
121
121
|
end
|
122
122
|
end
|
123
|
+
|
124
|
+
test 'builder allows label specific `label_text` option' do
|
125
|
+
with_label_for @user, :time_zone, label_text: lambda { |l, _, _| "#{l.titleize}:" }
|
126
|
+
|
127
|
+
assert_no_select 'label[label_text]'
|
128
|
+
assert_select 'label[for=user_time_zone]', 'Time Zone:'
|
129
|
+
end
|
123
130
|
end
|
@@ -242,6 +242,38 @@ class WrapperTest < ActionView::TestCase
|
|
242
242
|
assert_select "section.custom_wrapper div.another_wrapper input.string"
|
243
243
|
end
|
244
244
|
|
245
|
+
test "input attributes class will merge with wrapper_options' classes" do
|
246
|
+
swap_wrapper :default, custom_wrapper_with_input_class do
|
247
|
+
with_concat_form_for @user do |f|
|
248
|
+
concat f.input :name, input_html: { class: 'another-class' }
|
249
|
+
end
|
250
|
+
end
|
251
|
+
|
252
|
+
assert_select "div.custom_wrapper input.string.inline-class.another-class"
|
253
|
+
end
|
254
|
+
|
255
|
+
test "input with data attributes will merge with wrapper_options' data" do
|
256
|
+
swap_wrapper :default, custom_wrapper_with_input_data_modal do
|
257
|
+
with_concat_form_for @user do |f|
|
258
|
+
concat f.input :name, input_html: { data: { modal: 'another-data', target: 'merge-data' } }
|
259
|
+
end
|
260
|
+
end
|
261
|
+
|
262
|
+
assert_select "input[data-wrapper='data-wrapper'][data-modal='another-data'][data-target='merge-data']"
|
263
|
+
end
|
264
|
+
|
265
|
+
test "input with aria attributes will merge with wrapper_options' aria" do
|
266
|
+
skip unless ActionPack::VERSION::MAJOR == '4' && ActionPack::VERSION::MINOR >= '2'
|
267
|
+
|
268
|
+
swap_wrapper :default, custom_wrapper_with_input_aria_modal do
|
269
|
+
with_concat_form_for @user do |f|
|
270
|
+
concat f.input :name, input_html: { aria: { modal: 'another-aria', target: 'merge-aria' } }
|
271
|
+
end
|
272
|
+
end
|
273
|
+
|
274
|
+
assert_select "input[aria-wrapper='aria-wrapper'][aria-modal='another-aria'][aria-target='merge-aria']"
|
275
|
+
end
|
276
|
+
|
245
277
|
test 'input accepts attributes in the DSL' do
|
246
278
|
swap_wrapper :default, custom_wrapper_with_input_class do
|
247
279
|
with_concat_form_for @user do |f|
|
@@ -137,6 +137,14 @@ class BooleanInputTest < ActionView::TestCase
|
|
137
137
|
end
|
138
138
|
end
|
139
139
|
|
140
|
+
test 'input with nested style allows disabling hidden field' do
|
141
|
+
swap SimpleForm, boolean_style: :nested do
|
142
|
+
with_input_for @user, :active, :boolean, include_hidden: false
|
143
|
+
assert_select "label.boolean > input.boolean"
|
144
|
+
assert_no_select "input[type=hidden] + label.boolean"
|
145
|
+
end
|
146
|
+
end
|
147
|
+
|
140
148
|
test 'input boolean works using :input only in wrapper config (no label_input)' do
|
141
149
|
swap_wrapper do
|
142
150
|
with_input_for @user, :active, :boolean
|
@@ -6,7 +6,11 @@ class DateTimeInputWithHtml5Test < ActionView::TestCase
|
|
6
6
|
test 'input generates a datetime input for datetime attributes if HTML5 compatibility is explicitly enbled' do
|
7
7
|
with_input_for @user, :created_at, :datetime, html5: true
|
8
8
|
|
9
|
-
|
9
|
+
if ActionPack::VERSION::STRING >= '5'
|
10
|
+
assert_select 'input[type="datetime-local"]'
|
11
|
+
elsif ActionPack::VERSION::STRING < '5'
|
12
|
+
assert_select 'input[type="datetime"]'
|
13
|
+
end
|
10
14
|
end
|
11
15
|
|
12
16
|
test 'input generates a datetime select for datetime attributes' do
|
@@ -76,7 +80,11 @@ class DateTimeInputWithoutHtml5Test < ActionView::TestCase
|
|
76
80
|
swap_wrapper do
|
77
81
|
with_input_for @user, :created_at, :datetime, html5: true
|
78
82
|
|
79
|
-
|
83
|
+
if ActionPack::VERSION::STRING >= '5'
|
84
|
+
assert_select 'input[type="datetime-local"]'
|
85
|
+
elsif ActionPack::VERSION::STRING < '5'
|
86
|
+
assert_select 'input[type="datetime"]'
|
87
|
+
end
|
80
88
|
end
|
81
89
|
end
|
82
90
|
|
@@ -14,6 +14,7 @@ class DiscoveryTest < ActionView::TestCase
|
|
14
14
|
Object.send :remove_const, :CustomizedInput
|
15
15
|
Object.send :remove_const, :DeprecatedInput
|
16
16
|
Object.send :remove_const, :CollectionSelectInput
|
17
|
+
CustomInputs.send :remove_const, :CustomizedInput
|
17
18
|
CustomInputs.send :remove_const, :PasswordInput
|
18
19
|
CustomInputs.send :remove_const, :NumericInput
|
19
20
|
end
|
@@ -113,6 +113,9 @@ class NumericInputTest < ActionView::TestCase
|
|
113
113
|
|
114
114
|
with_input_for @validating_user, :age, :integer
|
115
115
|
assert_select 'input[step="1"]'
|
116
|
+
|
117
|
+
with_input_for @validating_user, :age, :integer, as: :decimal, input_html: { step: 0.5 }
|
118
|
+
assert_select 'input[step="0.5"]'
|
116
119
|
end
|
117
120
|
|
118
121
|
test 'numeric input does not generate placeholder by default' do
|
@@ -5,14 +5,22 @@ class PriorityInputTest < ActionView::TestCase
|
|
5
5
|
test 'input generates a country select field' do
|
6
6
|
with_input_for @user, :country, :country
|
7
7
|
assert_select 'select#user_country'
|
8
|
-
|
8
|
+
if ActionPack::VERSION::STRING >= '5'
|
9
|
+
assert_select 'select option[value=BR]', 'Brazil'
|
10
|
+
elsif ActionPack::VERSION::STRING < '5'
|
11
|
+
assert_select 'select option[value=Brazil]', 'Brazil'
|
12
|
+
end
|
9
13
|
assert_no_select 'select option[value=""][disabled=disabled]'
|
10
14
|
end
|
11
15
|
|
12
16
|
test 'input generates a country select with SimpleForm default' do
|
13
17
|
swap SimpleForm, country_priority: [ 'Brazil' ] do
|
14
18
|
with_input_for @user, :country, :country
|
15
|
-
|
19
|
+
if ActionPack::VERSION::STRING >= '5'
|
20
|
+
assert_select 'select option[value="---------------"][disabled=disabled]'
|
21
|
+
elsif ActionPack::VERSION::STRING < '5'
|
22
|
+
assert_select 'select option[value=""][disabled=disabled]'
|
23
|
+
end
|
16
24
|
end
|
17
25
|
end
|
18
26
|
|
@@ -34,6 +34,38 @@ class RequiredTest < ActionView::TestCase
|
|
34
34
|
with_input_for @user, :name, :string
|
35
35
|
assert_select 'input[type=text].required'
|
36
36
|
assert_no_select 'input[type=text][required]'
|
37
|
+
assert_no_select 'input[type=text][aria-required]'
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
test 'when not using browser validations, when required option is set to false, input does not generate required html attribute' do
|
42
|
+
swap SimpleForm, browser_validations: false do
|
43
|
+
with_input_for @user, :name, :string, required: false
|
44
|
+
assert_no_select 'input[type=text].required'
|
45
|
+
assert_no_select 'input[type=text][required]'
|
46
|
+
assert_no_select 'input[type=text][aria-required]'
|
47
|
+
end
|
48
|
+
end
|
49
|
+
|
50
|
+
test 'when not using browser validations, when required option is set to true, input generates required html attribute' do
|
51
|
+
swap SimpleForm, browser_validations: false do
|
52
|
+
with_input_for @user, :name, :string, required: true
|
53
|
+
assert_select 'input[type=text].required'
|
54
|
+
assert_select 'input[type=text][required]'
|
55
|
+
assert_select 'input[type=text][aria-required]'
|
56
|
+
end
|
57
|
+
end
|
58
|
+
|
59
|
+
test 'when not using browser validations, when required option is true in the wrapper, input does not generate required html attribute' do
|
60
|
+
swap SimpleForm, browser_validations: false do
|
61
|
+
swap_wrapper :default, self.custom_wrapper_with_required_input do
|
62
|
+
with_concat_form_for(@user) do |f|
|
63
|
+
concat f.input :name
|
64
|
+
end
|
65
|
+
assert_select 'input[type=text].required'
|
66
|
+
assert_no_select 'input[type=text][required]'
|
67
|
+
assert_no_select 'input[type=text][aria-required]'
|
68
|
+
end
|
37
69
|
end
|
38
70
|
end
|
39
71
|
|
@@ -32,9 +32,11 @@ class StringInputTest < ActionView::TestCase
|
|
32
32
|
assert_select 'input.string[maxlength="25"]'
|
33
33
|
end
|
34
34
|
|
35
|
-
|
36
|
-
|
37
|
-
|
35
|
+
if ActionPack::VERSION::STRING < '5'
|
36
|
+
test 'input does not get maxlength from validation when tokenizer present' do
|
37
|
+
with_input_for @validating_user, :action, :string
|
38
|
+
assert_no_select 'input.string[maxlength]'
|
39
|
+
end
|
38
40
|
end
|
39
41
|
|
40
42
|
test 'input gets maxlength from validation when :is option present' do
|
@@ -91,6 +91,20 @@ module MiscHelpers
|
|
91
91
|
end
|
92
92
|
end
|
93
93
|
|
94
|
+
def custom_wrapper_with_input_data_modal
|
95
|
+
SimpleForm.build tag: :div, class: "custom_wrapper" do |b|
|
96
|
+
b.use :label
|
97
|
+
b.use :input, data: { modal: 'data-modal', wrapper: 'data-wrapper' }
|
98
|
+
end
|
99
|
+
end
|
100
|
+
|
101
|
+
def custom_wrapper_with_input_aria_modal
|
102
|
+
SimpleForm.build tag: :div, class: "custom_wrapper" do |b|
|
103
|
+
b.use :label
|
104
|
+
b.use :input, aria: { modal: 'aria-modal', wrapper: 'aria-wrapper' }
|
105
|
+
end
|
106
|
+
end
|
107
|
+
|
94
108
|
def custom_wrapper_with_label_class
|
95
109
|
SimpleForm.build tag: :div, class: "custom_wrapper" do |b|
|
96
110
|
b.use :label, class: 'inline-class'
|
data/test/support/models.rb
CHANGED
@@ -1,10 +1,6 @@
|
|
1
1
|
Association = Struct.new(:klass, :name, :macro, :scope, :options)
|
2
2
|
|
3
3
|
Column = Struct.new(:name, :type, :limit) do
|
4
|
-
# Returns +true+ if the column is either of type integer, float or decimal.
|
5
|
-
def number?
|
6
|
-
type == :integer || type == :float || type == :decimal
|
7
|
-
end
|
8
4
|
end
|
9
5
|
|
10
6
|
Relation = Struct.new(:records) do
|
@@ -130,6 +126,33 @@ class User
|
|
130
126
|
Column.new(attribute, column_type, limit)
|
131
127
|
end
|
132
128
|
|
129
|
+
begin
|
130
|
+
require 'active_model/type'
|
131
|
+
def type_for_attribute(attribute)
|
132
|
+
column_type, limit = case attribute.to_sym
|
133
|
+
when :name, :status, :password then [:string, 100]
|
134
|
+
when :description then [:text, 200]
|
135
|
+
when :age then :integer
|
136
|
+
when :credit_limit then [:decimal, 15]
|
137
|
+
when :active then :boolean
|
138
|
+
when :born_at then :date
|
139
|
+
when :delivery_time then :time
|
140
|
+
when :created_at then :datetime
|
141
|
+
when :updated_at then :datetime
|
142
|
+
when :lock_version then :integer
|
143
|
+
when :home_picture then :string
|
144
|
+
when :amount then :integer
|
145
|
+
when :attempts then :integer
|
146
|
+
when :action then :string
|
147
|
+
when :credit_card then :string
|
148
|
+
when :uuid then :string
|
149
|
+
end
|
150
|
+
|
151
|
+
ActiveModel::Type.lookup(column_type, limit: limit)
|
152
|
+
end
|
153
|
+
rescue LoadError
|
154
|
+
end
|
155
|
+
|
133
156
|
def has_attribute?(attribute)
|
134
157
|
case attribute.to_sym
|
135
158
|
when :name, :status, :password, :description, :age,
|
@@ -215,7 +238,9 @@ class ValidatingUser < User
|
|
215
238
|
only_integer: true
|
216
239
|
validates_length_of :name, maximum: 25
|
217
240
|
validates_length_of :description, maximum: 50
|
218
|
-
|
241
|
+
if ActionPack::VERSION::STRING < '5'
|
242
|
+
validates_length_of :action, maximum: 10, tokenizer: lambda { |str| str.scan(/\w+/) }
|
243
|
+
end
|
219
244
|
validates_length_of :home_picture, is: 12
|
220
245
|
|
221
246
|
def min_amount
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: simple_form
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 3.
|
4
|
+
version: 3.3.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- José Valim
|
@@ -10,7 +10,7 @@ authors:
|
|
10
10
|
autorequire:
|
11
11
|
bindir: bin
|
12
12
|
cert_chain: []
|
13
|
-
date:
|
13
|
+
date: 2016-08-25 00:00:00.000000000 Z
|
14
14
|
dependencies:
|
15
15
|
- !ruby/object:Gem::Dependency
|
16
16
|
name: activemodel
|
@@ -178,7 +178,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
178
178
|
version: '0'
|
179
179
|
requirements: []
|
180
180
|
rubyforge_project: simple_form
|
181
|
-
rubygems_version: 2.
|
181
|
+
rubygems_version: 2.6.3
|
182
182
|
signing_key:
|
183
183
|
specification_version: 4
|
184
184
|
summary: Forms made easy!
|