@@ -4,7 +4,6 @@ module DateAccessible
4
4
TAX_YEAR = Date . new ( Rails . configuration . statefile_current_tax_year )
5
5
6
6
included do
7
- private
8
7
9
8
# Calls `date_reader` and `date_writer` on specified date properties to set
10
9
# getters and setters on the specified date properties. For use with
@@ -28,17 +27,7 @@ def self.date_reader(*properties)
28
27
properties = [ properties ] unless properties . is_a? ( Enumerable )
29
28
30
29
properties . each do |property |
31
- self . define_method ( "#{ property } _month" ) do
32
- send ( property ) &.month
33
- end
34
-
35
- self . define_method ( "#{ property } _year" ) do
36
- send ( property ) &.year
37
- end
38
-
39
- self . define_method ( "#{ property } _day" ) do
40
- send ( property ) &.day
41
- end
30
+ attr_reader :"#{ property } _month" , :"#{ property } _year" , :"#{ property } _day"
42
31
end
43
32
end
44
33
@@ -52,42 +41,32 @@ def self.date_writer(*properties)
52
41
properties = [ properties ] unless properties . is_a? ( Enumerable )
53
42
54
43
properties . each do |property |
55
- self . define_method ( "#{ property } _month=" ) do |month |
56
- change_date_property ( property , month : month ) unless month . blank?
57
- end
44
+ attr_writer :"#{ property } _month" , :"#{ property } _year" , :"#{ property } _day"
58
45
59
- self . define_method ( "#{ property } _year=" ) do |year |
60
- change_date_property ( property , year : year ) unless year . blank?
46
+ before_validation do
47
+ send (
48
+ "#{ property } =" ,
49
+ Date . new (
50
+ send ( "#{ property } _year" ) . to_i ,
51
+ send ( "#{ property } _month" ) . to_i ,
52
+ send ( "#{ property } _day" ) . to_i ,
53
+ )
54
+ )
55
+ rescue Date ::Error
56
+ send ( "#{ property } =" , nil )
61
57
end
62
58
63
- self . define_method ( "#{ property } _day=" ) do |day |
64
- change_date_property ( property , day : day ) unless day . blank?
59
+ self . class_eval do
60
+ validate :"#{ property } _date_valid"
61
+
62
+ define_method ( "#{ property } _date_valid" ) do
63
+ date = send ( property )
64
+ if date . present? && !Date . valid_date? ( date . year , date . month , date . day )
65
+ errors . add ( property , :invalid_date , message : "is not a valid calendar date" )
66
+ end
67
+ end
65
68
end
66
69
end
67
70
end
68
-
69
- # Takes in valid arguments to Date#change. Will create a new date if
70
- # `date_of_contribution` is nil, otherwise will merely modify the correct
71
- # date part. Values can be strings as long as #to_i renders an appropriate
72
- # integer. Note that Date#change only accepts :year, :month, and :day as
73
- # keys, all other keys will be treated as nothing was passed at all.
74
- #
75
- # Note that until all three fragments are passed; month, day, and year
76
- # For year, a range must be indicated on the validator on the property itself
77
- #
78
- # @see Date#change
79
- #
80
- # @param date_property [Symbol] The property to manipulate
81
- # @param args [Hash<Symbol, String | Integer>] Arguments conforming to Date#change
82
- def change_date_property ( date_property , args )
83
- existing_date = send ( date_property ) || Date . new
84
-
85
- self . send (
86
- "#{ date_property } =" ,
87
- existing_date . change ( **args . transform_values ( &:to_i ) )
88
- )
89
- rescue Date ::Error
90
- nil
91
- end
92
71
end
93
72
end
0 commit comments