reform 0.2.7 → 1.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.
@@ -0,0 +1,28 @@
1
+ require 'test_helper'
2
+
3
+ class FeatureInheritanceTest < BaseTest
4
+ class AlbumForm < Reform::Form
5
+ # include Reform::Form::ActiveModel
6
+ # include Coercion
7
+ # include MultiParameterAttributes
8
+
9
+ property :band do
10
+ property :label do
11
+ end
12
+ end
13
+ end
14
+
15
+ subject { AlbumForm.new(Album.new(nil, nil, nil, Band.new(Label.new))) }
16
+
17
+ # it { subject.class.include?(Reform::Form::ActiveModel) }
18
+ # it { subject.class.include?(Reform::Form::Coercion) }
19
+ # it { subject.is_a?(Reform::Form::MultiParameterAttributes) }
20
+
21
+ # it { subject.band.class.include?(Reform::Form::ActiveModel) }
22
+ # it { subject.band.is_a?(Reform::Form::Coercion) }
23
+ # it { subject.band.is_a?(Reform::Form::MultiParameterAttributes) }
24
+
25
+ # it { subject.band.label.is_a?(Reform::Form::ActiveModel) }
26
+ # it { subject.band.label.is_a?(Reform::Form::Coercion) }
27
+ # it { subject.band.label.is_a?(Reform::Form::MultiParameterAttributes) }
28
+ end
@@ -0,0 +1,105 @@
1
+ require 'test_helper'
2
+
3
+ class FormBuilderCompatTest < BaseTest
4
+ let (:form_class) {
5
+ Class.new(Reform::Form) do
6
+ include Reform::Form::ActiveModel::FormBuilderMethods
7
+
8
+ property :artist do
9
+ property :name
10
+ validates :name, :presence => true
11
+ end
12
+
13
+ collection :songs do
14
+ property :title
15
+ property :release_date
16
+ validates :title, :presence => true
17
+ end
18
+
19
+ class LabelForm < Reform::Form
20
+ property :name
21
+ end
22
+
23
+ property :label, :form => LabelForm
24
+
25
+ property :band do
26
+ property :label do
27
+ property :name
28
+ end
29
+ end
30
+ end
31
+ }
32
+
33
+ let (:song) { OpenStruct.new }
34
+ let (:form) { form_class.new(OpenStruct.new(
35
+ :artist => Artist.new(:name => "Propagandhi"),
36
+ :songs => [song],
37
+ :label => OpenStruct.new,
38
+
39
+ :band => Band.new(Label.new)
40
+ )) }
41
+
42
+ it "respects _attributes params hash" do
43
+ form.validate("artist_attributes" => {"name" => "Blink 182"},
44
+ "songs_attributes" => {"0" => {"title" => "Damnit"}},
45
+ "band_attributes" => {"label_attributes" => {"name" => "Epitaph"}})
46
+
47
+ form.artist.name.must_equal "Blink 182"
48
+ form.songs.first.title.must_equal "Damnit"
49
+ form.band.label.name.must_equal "Epitaph"
50
+ end
51
+
52
+ it "allows nested collection and property to be missing" do
53
+ form.validate({})
54
+
55
+ form.artist.name.must_equal "Propagandhi"
56
+
57
+ form.songs.size.must_equal 1
58
+ form.songs[0].model.must_equal song # this is a weird test.
59
+ end
60
+
61
+ it "defines _attributes= setter so Rails' FB works properly" do
62
+ form.must_respond_to("artist_attributes=")
63
+ form.must_respond_to("songs_attributes=")
64
+ form.must_respond_to("label_attributes=")
65
+ end
66
+
67
+ describe "deconstructed date parameters" do
68
+ let(:form_attributes) do
69
+ {
70
+ "artist_attributes" => {"name" => "Blink 182"},
71
+ "songs_attributes" => {"0" => {"title" => "Damnit", "release_date(1i)" => release_year,
72
+ "release_date(2i)" => release_month, "release_date(3i)" => release_day}}
73
+ }
74
+ end
75
+ let(:release_year) { "1997" }
76
+ let(:release_month) { "9" }
77
+ let(:release_day) { "27" }
78
+
79
+ describe "with valid parameters" do
80
+ it "creates a date" do
81
+ form.validate(form_attributes)
82
+
83
+ form.songs.first.release_date.must_equal Date.new(1997, 9, 27)
84
+ end
85
+ end
86
+
87
+ %w(year month day).each do |date_attr|
88
+ describe "when the #{date_attr} is missing" do
89
+ let(:"release_#{date_attr}") { "" }
90
+
91
+ it "rejects the date" do
92
+ form.validate(form_attributes)
93
+
94
+ form.songs.first.release_date.must_be_nil
95
+ end
96
+ end
97
+ end
98
+ end
99
+
100
+ it "returns flat errors hash" do
101
+ form.validate("artist_attributes" => {"name" => ""},
102
+ "songs_attributes" => {"0" => {"title" => ""}})
103
+ form.errors.messages.must_equal(:"artist.name" => ["can't be blank"], :"songs.title" => ["can't be blank"])
104
+ end
105
+ end
@@ -1,26 +1,36 @@
1
1
  require 'test_helper'
2
2
 
3
3
  class FormCompositionTest < MiniTest::Spec
4
- class SongForm < Reform::Form
4
+ Song = Struct.new(:id, :title)
5
+ Requester = Struct.new(:id, :name)
6
+
7
+ class RequestForm < Reform::Form
5
8
  include Composition
6
9
 
7
- property :title, :on => :song
8
- properties [:name, :genre], :on => :artist
10
+ property :name, :on => :requester
11
+ property :requester_id, :on => :requester, :as => :id
12
+ properties [:title, :id], :on => :song
13
+ # property :channel # FIXME: what about the "main model"?
14
+ property :channel, :empty => true, :on => :song
9
15
 
10
- validates :name, :title, :genre, :presence => true
16
+ validates :name, :title, :channel, :presence => true
11
17
  end
12
18
 
13
- let (:form) { SongForm.new(:song => song, :artist => artist) }
14
- let (:song) { OpenStruct.new(:title => "Rio") }
15
- let (:artist) { OpenStruct.new(:name => "Duran Duran") }
19
+ let (:form) { RequestForm.new(:song => song, :requester => requester) }
20
+ let (:song) { Song.new(1, "Rio") }
21
+ let (:requester) { Requester.new(2, "Duran Duran") }
16
22
 
17
23
 
18
24
  # delegation form -> composition works
19
- it { form.title.must_equal "Rio" }
20
- it { form.name.must_equal "Duran Duran" }
25
+ it { form.id.must_equal 1 }
26
+ it { form.title.must_equal "Rio" }
27
+ it { form.name.must_equal "Duran Duran" }
28
+ it { form.requester_id.must_equal 2 }
29
+ it { form.channel.must_equal nil }
30
+
21
31
  # delegation form -> composed models (e.g. when saving this can be handy)
22
32
  it { form.song.must_equal song }
23
- it { form.artist.must_equal artist }
33
+ it { form.requester.must_equal requester }
24
34
 
25
35
 
26
36
  it "creates Composition for you" do
@@ -40,21 +50,28 @@ class FormCompositionTest < MiniTest::Spec
40
50
  end
41
51
 
42
52
  it "provides nested symbolized hash as second block argument" do
53
+ form.validate("title" => "Greyhound", "name" => "Frenzal Rhomb", "channel" => "JJJ")
54
+
43
55
  hash = {}
44
56
 
45
57
  form.save do |data, map|
46
58
  hash = map
47
59
  end
48
60
 
49
- hash.must_equal({:song=>{:title=>"Rio"}, :artist=>{:name=>"Duran Duran"}})
61
+ hash.must_equal({:song=>{:title=>"Greyhound", :id=>1, :channel => "JJJ"}, :requester=>{:name=>"Frenzal Rhomb", :id=>2}})
50
62
  end
51
63
 
52
- it "pushes data to models when no block passed" do
64
+ it "pushes data to models and calls #save when no block passed" do
65
+ song.extend(Saveable)
66
+ requester.extend(Saveable)
67
+
53
68
  form.validate("title" => "Greyhound", "name" => "Frenzal Rhomb")
54
69
  form.save
55
70
 
56
- artist.name.must_equal "Frenzal Rhomb"
71
+ requester.name.must_equal "Frenzal Rhomb"
72
+ requester.saved?.must_equal true
57
73
  song.title.must_equal "Greyhound"
74
+ song.saved?.must_equal true
58
75
  end
59
76
  end
60
77
  end
@@ -37,14 +37,18 @@ class NestedFormTest < MiniTest::Spec
37
37
  let (:songs) { [OpenStruct.new(:title => "Calling")] }
38
38
  let (:form) { AlbumForm.new(album) }
39
39
 
40
- it "responds to #to_hash" do
41
- form.to_hash.must_equal({"hit"=>{"title"=>"Downtown"}, "title" => "Blackhawks Over Los Angeles", "songs"=>[{"title"=>"Calling"}]})
40
+ it "responds to #save" do
41
+ hsh = nil
42
+ form.save do |f, nested|
43
+ hsh = nested
44
+ end
45
+ hsh.must_equal({"hit"=>{"title"=>"Downtown"}, "title" => "Blackhawks Over Los Angeles", "songs"=>[{"title"=>"Calling"}]})
42
46
  end
43
47
 
44
48
 
45
49
  it "creates nested forms" do
46
50
  form.hit.must_be_kind_of Reform::Form
47
- form.songs.must_be_kind_of Reform::Form::Forms
51
+ form.songs.must_be_kind_of Array
48
52
  end
49
53
 
50
54
  describe "#initialize" do
@@ -70,19 +74,7 @@ class NestedFormTest < MiniTest::Spec
70
74
  # end
71
75
  end
72
76
 
73
- describe "with empty object and cardinality" do
74
- subject { Class.new(Reform::Form) do
75
- # collection :songs, :validates => {:length => {:minimum => 1}}
76
- collection :songs, :cardinality => {:minimum => 1} do
77
- property :title
78
- end
79
- end.new(OpenStruct.new) }
80
-
81
- it "whatxxx" do
82
- subject.validate({}).must_equal false
83
- subject.errors.messages.must_equal(:"songs.size"=>["songs size is 0 but must be {:minimum=>1}"])
84
- end
85
- end
77
+
86
78
  end
87
79
 
88
80
 
@@ -194,14 +186,16 @@ class NestedFormTest < MiniTest::Spec
194
186
  form.hit.title.must_equal "Downtown"
195
187
  end
196
188
 
197
- it { form.validate({"hit" => {"title" => ""}})
189
+ it ("xxx") {
190
+ form.validate({"hit" => {"title" => ""}})
191
+ form.hit.title.must_equal ""
198
192
  form.errors[:"hit.title"].must_equal(["can't be blank"])
199
193
  }
200
194
  end
201
195
 
202
196
  class UnitTest < self
203
197
  it "keeps Forms for form collection" do
204
- form.send(:fields).songs.must_be_kind_of Reform::Form::Forms
198
+ form.send(:fields).songs.must_be_kind_of Array
205
199
  end
206
200
 
207
201
  describe "#validate" do
@@ -31,13 +31,13 @@ end
31
31
  class FieldsTest < MiniTest::Spec
32
32
  describe "#new" do
33
33
  it "accepts list of properties" do
34
- fields = Reform::Fields.new([:name, :title])
34
+ fields = Reform::Contract::Fields.new([:name, :title])
35
35
  fields.name.must_equal nil
36
36
  fields.title.must_equal nil
37
37
  end
38
38
 
39
39
  it "accepts list of properties and values" do
40
- fields = Reform::Fields.new(["name", "title"], "title" => "The Body")
40
+ fields = Reform::Contract::Fields.new(["name", "title"], "title" => "The Body")
41
41
  fields.name.must_equal nil
42
42
  fields.title.must_equal "The Body"
43
43
  end
@@ -58,11 +58,14 @@ class ReformTest < ReformSpec
58
58
 
59
59
 
60
60
  describe "::properties" do
61
- it do
61
+ subject do
62
62
  Class.new(Reform::Form) do
63
63
  properties [:name, :title]
64
- end.new(comp).to_hash.must_equal({"name"=>"Duran Duran", "title"=>"Rio"})
64
+ end.new(comp)
65
65
  end
66
+
67
+ it { subject.name.must_equal "Duran Duran" }
68
+ it { subject.title.must_equal "Rio" }
66
69
  end
67
70
 
68
71
  class SongForm < Reform::Form
@@ -163,6 +166,8 @@ class ReformTest < ReformSpec
163
166
  end
164
167
 
165
168
  describe "#errors" do
169
+ before { form.validate({})}
170
+
166
171
  it { form.errors.must_be_kind_of Reform::Form::Errors }
167
172
 
168
173
  it { form.errors.messages.must_equal({}) }
@@ -252,7 +257,7 @@ class EmptyAttributesTest < MiniTest::Spec
252
257
  form.password.must_equal "123"
253
258
  form.password_confirmation.must_equal "321"
254
259
 
255
- form.save
260
+ form.sync
256
261
  cred.password.must_equal "123"
257
262
 
258
263
  hash = {}
@@ -280,7 +285,7 @@ class ReadonlyAttributesTest < MiniTest::Spec
280
285
  form.country.must_equal "Germany"
281
286
 
282
287
 
283
- form.save
288
+ form.sync
284
289
  loc.country.must_equal "Australia" # the writer wasn't called.
285
290
 
286
291
  hash = {}
@@ -0,0 +1,81 @@
1
+ require 'test_helper'
2
+
3
+ class SaveTest < BaseTest
4
+ let (:params) {
5
+ {
6
+ "title" => "Best Of",
7
+ "hit" => {"title" => "Roxanne"},
8
+ "songs" => [{"title" => "Fallout"}, {"title" => "Roxanne"}],
9
+ :band => {:label => {:name => "Polydor"}}
10
+ }
11
+ }
12
+
13
+ let (:album) { Album.new(nil, hit, [song1, song2], band) }
14
+ let (:hit) { Song.new }
15
+ let (:song1) { Song.new }
16
+ let (:song2) { Song.new }
17
+ let (:band) { Band.new(label) }
18
+ let (:label) { Label.new }
19
+
20
+ subject { ErrorsTest::AlbumForm.new(album) }
21
+
22
+ before do
23
+ [album, hit, song1, song2, band, label].each { |mdl| mdl.extend(Saveable) }
24
+
25
+ subject.validate(params)
26
+ subject.save
27
+ end
28
+
29
+ # synced?
30
+ it { album.title.must_equal "Best Of" }
31
+ it { hit.title.must_equal "Roxanne" }
32
+ it { song1.title.must_equal "Fallout" }
33
+ it { song2.title.must_equal "Roxanne" }
34
+ it { label.name.must_equal "Polydor" }
35
+
36
+ # saved?
37
+ it { album.saved?.must_equal true }
38
+ it { hit.saved?.must_equal true }
39
+ it { song1.saved?.must_equal true }
40
+ it { song1.saved?.must_equal true }
41
+ it { band.saved?.must_equal true }
42
+ it { label.saved?.must_equal true }
43
+
44
+
45
+ describe "save: false" do
46
+ let (:form) {
47
+ Class.new(Reform::Form) do
48
+ property :hit do
49
+ property :title
50
+ end
51
+
52
+ collection :songs, :save => false do
53
+ property :title
54
+ end
55
+
56
+ property :band do # yepp, people do crazy stuff like that.
57
+ property :label, :save => false do
58
+ property :name
59
+ end
60
+ # TODO: make band a required object.
61
+ end
62
+ end
63
+ }
64
+
65
+ subject { form.new(album) }
66
+
67
+ # synced?
68
+ it { hit.title.must_equal "Roxanne" }
69
+ it { song1.title.must_equal "Fallout" }
70
+ it { song2.title.must_equal "Roxanne" }
71
+ it { label.name.must_equal "Polydor" }
72
+
73
+ # saved?
74
+ it { album.saved?.must_equal true }
75
+ it { hit.saved?.must_equal true }
76
+ it { song1.saved?.must_equal nil }
77
+ it { song1.saved?.must_equal nil }
78
+ it { band.saved?.must_equal true }
79
+ it { label.saved?.must_equal nil }
80
+ end
81
+ end
@@ -0,0 +1,38 @@
1
+ require 'test_helper'
2
+
3
+ class SetupTest < BaseTest
4
+ describe "populated" do
5
+ subject { AlbumForm.new(Album.new("Best Of", hit, [Song.new("Fallout"), Song.new("Roxanne")])) }
6
+
7
+ it { subject.title.must_equal "Best Of" }
8
+
9
+
10
+ it { subject.hit.must_be_kind_of Reform::Form }
11
+ it { subject.hit.title.must_equal "Roxanne" }
12
+
13
+ it { subject.songs.must_be_kind_of Array }
14
+ it { subject.songs.size.must_equal 2 }
15
+
16
+ it { subject.songs[0].must_be_kind_of Reform::Form }
17
+ it { subject.songs[0].title.must_equal "Fallout" }
18
+
19
+ it { subject.songs[1].must_be_kind_of Reform::Form }
20
+ it { subject.songs[1].title.must_equal "Roxanne" }
21
+ end
22
+
23
+
24
+ describe "empty" do
25
+ subject { AlbumForm.new(Album.new) }
26
+
27
+ it { subject.title.must_equal nil }
28
+
29
+
30
+ # TODO: discuss and implement.
31
+ # it { subject.hit.must_be_kind_of Reform::Form }
32
+ # it { subject.hit.title.must_equal nil }
33
+
34
+
35
+ # it { subject.songs.must_be_kind_of Reform::Form::Forms }
36
+ # it { subject.songs.size.must_equal 0 }
37
+ end
38
+ end