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 643c8fa5fd8..b0825347ab4 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 802c185d9ec..a72d49fbf47 100644
--- a/superset/utils/date_parser.py
+++ b/superset/utils/date_parser.py
@@ -21,6 +21,7 @@ from datetime import datetime, timedelta
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 @@ class EvalDateTruncFunc: # pylint: disable=too-few-public-methods
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 4cf979e83c6..98e149d4057 100644
--- a/tests/integration_tests/utils/date_parser_tests.py
+++ b/tests/integration_tests/utils/date_parser_tests.py
@@ -209,6 +209,10 @@ class TestDateParser(SupersetTestCase):
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)