Skip to content

Commit 13efeac

Browse files
committed
Fix date_parser with prefer_month_of_year wrong results
Fix two problems 1. Parser would use current month even if prefer_month_of_year was not current when relative_base was not none 2. Parser would use current month to derive 'what is the last day of this month' - for example, with prefer_month=last and prefer_day=past, but current_month=april, it would return december 30th, because it would use april to find that the last day was the 30th, when it should use the month. Additionally, add a test to test_date_parser that uses prefer_month
1 parent f659364 commit 13efeac

File tree

2 files changed

+64
-4
lines changed

2 files changed

+64
-4
lines changed

dateparser/parser.py

+7-4
Original file line numberDiff line numberDiff line change
@@ -598,10 +598,11 @@ def _correct_for_month(self, dateobj):
598598
relative_base_month = (
599599
relative_base.month if hasattr(relative_base, "month") else relative_base
600600
)
601-
if getattr(self, "_token_month", None) or relative_base_month:
601+
602+
if getattr(self, "_token_month", None):
602603
return dateobj
603604

604-
dateobj = set_correct_month_from_settings(dateobj, self.settings)
605+
dateobj = set_correct_month_from_settings(dateobj, self.settings, relative_base_month)
605606
return dateobj
606607

607608
@classmethod
@@ -613,11 +614,13 @@ def parse(cls, datestring, settings, tz=None):
613614
# correction for past, future if applicable
614615
dateobj = po._correct_for_time_frame(dateobj, tz)
615616

617+
# correction for preference of month: beginning, current, end
618+
# must happen before day so that day is derived from the correct month
619+
dateobj = po._correct_for_month(dateobj)
620+
616621
# correction for preference of day: beginning, current, end
617622
dateobj = po._correct_for_day(dateobj)
618623

619-
# correction for preference of month: beginning, current, end
620-
dateobj = po._correct_for_month(dateobj)
621624
period = po._get_period()
622625

623626
return dateobj, period

tests/test_date_parser.py

+57
Original file line numberDiff line numberDiff line change
@@ -1265,6 +1265,63 @@ def test_prefer_dates_from_with_timezone(
12651265
self.then_date_was_parsed_by_date_parser()
12661266
self.then_date_obj_exactly_is(expected)
12671267

1268+
1269+
@parameterized.expand(
1270+
[
1271+
param(
1272+
"2015",
1273+
prefer_day="current",
1274+
prefer_month="current",
1275+
today=datetime(2010, 2, 10),
1276+
expected=datetime(2015, 2, 10),
1277+
),
1278+
param(
1279+
"2015",
1280+
prefer_day="last",
1281+
prefer_month="current",
1282+
today=datetime(2010, 2, 10),
1283+
expected=datetime(2015, 2, 28),
1284+
),
1285+
param(
1286+
"2015",
1287+
prefer_day="first",
1288+
prefer_month="current",
1289+
today=datetime(2010, 2, 10),
1290+
expected=datetime(2015, 2, 1),
1291+
),
1292+
param(
1293+
"2015",
1294+
prefer_day="current",
1295+
prefer_month="last",
1296+
today=datetime(2010, 2, 10),
1297+
expected=datetime(2015, 12, 10),
1298+
),
1299+
param(
1300+
"2015",
1301+
prefer_day="last",
1302+
prefer_month="last",
1303+
today=datetime(2010, 2, 10),
1304+
expected=datetime(2015, 12, 31),
1305+
),
1306+
param(
1307+
"2020", #Leap year last day test
1308+
prefer_day="last",
1309+
prefer_month="current",
1310+
today=datetime(2010, 2, 10),
1311+
expected=datetime(2020, 2, 29),
1312+
),
1313+
]
1314+
)
1315+
def test_dates_with_no_day_or_month(
1316+
self, date_string, prefer_day, prefer_month, today=None, expected=None
1317+
):
1318+
self.given_parser(
1319+
settings={"PREFER_DAY_OF_MONTH": prefer_day, "PREFER_MONTH_OF_YEAR": prefer_month, "RELATIVE_BASE": today}
1320+
)
1321+
self.when_date_is_parsed(date_string)
1322+
self.then_date_was_parsed_by_date_parser()
1323+
self.then_date_obj_exactly_is(expected)
1324+
12681325
def given_local_tz_offset(self, offset):
12691326
self.add_patch(
12701327
patch.object(

0 commit comments

Comments
 (0)