datetime manipulation is now much clearer. tests were added, and expectations stated explicitly in many places. rules got lots of attention.
This commit is contained in:
@@ -3,8 +3,7 @@
|
||||
|
||||
|
||||
-export([parse/1]).
|
||||
-export([next_event/4]).
|
||||
|
||||
-export([project_next/4]).
|
||||
|
||||
|
||||
parse([Name,FromS,ToS,_Type,InS,OnS,AtS,SaveS,Letters]) ->
|
||||
@@ -25,37 +24,38 @@ parse([Name,FromS,ToS,_Type,InS,OnS,AtS,SaveS,Letters]) ->
|
||||
|
||||
|
||||
|
||||
% determines the next zone or dst change event
|
||||
% returns the latest possible times the previous period is in effect (`Until -1sec` in most cases)
|
||||
% Rules are sorted
|
||||
next_event(_BaseFlat, ZoneEnd, Offset, []) ->
|
||||
{end_until, make_times(ZoneEnd, Offset)};
|
||||
|
||||
% BaseFlat has offset defined
|
||||
% @todo ensure offset defined on BaseFlat
|
||||
% Rules are sorted in ascending order (oldest first)
|
||||
next_event(_BaseFlat=#flatzone{utc_from=#tztime{time={{_Year,_,_},_}}},
|
||||
_ZoneEnd, _ZoneOffset, [_Rule|_RestRules]) ->
|
||||
|
||||
not_done.
|
||||
|
||||
|
||||
|
||||
% returns the projected date of the next "rule event" in UTC time,
|
||||
% after the given UTCDatetime, with the given the zone Offset and current DST offset.
|
||||
project_next(Rule=#rule{from=RFrom, to=RTo}, Offset, DSTOff, UTCAfter={{AY,_,_},_}) ->
|
||||
AllYears= years(Rule),
|
||||
GoodYears= years_after(AY, AllYears),
|
||||
project_next2(Rule, Offset, UTCAfter, DSTOff, GoodYears).
|
||||
|
||||
|
||||
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||
% PRIVATE
|
||||
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||
|
||||
% create endtimes for a #flatzone, with no dst offset
|
||||
make_times(Until, Offset) ->
|
||||
make_times(Until, Offset, 0).
|
||||
|
||||
make_times(Until, Offset, DSTOffset) ->
|
||||
ezic_date:all_times(Until, Offset, DSTOffset).
|
||||
|
||||
|
||||
% returns the sorted list of years a rule existed for.
|
||||
years(Rule=#rule{from=From, to=only}) ->
|
||||
[From];
|
||||
years(Rule=#rule{from=From, to=To}) ->
|
||||
try lists:seq(From, To)
|
||||
catch error:function_clause ->
|
||||
erlang:error(bad_year_range)
|
||||
end.
|
||||
|
||||
% returns the years from the list that are greater than OR equal to Y
|
||||
years_after(Y, []) ->
|
||||
[];
|
||||
years_after(Y, Years) ->
|
||||
{GOOD, _}= lists:partition(
|
||||
fun(X) when Y =< X -> true;
|
||||
(_) -> false
|
||||
end, Years),
|
||||
GOOD.
|
||||
|
||||
|
||||
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||
% INTERNAL
|
||||
@@ -63,4 +63,45 @@ make_times(Until, Offset, DSTOffset) ->
|
||||
|
||||
|
||||
|
||||
project_next2(_,_,_,_,[]) ->
|
||||
none;
|
||||
project_next2(Rule, Offset, UTCAfter, DSTOffset, [Year|RestYears]) ->
|
||||
RuleDate= ezic_date:for_rule_utc(Rule, Offset, DSTOffset, Year),
|
||||
case ezic_date:compare(UTCAfter, RuleDate) andalso (not ezic_date:equal(UTCAfter, RuleDate)) of
|
||||
true -> RuleDate;
|
||||
_ -> project_next2(Rule, Offset, UTCAfter, DSTOffset, RestYears)
|
||||
end.
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||
% Tests of Private Methods
|
||||
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
|
||||
|
||||
|
||||
-ifdef(TEST).
|
||||
-include_lib("eunit/include/eunit.hrl").
|
||||
|
||||
years_test_() ->
|
||||
[
|
||||
?_assertEqual([1952], years(#rule{from=1952,to=only}))
|
||||
, ?_assertEqual([1952,1953], years(#rule{from=1952,to=1953}))
|
||||
, ?_assertEqual([1952,1953,1954,1955], years(#rule{from=1952,to=1955}))
|
||||
, ?_assertError(bad_year_range, years(#rule{from=1955,to=1952}))
|
||||
].
|
||||
|
||||
|
||||
% @todo type checking. lack of types worries me sometimes :(
|
||||
years_after_test_() ->
|
||||
[
|
||||
?_assertEqual([2010], years_after(2010, [2010]))
|
||||
, ?_assertEqual([2010,2011], years_after(2010, [2010,2011]))
|
||||
, ?_assertEqual([2011], years_after(2011, [2010,2011]))
|
||||
, ?_assertEqual([], years_after(2012, [2010,2011]))
|
||||
, ?_assertEqual([], years_after(2012, []))
|
||||
].
|
||||
|
||||
-endif.
|
||||
|
||||
Reference in New Issue
Block a user