Last active
August 29, 2015 14:10
-
-
Save bethesque/45f9c0e635eb8527d44d to your computer and use it in GitHub Desktop.
Reform writeable:false behaviour not the same as virtual: true
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
require 'minitest/autorun' | |
require 'date' | |
require 'reform' # 1.2.2 | |
Person = Struct.new(:date_of_birth) | |
class DateForm < Reform::Form | |
property :day | |
property :month | |
property :year | |
validate :validate_date | |
def validate_date | |
# Need a more elegant way to add error to base of date_of_birth. | |
# Using :base will add the error to the Person object. | |
# Can't hardcode the message to "Date of birth ..." | |
# because this form can be used for | |
# more than one date property. | |
unless valid_date? | |
errors.add(:'', "is not a valid date") | |
end | |
end | |
def date | |
Date.parse("#{year}-#{month}-#{day}") | |
end | |
def valid_date? | |
date | |
true | |
rescue ArgumentError => e | |
false | |
end | |
end | |
class PersonForm < Reform::Form | |
NilDate = Struct.new(:year, :month, :day) | |
property :date_of_birth, | |
form: DateForm, | |
populate_if_empty: NilDate, | |
# virtual: true | |
writeable: false, | |
readable: false | |
def date_of_birth | |
super || DateForm.new(NilDate.new) | |
end | |
def sync | |
result = super | |
model.date_of_birth = date_of_birth.date | |
result | |
end | |
end | |
describe PersonForm do | |
let(:date) { nil } | |
let(:person) { Person.new(date) } | |
let(:form_data) do | |
{ | |
"date_of_birth" => { | |
"day" => "2", | |
"month" => "1", | |
"year" => "2000", | |
} | |
} | |
end | |
subject { PersonForm.new(person) } | |
describe "date_of_birth" do | |
describe "with a date" do | |
let(:date) { Date.new(2014, 1, 2) } | |
it "is a DateForm" do | |
assert_kind_of(DateForm, subject.date_of_birth) | |
end | |
describe "day" do | |
it 'returns the day' do | |
assert_equal(2, subject.date_of_birth.day) | |
end | |
end | |
describe "month" do | |
it 'returns the month number' do | |
assert_equal(1, subject.date_of_birth.month) | |
end | |
end | |
describe "year" do | |
it 'returns the year' do | |
assert_equal(2014, subject.date_of_birth.year) | |
end | |
end | |
end | |
describe "with a nil date" do | |
it "is a DateForm" do | |
assert_kind_of(DateForm, subject.date_of_birth) | |
end | |
describe "day" do | |
it 'returns nil' do | |
assert_nil(subject.date_of_birth.day) | |
end | |
end | |
describe "month" do | |
it 'returns nil' do | |
assert_nil(subject.date_of_birth.month) | |
end | |
end | |
describe "year" do | |
it 'returns nil' do | |
assert_nil(subject.date_of_birth.year) | |
end | |
end | |
end | |
end | |
describe "validate" do | |
before do | |
subject.validate(form_data) | |
end | |
describe "with an invalid date" do | |
let(:form_data) do | |
{ | |
"date_of_birth" => { | |
"day" => "30", | |
"month" => "2", | |
"year" => "2000", | |
} | |
} | |
end | |
it 'returns an error' do | |
assert_equal(["Date of birth is not a valid date"], subject.errors.full_messages) | |
end | |
end | |
describe "with a valid date" do | |
it "does not return an error" do | |
assert_empty(subject.errors) | |
end | |
end | |
end | |
describe "sync" do | |
before do | |
subject.validate(form_data) | |
subject.sync | |
end | |
describe "with an existing date" do | |
let(:date) { Date.new(2014, 3, 4) } | |
it "sets the date_of_birth" do | |
assert_equal(Date.new(2000, 1, 2), person.date_of_birth) | |
end | |
end | |
describe "with no existing date" do | |
it "sets the date_of_birth" do | |
assert_equal(Date.new(2000, 1, 2), person.date_of_birth) | |
end | |
end | |
end | |
end |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
1) Error: | |
PersonForm::sync::with no existing date#test_0001_sets the date_of_birth: | |
ArgumentError: invalid date | |
reform.rb:26:in `parse' | |
reform.rb:26:in `date' | |
reform.rb:54:in `sync' | |
reform.rb:161:in `block (3 levels) in <main>' | |
2) Failure: | |
PersonForm::date_of_birth::with a date::month#test_0001_returns the month number [reform.rb:93]: | |
Expected: 1 | |
Actual: nil | |
3) Failure: | |
PersonForm::date_of_birth::with a date::year#test_0001_returns the year [reform.rb:98]: | |
Expected: 2014 | |
Actual: nil | |
4) Error: | |
PersonForm::sync::with an existing date#test_0001_sets the date_of_birth: | |
ArgumentError: invalid date | |
reform.rb:26:in `parse' | |
reform.rb:26:in `date' | |
reform.rb:54:in `sync' | |
reform.rb:161:in `block (3 levels) in <main>' | |
5) Failure: | |
PersonForm::validate::with an invalid date#test_0001_returns an error [reform.rb:144]: | |
--- expected | |
+++ actual | |
@@ -1 +1 @@ | |
-["Date of birth is not a valid date"] | |
+[] | |
6) Failure: | |
PersonForm::date_of_birth::with a date::day#test_0001_returns the day [reform.rb:88]: | |
Expected: 2 | |
Actual: nil | |
12 runs, 11 assertions, 4 failures, 2 errors, 0 skips |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment