diff --git a/arrow/parser.py b/arrow/parser.py index fc3774b09..75eaff602 100644 --- a/arrow/parser.py +++ b/arrow/parser.py @@ -689,6 +689,10 @@ def _parse_token( ) elif value in (self.locale.meridians["pm"], self.locale.meridians["PM"]): parts["am_pm"] = "pm" + if "hour" in parts and not 0 <= parts["hour"] <= 12: + raise ParserMatchError( + f"Hour token value must be between 0 and 12 inclusive for token {token!r}." + ) elif token == "W": parts["weekdate"] = value diff --git a/tests/test_parser.py b/tests/test_parser.py index 7038d880f..0842a050a 100644 --- a/tests/test_parser.py +++ b/tests/test_parser.py @@ -206,6 +206,11 @@ def test_parse_am(self): with pytest.raises(ParserMatchError): self.parser.parse("2021-01-30 14:00:00 AM", "YYYY-MM-DD HH:mm:ss A") + def test_parse_pm_invalid_hour(self): + # A PM meridian must reject out-of-range hours just like AM does. + with pytest.raises(ParserMatchError): + self.parser.parse("2021-01-30 14:00:00 PM", "YYYY-MM-DD HH:mm:ss A") + def test_parse_year_two_digit(self): self.expected = datetime(1979, 1, 1, 12, 5, 10) assert (