Skip to content

gh-151770: Fix datetime.fromisoformat() assertion on an out-of-range month with a 24:00 time#151771

Merged
StanFromIreland merged 3 commits into
python:mainfrom
tonghuaroot:gh-151770-fromiso-month-24h
Jun 20, 2026
Merged

gh-151770: Fix datetime.fromisoformat() assertion on an out-of-range month with a 24:00 time#151771
StanFromIreland merged 3 commits into
python:mainfrom
tonghuaroot:gh-151770-fromiso-month-24h

Conversation

@tonghuaroot

@tonghuaroot tonghuaroot commented Jun 20, 2026

Copy link
Copy Markdown
Contributor

datetime.fromisoformat() reached days_in_month() with month == 0 when the input combined an out-of-range (below 1) month with a 24:00 time, for example "2009-00-01T24:00:00". On a --with-pydebug build this tripped assert(month >= 1) in days_in_month (Modules/_datetimemodule.c); the pure-Python implementation in Lib/_pydatetime.py raised AssertionError on the same input. On a release build both already raised ValueError.

The 24:00 midnight-rollover guard validated only the upper month bound (month <= 12) before the days_in_month() call, and the parser does not range-check the month before that point, so a month below 1 slipped through. The matching upper-bound input "2009-13-01T24:00:00" was already rejected by the month <= 12 check.

This adds the missing month >= 1 lower bound to the guard in both implementations (mirroring the existing check_date_args validation), so an out-of-range month consistently raises ValueError. A regression test is added next to the existing out-of-range-month case in datetimetester.py.

…range month with a 24:00 time

The 24:00 midnight-rollover path validated only the upper month bound
before calling days_in_month(), so a month below 1 reached
assert(month >= 1) on a debug build (and AssertionError in the pure
Python implementation). Add the missing lower bound to both so an
out-of-range month consistently raises ValueError.

@StanFromIreland StanFromIreland left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just a few little nits, the core change is correct.

While we're dealing with this assert, can you please update it (on L58) like so:

- assert 1 <= month <= 12, month
+ assert 1 <= month <= 12, f"month must be in 1..12, not {month}"

Comment on lines +1 to +3
Fix :meth:`datetime.datetime.fromisoformat` raising an unexpected error on an
out-of-range month combined with a ``24:00`` time, such as
``"2009-00-01T24:00:00"``. It now consistently raises :exc:`ValueError`.

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
Fix :meth:`datetime.datetime.fromisoformat` raising an unexpected error on an
out-of-range month combined with a ``24:00`` time, such as
``"2009-00-01T24:00:00"``. It now consistently raises :exc:`ValueError`.
Fix :meth:`datetime.datetime.fromisoformat` raising :exc:`AssertionError`
instead of :exc:`ValueError` for an out-of-range month combined with a
``24:00`` time.

Comment thread Lib/test/datetimetester.py Outdated
"2009-04-01T12:30:90", # Second out of range
"2009-04-01T12:90:45", # Minute out of range
"2009-04-01T25:30:45", # Hour out of range
"2009-00-01T24:00:00", # Month out of range (below)

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
"2009-00-01T24:00:00", # Month out of range (below)
"2009-00-01T24:00:00", # Month below range

@tonghuaroot

Copy link
Copy Markdown
Contributor Author

Thanks @StanFromIreland — applied all three.

Comment thread Modules/_datetimemodule.c Outdated

@StanFromIreland StanFromIreland left a comment

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

@StanFromIreland StanFromIreland added needs backport to 3.13 bugs and security fixes needs backport to 3.14 bugs and security fixes needs backport to 3.15 pre-release feature fixes, bugs and security fixes labels Jun 20, 2026
@StanFromIreland StanFromIreland merged commit 1fb874c into python:main Jun 20, 2026
108 of 110 checks passed
@miss-islington-app

Copy link
Copy Markdown

Thanks @tonghuaroot for the PR, and @StanFromIreland for merging it 🌮🎉.. I'm working now to backport this PR to: 3.13, 3.14, 3.15.
🐍🍒⛏🤖

@bedevere-app

bedevere-app Bot commented Jun 20, 2026

Copy link
Copy Markdown

GH-151809 is a backport of this pull request to the 3.15 branch.

@bedevere-app bedevere-app Bot removed the needs backport to 3.15 pre-release feature fixes, bugs and security fixes label Jun 20, 2026
@miss-islington-app

Copy link
Copy Markdown

Sorry, @tonghuaroot and @StanFromIreland, I could not cleanly backport this to 3.13 due to a conflict.
Please backport using cherry_picker on command line.

cherry_picker 1fb874cc076e771c39a7bbc650dce386e3c5b7a0 3.13

@bedevere-app

bedevere-app Bot commented Jun 20, 2026

Copy link
Copy Markdown

GH-151810 is a backport of this pull request to the 3.14 branch.

@bedevere-app bedevere-app Bot removed the needs backport to 3.14 bugs and security fixes label Jun 20, 2026
@StanFromIreland

Copy link
Copy Markdown
Member

@tonghuaroot are you able to do the backport (see bot comment above)?

StanFromIreland added a commit that referenced this pull request Jun 20, 2026
…onth w/ a 24:00 time (GH-151771) (#151810)

(cherry picked from commit 1fb874c)

Co-authored-by: tonghuaroot (童话) <[email protected]>
Co-authored-by: Stan Ulbrych <[email protected]>
StanFromIreland added a commit that referenced this pull request Jun 20, 2026
…onth w/ a 24:00 time (GH-151771) (#151809)

(cherry picked from commit 1fb874c)

Co-authored-by: tonghuaroot (童话) <[email protected]>
Co-authored-by: Stan Ulbrych <[email protected]>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

needs backport to 3.13 bugs and security fixes

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants