Skip to content

[6.x] Fix range date fields not updating with configured timezone#14984

Closed
lazerg wants to merge 1 commit into
statamic:6.xfrom
lazerg:fix/issue-14636-range-dates-timezone
Closed

[6.x] Fix range date fields not updating with configured timezone#14984
lazerg wants to merge 1 commit into
statamic:6.xfrom
lazerg:fix/issue-14636-range-dates-timezone

Conversation

@lazerg

@lazerg lazerg commented Jul 12, 2026

Copy link
Copy Markdown
Contributor

Fixes #14636

Reworked from the original backend approach after @jasonvarga pointed out it was a no-op on real saves: the Control Panel always submits an absolute UTC value, and Carbon::parse() ignores its timezone argument once the string carries an offset. The real fix is on the frontend.

Root cause

DateFieldtype.vue's datePickerUpdated() handles single dates and ranges differently. For a single date, the naive CalendarDateTime from the picker is first interpreted in the field's configured timezone before being converted to UTC:

if (!this.isRange && !value.offset && !value.timeZone) {
    value = toZoned(value, this.displayTimezone);
}
// ...
return this.update(toTimeZone(value, 'UTC').toAbsoluteString());

The range branch skipped that step and sent the naive start/end straight to UTC via toZoned(start, 'UTC'), so the field's wall-clock time was treated as if it were already UTC. Loading uses parseAbsolute(value, displayTimezone) (correct), so the load/save round-trip was asymmetric and the stored value drifted by the offset on every save.

Fix

Interpret the range's naive start/end in displayTimezone before converting to UTC, the same way single dates already do.

Test

Added a DateFieldtype.test.js case that drives datePickerUpdated() with the CalendarDateTime objects the picker actually emits (range + time mode, configured timezone). For a New York field, entering 05:00 now saves 09:00Z; it fails on the current code (which saves 05:00Z) and passes with the fix. Full unit suite green.

@lazerg lazerg changed the title Fix range date fields not updating with configured timezone [6.x] Fix range date fields not updating with configured timezone Jul 12, 2026
@jasonvarga

Copy link
Copy Markdown
Member

Thanks for taking a crack at this! After tracing it through, this doesn't actually fix #14636.

The Control Panel always submits datetime values with an explicit UTC offset already applied (e.g. 2012-08-29T05:00:00.000Z), and Carbon::parse() ignores the second $timezone argument once a string has its own offset. So this change has no effect on real CP saves — the new tests only pass because they use naive strings without an offset, which isn't what the frontend actually sends.

The real bug is likely in DateFieldtype.vue: for single dates, a naive value gets converted into the field's configured timezone before being converted to UTC, but that step is skipped for range mode.

Closing for now — feel free to update the PR description if you're actually intending on fixing a different issue, and we can reopen it if you want to keep going.

@jasonvarga jasonvarga closed this Jul 13, 2026
@lazerg

lazerg commented Jul 13, 2026

Copy link
Copy Markdown
Contributor Author

@jasonvarga you were right, thanks for tracing it. The CP sends an absolute UTC value so the Carbon timezone arg did nothing on real saves, and only my naive test strings made it look fixed.

I reworked it as the frontend fix you pointed at. The range branch in datePickerUpdated() was sending the naive start/end straight to UTC (toZoned(start, 'UTC')) instead of first anchoring them to the field's timezone the way single dates do. It now mirrors the single-date path.

The new test drives datePickerUpdated() with the CalendarDateTime objects the picker actually emits: a New York field entering 05:00 now saves 09:00Z instead of 05:00Z. Fails on the old code, passes now, full unit suite green.

@lazerg

lazerg commented Jul 13, 2026

Copy link
Copy Markdown
Contributor Author

Turns out GitHub won't let this one reopen since the branch was force-pushed with the rework (state cannot be changed... force-pushed or recreated). I've put the frontend fix up as #15001 from the same branch. Continuing there — sorry for the shuffle.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Range dates not updating properly

2 participants