diff --git a/superset-frontend/src/explore/components/controls/DateFilterControl/components/DateFunctionTooltip.tsx b/superset-frontend/src/explore/components/controls/DateFilterControl/components/DateFunctionTooltip.tsx index 643c8fa5fd853..b0825347ab465 100644 --- a/superset-frontend/src/explore/components/controls/DateFilterControl/components/DateFunctionTooltip.tsx +++ b/superset-frontend/src/explore/components/controls/DateFilterControl/components/DateFunctionTooltip.tsx @@ -62,7 +62,7 @@ dateadd(datetime("2020-03-01"), 2, day)`}
{`datetrunc([datetime], [dateunit])
-dateunit = (year | month | week)`}
+dateunit = (year | quarter | month | week)`}
diff --git a/superset/utils/date_parser.py b/superset/utils/date_parser.py index 802c185d9ec64..a72d49fbf47aa 100644 --- a/superset/utils/date_parser.py +++ b/superset/utils/date_parser.py @@ -21,6 +21,7 @@ from time import struct_time from typing import Dict, List, Optional, Tuple +import pandas as pd import parsedatetime from dateutil.parser import parse from dateutil.relativedelta import relativedelta @@ -322,10 +323,12 @@ def eval(self) -> datetime: dttm = dttm.replace( month=1, day=1, hour=0, minute=0, second=0, microsecond=0 ) + if unit == "quarter": + dttm = pd.Period(pd.Timestamp(dttm), freq="Q").to_timestamp() elif unit == "month": dttm = dttm.replace(day=1, hour=0, minute=0, second=0, microsecond=0) elif unit == "week": - dttm = dttm - relativedelta(days=dttm.weekday()) + dttm -= relativedelta(days=dttm.weekday()) dttm = dttm.replace(hour=0, minute=0, second=0, microsecond=0) elif unit == "day": dttm = dttm.replace(hour=0, minute=0, second=0, microsecond=0) @@ -443,7 +446,7 @@ def datetime_parser() -> ParseResults: # pylint: disable=too-many-locals + Group( date_expr + comma - + (YEAR | MONTH | WEEK | DAY | HOUR | MINUTE | SECOND) + + (YEAR | QUARTER | MONTH | WEEK | DAY | HOUR | MINUTE | SECOND) + ppOptional(comma) ) + rparen diff --git a/tests/integration_tests/utils/date_parser_tests.py b/tests/integration_tests/utils/date_parser_tests.py index 4cf979e83c671..98e149d4057af 100644 --- a/tests/integration_tests/utils/date_parser_tests.py +++ b/tests/integration_tests/utils/date_parser_tests.py @@ -209,6 +209,10 @@ def test_datetime_eval(self): expected = datetime(2016, 1, 1, 0, 0, 0) self.assertEqual(result, expected) + result = datetime_eval("datetrunc(datetime('now'), quarter)") + expected = datetime(2016, 10, 1, 0, 0, 0) + self.assertEqual(result, expected) + result = datetime_eval("datetrunc(datetime('now'), month)") expected = datetime(2016, 11, 1, 0, 0, 0) self.assertEqual(result, expected)