formulary 0.0.1 → 0.0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/README.md +50 -6
- data/formulary.gemspec +1 -0
- data/lib/formulary.rb +13 -0
- data/lib/formulary/html_form.rb +39 -58
- data/lib/formulary/html_form/fields.rb +21 -0
- data/lib/formulary/html_form/fields/checkbox_group.rb +43 -0
- data/lib/formulary/html_form/fields/email_input.rb +23 -0
- data/lib/formulary/html_form/fields/field.rb +45 -0
- data/lib/formulary/html_form/fields/field_group.rb +26 -0
- data/lib/formulary/html_form/fields/hidden_input.rb +7 -0
- data/lib/formulary/html_form/fields/input.rb +32 -0
- data/lib/formulary/html_form/fields/radio_button_group.rb +29 -0
- data/lib/formulary/html_form/fields/select.rb +24 -0
- data/lib/formulary/html_form/fields/tel_input.rb +7 -0
- data/lib/formulary/html_form/fields/text_input.rb +7 -0
- data/lib/formulary/html_form/fields/textarea.rb +12 -0
- data/lib/formulary/version.rb +1 -1
- data/spec/html_form/fields/checkbox_group_spec.rb +141 -0
- data/spec/html_form/fields/email_input_spec.rb +55 -0
- data/spec/html_form/fields/field_spec.rb +10 -0
- data/spec/html_form/fields/hidden_input_spec.rb +37 -0
- data/spec/html_form/fields/input_spec.rb +17 -0
- data/spec/html_form/fields/radio_button_group_spec.rb +94 -0
- data/spec/html_form/fields/select_spec.rb +62 -0
- data/spec/html_form/fields/tel_input_spec.rb +29 -0
- data/spec/html_form/fields/text_input_spec.rb +29 -0
- data/spec/html_form/fields/textarea_spec.rb +28 -0
- data/spec/html_form_spec.rb +53 -109
- data/spec/spec_helper.rb +5 -10
- data/spec/support/element_helper.rb +15 -0
- data/spec/support/shared_examples_for_pattern.rb +15 -0
- data/spec/support/shared_examples_for_required.rb +35 -0
- metadata +149 -94
- checksums.yaml +0 -7
@@ -0,0 +1,29 @@
|
|
1
|
+
module Formulary::HtmlForm::Fields
|
2
|
+
class RadioButtonGroup < FieldGroup
|
3
|
+
def self.compatible_type
|
4
|
+
"radio"
|
5
|
+
end
|
6
|
+
|
7
|
+
def self.supports_required?
|
8
|
+
true
|
9
|
+
end
|
10
|
+
|
11
|
+
protected
|
12
|
+
|
13
|
+
def required?
|
14
|
+
@elements.any? { |e| e.attributes.include?("required") }
|
15
|
+
end
|
16
|
+
|
17
|
+
def value_in_list?
|
18
|
+
return true if @value.blank?
|
19
|
+
valid_values.include?(@value)
|
20
|
+
end
|
21
|
+
|
22
|
+
def valid_values
|
23
|
+
@valid_values ||= \
|
24
|
+
@elements.map do |element|
|
25
|
+
element.attributes["value"].value
|
26
|
+
end
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
@@ -0,0 +1,24 @@
|
|
1
|
+
module Formulary::HtmlForm::Fields
|
2
|
+
class Select < Field
|
3
|
+
def self.compatible_with?(element)
|
4
|
+
element.name == "select"
|
5
|
+
end
|
6
|
+
|
7
|
+
def valid?
|
8
|
+
valid_values.include?(@value)
|
9
|
+
end
|
10
|
+
|
11
|
+
def error
|
12
|
+
return "choose" unless valid?
|
13
|
+
end
|
14
|
+
|
15
|
+
protected
|
16
|
+
|
17
|
+
def valid_values
|
18
|
+
@valid_values ||= \
|
19
|
+
@element.css("option").map do |option|
|
20
|
+
option["value"] ? option["value"] : option.text
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
24
|
+
end
|
data/lib/formulary/version.rb
CHANGED
@@ -0,0 +1,141 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Formulary::HtmlForm::Fields::CheckboxGroup do
|
4
|
+
describe ".compatible_with?" do
|
5
|
+
subject { Formulary::HtmlForm::Fields::CheckboxGroup.compatible_with?(elements) }
|
6
|
+
|
7
|
+
context "with checkboxen" do
|
8
|
+
let(:markup) do
|
9
|
+
%{
|
10
|
+
<input type="checkbox" name="field" value="one">
|
11
|
+
<input type="checkbox" name="field" value="two">
|
12
|
+
}
|
13
|
+
end
|
14
|
+
|
15
|
+
it { should be_true }
|
16
|
+
end
|
17
|
+
|
18
|
+
context "with radio buttons" do
|
19
|
+
let(:markup) do
|
20
|
+
%{
|
21
|
+
<input type="radio" name="field" value="one">
|
22
|
+
<input type="radio" name="field" value="two">
|
23
|
+
}
|
24
|
+
end
|
25
|
+
|
26
|
+
it { should be_false }
|
27
|
+
end
|
28
|
+
|
29
|
+
context "with a sweet mix of the two" do
|
30
|
+
let(:markup) do
|
31
|
+
%{
|
32
|
+
<input type="checkbox" name="field" value="one">
|
33
|
+
<input type="radio" name="field" value="two">
|
34
|
+
}
|
35
|
+
end
|
36
|
+
it { should be_false }
|
37
|
+
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
describe "validations" do
|
42
|
+
subject(:checkbox_group) do
|
43
|
+
Formulary::HtmlForm::Fields::CheckboxGroup.new("food", elements)
|
44
|
+
end
|
45
|
+
|
46
|
+
context "when one of the items in the group is required" do
|
47
|
+
let(:markup) do
|
48
|
+
%{
|
49
|
+
<input type="checkbox" name="field" value="first" required>
|
50
|
+
<input type="checkbox" name="field" value="second">
|
51
|
+
}
|
52
|
+
end
|
53
|
+
|
54
|
+
context "with the required item" do
|
55
|
+
before { checkbox_group.set_value("first") }
|
56
|
+
|
57
|
+
it { should be_valid }
|
58
|
+
its(:error) { should be_blank }
|
59
|
+
end
|
60
|
+
|
61
|
+
context "with required and non-required items" do
|
62
|
+
before { checkbox_group.set_value(["first","second"]) }
|
63
|
+
|
64
|
+
it { should be_valid }
|
65
|
+
its(:error) { should be_blank }
|
66
|
+
end
|
67
|
+
|
68
|
+
context "with a non-required item" do
|
69
|
+
before { checkbox_group.set_value("second") }
|
70
|
+
|
71
|
+
it { should_not be_valid }
|
72
|
+
its(:error) { should include("required") }
|
73
|
+
end
|
74
|
+
|
75
|
+
context "with a value that isn't expected" do
|
76
|
+
before { checkbox_group.set_value([ "first", "invalid" ]) }
|
77
|
+
|
78
|
+
it { should_not be_valid }
|
79
|
+
its(:error) { should include("choose") }
|
80
|
+
end
|
81
|
+
|
82
|
+
context "with no value" do
|
83
|
+
it { should_not be_valid }
|
84
|
+
its(:error) { should include("required") }
|
85
|
+
end
|
86
|
+
end
|
87
|
+
|
88
|
+
context "when none are required" do
|
89
|
+
let(:markup) do
|
90
|
+
%{
|
91
|
+
<input type="checkbox" name="field" value="first">
|
92
|
+
<input type="checkbox" name="field" value="second">
|
93
|
+
}
|
94
|
+
end
|
95
|
+
|
96
|
+
context "with a value that isn't expected" do
|
97
|
+
before { checkbox_group.set_value("invalid") }
|
98
|
+
|
99
|
+
it { should_not be_valid }
|
100
|
+
its(:error) { should include("choose") }
|
101
|
+
end
|
102
|
+
|
103
|
+
context "with no value" do
|
104
|
+
it { should be_valid }
|
105
|
+
its(:error) { should be_blank }
|
106
|
+
end
|
107
|
+
|
108
|
+
context "passed 'on' when all values are specified" do
|
109
|
+
before { checkbox_group.set_value("on") }
|
110
|
+
|
111
|
+
it { should_not be_valid }
|
112
|
+
its(:error) { should include("choose") }
|
113
|
+
end
|
114
|
+
end
|
115
|
+
|
116
|
+
context "when no value is specified in the markup" do
|
117
|
+
context "when it is required" do
|
118
|
+
let(:markup) { %{<input type="checkbox" name="field" required>} }
|
119
|
+
|
120
|
+
context "when it is checked" do
|
121
|
+
before { checkbox_group.set_value("on") }
|
122
|
+
|
123
|
+
it { should be_valid }
|
124
|
+
its(:error) { should be_blank }
|
125
|
+
end
|
126
|
+
end
|
127
|
+
|
128
|
+
context "when it is not required" do
|
129
|
+
let(:markup) { %{<input type="checkbox" name="field">} }
|
130
|
+
|
131
|
+
|
132
|
+
context "when it is checked" do
|
133
|
+
before { checkbox_group.set_value("on") }
|
134
|
+
|
135
|
+
it { should be_valid }
|
136
|
+
its(:error) { should be_blank }
|
137
|
+
end
|
138
|
+
end
|
139
|
+
end
|
140
|
+
end
|
141
|
+
end
|
@@ -0,0 +1,55 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Formulary::HtmlForm::Fields::EmailInput do
|
4
|
+
describe ".compatible_with?" do
|
5
|
+
subject { Formulary::HtmlForm::Fields::EmailInput.compatible_with?(element) }
|
6
|
+
let(:markup) { %{<input type="#{type}" name="name" />} }
|
7
|
+
|
8
|
+
context "text type" do
|
9
|
+
let(:type) { "text" }
|
10
|
+
it { should be_false }
|
11
|
+
end
|
12
|
+
|
13
|
+
context "email type" do
|
14
|
+
let(:type) { "email" }
|
15
|
+
it { should be_true }
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
it_should_behave_like "a field that allows the required attribute" do
|
20
|
+
let(:markup_with_required) { %{<input type="email" name="field" required />} }
|
21
|
+
let(:markup_without_required) { %{<input type="email" name="field" />} }
|
22
|
+
let(:valid_value) { "test@example.com" }
|
23
|
+
end
|
24
|
+
|
25
|
+
it_should_behave_like "a field that allows the pattern attribute" do
|
26
|
+
let(:markup) { '<input type="email" name="field" pattern="@example\.com$" />' }
|
27
|
+
let(:valid_value) { "test@example.com" }
|
28
|
+
end
|
29
|
+
|
30
|
+
describe "validations" do
|
31
|
+
subject(:input) { Formulary::HtmlForm::Fields::EmailInput.new(element) }
|
32
|
+
let(:markup) { %{<input type="email" name="name" />} }
|
33
|
+
|
34
|
+
context "with a valid email address" do
|
35
|
+
before { input.set_value("test@example.com") }
|
36
|
+
|
37
|
+
it { should be_valid }
|
38
|
+
its(:error) { should be_blank }
|
39
|
+
end
|
40
|
+
|
41
|
+
context "with an invalid email address" do
|
42
|
+
before { input.set_value("invalid!") }
|
43
|
+
|
44
|
+
it { should_not be_valid }
|
45
|
+
its(:error) { should include("email") }
|
46
|
+
end
|
47
|
+
|
48
|
+
context "with a nil email address" do
|
49
|
+
before { input.set_value(nil) }
|
50
|
+
|
51
|
+
it { should be_valid }
|
52
|
+
its(:error) { should be_blank }
|
53
|
+
end
|
54
|
+
end
|
55
|
+
end
|
@@ -0,0 +1,10 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Formulary::HtmlForm::Fields::Field do
|
4
|
+
describe "#name" do
|
5
|
+
subject { Formulary::HtmlForm::Fields::Field.new(element).name }
|
6
|
+
let(:markup) { %{<input type="text" name="field" />} }
|
7
|
+
|
8
|
+
it { should eq("field") }
|
9
|
+
end
|
10
|
+
end
|
@@ -0,0 +1,37 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Formulary::HtmlForm::Fields::HiddenInput do
|
4
|
+
describe ".compatible_with?" do
|
5
|
+
subject { Formulary::HtmlForm::Fields::HiddenInput.compatible_with?(element) }
|
6
|
+
let(:markup) { %{<input type="#{type}" name="name" />} }
|
7
|
+
|
8
|
+
context "text type" do
|
9
|
+
let(:type) { "text" }
|
10
|
+
it { should be_false }
|
11
|
+
end
|
12
|
+
|
13
|
+
context "hidden type" do
|
14
|
+
let(:type) { "hidden" }
|
15
|
+
it { should be_true }
|
16
|
+
end
|
17
|
+
end
|
18
|
+
|
19
|
+
describe "validations" do
|
20
|
+
subject(:input) { Formulary::HtmlForm::Fields::HiddenInput.new(element) }
|
21
|
+
let(:markup) { %{<input type="hidden" name="field"></input>} }
|
22
|
+
|
23
|
+
context "passed a value" do
|
24
|
+
before { input.set_value("test") }
|
25
|
+
|
26
|
+
it { should be_valid }
|
27
|
+
its(:error) { should be_blank }
|
28
|
+
end
|
29
|
+
|
30
|
+
context "passed no value" do
|
31
|
+
before { input.set_value("") }
|
32
|
+
|
33
|
+
it { should be_valid }
|
34
|
+
its(:error) { should be_blank }
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
@@ -0,0 +1,17 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Formulary::HtmlForm::Fields::Input do
|
4
|
+
describe ".compatible_with?" do
|
5
|
+
subject { Formulary::HtmlForm::Fields::EmailInput.compatible_with?(element) }
|
6
|
+
|
7
|
+
context "with a textarea" do
|
8
|
+
let(:markup) { %{<textarea name="name"></textarea>} }
|
9
|
+
it { should be_false }
|
10
|
+
end
|
11
|
+
|
12
|
+
context "with a select" do
|
13
|
+
let(:markup) { %{<select name="name"></select>} }
|
14
|
+
it { should be_false }
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
@@ -0,0 +1,94 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Formulary::HtmlForm::Fields::RadioButtonGroup do
|
4
|
+
describe ".compatible_with?" do
|
5
|
+
subject { Formulary::HtmlForm::Fields::RadioButtonGroup.compatible_with?(elements) }
|
6
|
+
|
7
|
+
context "with checkboxen" do
|
8
|
+
let(:markup) do
|
9
|
+
%{
|
10
|
+
<input type="checkbox" name="field" value="one">
|
11
|
+
<input type="checkbox" name="field" value="two">
|
12
|
+
}
|
13
|
+
end
|
14
|
+
|
15
|
+
it { should be_false }
|
16
|
+
end
|
17
|
+
|
18
|
+
context "with radio buttons" do
|
19
|
+
let(:markup) do
|
20
|
+
%{
|
21
|
+
<input type="radio" name="field" value="one">
|
22
|
+
<input type="radio" name="field" value="two">
|
23
|
+
}
|
24
|
+
end
|
25
|
+
|
26
|
+
it { should be_true }
|
27
|
+
end
|
28
|
+
|
29
|
+
context "with a sweet mix of the two" do
|
30
|
+
let(:markup) do
|
31
|
+
%{
|
32
|
+
<input type="checkbox" name="field" value="one">
|
33
|
+
<input type="radio" name="field" value="two">
|
34
|
+
}
|
35
|
+
end
|
36
|
+
|
37
|
+
it { should be_false }
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
describe "validations" do
|
42
|
+
subject(:radio_group) { Formulary::HtmlForm::Fields::RadioButtonGroup.new("food", elements) }
|
43
|
+
|
44
|
+
context "when one of the items in the group is required" do
|
45
|
+
let(:markup) do
|
46
|
+
%{<input type="radio" name="food" value="bacon" required />
|
47
|
+
<input type="radio" name="food" value="butter" /> }
|
48
|
+
end
|
49
|
+
|
50
|
+
context "with a valid submission" do
|
51
|
+
before { radio_group.set_value("bacon") }
|
52
|
+
it { should be_valid }
|
53
|
+
its(:error) { should be_blank }
|
54
|
+
end
|
55
|
+
|
56
|
+
context "with a value that isn't expected" do
|
57
|
+
before { radio_group.set_value("eggplant") }
|
58
|
+
it { should_not be_valid }
|
59
|
+
its(:error) { should include("choose") }
|
60
|
+
end
|
61
|
+
|
62
|
+
context "with no value" do
|
63
|
+
before { radio_group.set_value("") }
|
64
|
+
it { should_not be_valid }
|
65
|
+
its(:error) { should include("required") }
|
66
|
+
end
|
67
|
+
end
|
68
|
+
|
69
|
+
context "when none are required" do
|
70
|
+
let(:markup) do
|
71
|
+
%{<input type="radio" name="food" value="bacon" />
|
72
|
+
<input type="radio" name="food" value="butter" /> }
|
73
|
+
end
|
74
|
+
|
75
|
+
context "with a value that isn't expected" do
|
76
|
+
before { radio_group.set_value("eggplant") }
|
77
|
+
it { should_not be_valid }
|
78
|
+
its(:error) { should include("choose") }
|
79
|
+
end
|
80
|
+
|
81
|
+
context "with no value" do
|
82
|
+
before { radio_group.set_value("") }
|
83
|
+
it { should be_valid }
|
84
|
+
its(:error) { should be_blank }
|
85
|
+
end
|
86
|
+
|
87
|
+
context "with nil value" do
|
88
|
+
before { radio_group.set_value(nil) }
|
89
|
+
it { should be_valid }
|
90
|
+
its(:error) { should be_blank }
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
94
|
+
end
|