Skip to content

Commit 079c7ce

Browse files
committed
CLN: add nice message for ValueError of 'origin' and 'offset' in resample
1 parent 3d52b25 commit 079c7ce

File tree

3 files changed

+48
-7
lines changed

3 files changed

+48
-7
lines changed

pandas/core/resample.py

+19-6
Original file line numberDiff line numberDiff line change
@@ -1356,18 +1356,31 @@ def __init__(
13561356
self.fill_method = fill_method
13571357
self.limit = limit
13581358

1359-
if origin in {"epoch", "start_day", "start"}:
1359+
if origin in {"epoch", "start", "start_day"}:
13601360
self.origin = origin
13611361
else:
1362-
self.origin = Timestamp(origin)
1363-
self.offset = Timedelta(offset) if offset is not None else None
1362+
try:
1363+
self.origin = Timestamp(origin)
1364+
except Exception as e:
1365+
raise ValueError(
1366+
"'origin' should be equal to 'epoch', 'start', 'start_day' or "
1367+
f"should be a Timestamp convertible type. Got '{origin}' instead."
1368+
) from e
1369+
1370+
try:
1371+
self.offset = Timedelta(offset) if offset is not None else None
1372+
except Exception as e:
1373+
raise ValueError(
1374+
"'offset' should be a Timedelta convertible type. "
1375+
f"Got '{offset}' instead."
1376+
) from e
13641377

13651378
# always sort time groupers
13661379
kwargs["sort"] = True
13671380

13681381
# Handle deprecated arguments since v1.1.0 of `base` and `loffset` (GH #31809)
13691382
if base is not None and offset is not None:
1370-
raise ValueError("`offset` and `base` cannot be present at the same time")
1383+
raise ValueError("'offset' and 'base' cannot be present at the same time")
13711384

13721385
if base and isinstance(freq, Tick):
13731386
# this conversion handle the default behavior of base and the
@@ -1584,8 +1597,8 @@ def _get_period_bins(self, ax):
15841597
bin_shift = 0
15851598

15861599
if isinstance(self.freq, Tick):
1587-
# GH 23882 & 31809: get adjusted bin edge labels with `origin`
1588-
# and `origin` support. This call only makes sense if the freq is a
1600+
# GH 23882 & 31809: get adjusted bin edge labels with 'origin'
1601+
# and 'origin' support. This call only makes sense if the freq is a
15891602
# Tick since offset and origin are only used in those cases.
15901603
# Not doing this check could create an extra empty bin.
15911604
p_start, end = _get_period_range_edges(

pandas/tests/resample/test_datetime_index.py

+25
Original file line numberDiff line numberDiff line change
@@ -763,6 +763,31 @@ def test_resample_origin():
763763
tm.assert_index_equal(resampled.index, exp_rng)
764764

765765

766+
@pytest.mark.parametrize(
767+
"origin",
768+
["invalid_value", "epch", "startday", "startt", "2000-30-30", object()],
769+
)
770+
def test_resample_bad_origin(origin):
771+
rng = date_range("2000-01-01 00:00:00", "2000-01-01 02:00", freq="s")
772+
ts = Series(np.random.randn(len(rng)), index=rng)
773+
msg = ("'origin' should be equal to 'epoch', 'start', 'start_day' or "
774+
f"should be a Timestamp convertible type. Got '{origin}' instead.")
775+
with pytest.raises(ValueError, match=msg):
776+
ts.resample("5min", origin=origin)
777+
778+
779+
@pytest.mark.parametrize(
780+
"offset",
781+
["invalid_value", "12dayys", "2000-30-30", object()],
782+
)
783+
def test_resample_bad_offset(offset):
784+
rng = date_range("2000-01-01 00:00:00", "2000-01-01 02:00", freq="s")
785+
ts = Series(np.random.randn(len(rng)), index=rng)
786+
msg = f"'offset' should be a Timedelta convertible type. Got '{offset}' instead."
787+
with pytest.raises(ValueError, match=msg):
788+
ts.resample("5min", offset=offset)
789+
790+
766791
def test_resample_origin_prime_freq():
767792
# GH 31809
768793
start, end = "2000-10-01 23:30:00", "2000-10-02 00:30:00"

pandas/tests/resample/test_deprecated.py

+4-1
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,9 @@ def test_deprecating_on_loffset_and_base():
5555
df.resample("3T", base=0).sum()
5656
with tm.assert_produces_warning(FutureWarning):
5757
df.resample("3T", loffset="0s").sum()
58+
msg = "'offset' and 'base' cannot be present at the same time"
59+
with pytest.raises(ValueError, match=msg):
60+
df.groupby("a").resample("3T", base=0, offset=0).sum()
5861

5962

6063
@all_ts
@@ -228,7 +231,7 @@ def test_resample_with_non_zero_base(start, end, start_freq, end_freq, base, off
228231
result = s.resample(end_freq, base=base).mean()
229232
result = result.to_timestamp(end_freq)
230233

231-
# test that the replacement argument `offset` works
234+
# test that the replacement argument 'offset' works
232235
result_offset = s.resample(end_freq, offset=offset).mean()
233236
result_offset = result_offset.to_timestamp(end_freq)
234237
tm.assert_series_equal(result, result_offset)

0 commit comments

Comments
 (0)