{"record":{"id":"9716610354c92809","repo":"python/cpython","slug":"invalid-isoformat-string-date-string-r","errorCode":null,"errorMessage":"Invalid isoformat string: {date_string!r}","messagePattern":"Invalid isoformat string: (.+?)","errorType":"exception","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"Lib/_pydatetime.py","lineNumber":1060,"sourceCode":"\n        January 1 of year 1 is day 1.  Only the year, month and day are\n        non-zero in the result.\n        \"\"\"\n        y, m, d = _ord2ymd(n)\n        return cls(y, m, d)\n\n    @classmethod\n    def fromisoformat(cls, date_string):\n        \"\"\"Construct a date from a string in ISO 8601 format.\"\"\"\n\n        if not isinstance(date_string, str):\n            raise TypeError('Argument must be a str')\n\n        if not date_string.isascii():\n            raise ValueError('Argument must be an ASCII str')\n\n        if len(date_string) not in (7, 8, 10):\n            raise ValueError(f'Invalid isoformat string: {date_string!r}')\n\n        try:\n            return cls(*_parse_isoformat_date(date_string))\n        except Exception:\n            raise ValueError(f'Invalid isoformat string: {date_string!r}')\n\n    @classmethod\n    def fromisocalendar(cls, year, week, day):\n        \"\"\"Construct a date from the ISO year, week number and weekday.\n\n        This is the inverse of the date.isocalendar() function\"\"\"\n        return cls(*_isoweek_to_gregorian(year, week, day))\n\n    @classmethod\n    def strptime(cls, date_string, format):\n        \"\"\"Parse string according to the given date format (like time.strptime()).\n\n        For a list of supported format codes, see the documentation:","sourceCodeStart":1042,"sourceCodeEnd":1078,"githubUrl":"https://github.com/python/cpython/blob/bc6749cc3b5ae4a5e88a6cc2d5b3bebbe354eae6/Lib/_pydatetime.py#L1042-L1078","documentation":"Raised by date.fromisoformat() when the string length is not 7, 8, or 10 characters — the only shapes date.fromisoformat accepts before 3.11 (YYYY-MM-DD 10 chars, plus compact YYYYMMDD 8 and YYYY-Www 7 for ISO weeks in later versions). Any other length, including datetime strings with a 'T' time part, fails here for date.fromisoformat.","triggerScenarios":"date.fromisoformat('2024-01-01T00:00:00') (length 19, contains time — use datetime.fromisoformat); date.fromisoformat('2024-1-1') (length 8 but wrong shape may still fail later); trailing whitespace or newline making the length 11.","commonSituations":"Receiving full ISO datetimes from APIs (e.g. database DATE columns or JSON 'created_at' fields) and passing them to date.fromisoformat; untrimmed input with \\n from files; ISO week strings on Python < 3.11.","solutions":["Use datetime.fromisoformat() when the string contains a time component","Strip whitespace: date.fromisoformat(s.strip())","Slice the date part: date.fromisoformat(s[:10]) for well-formed ISO datetimes"],"exampleFix":"# before\nd = date.fromisoformat('2024-01-01T00:00:00')  # 19 chars -> ValueError\n# after\nfrom datetime import datetime\nd = datetime.fromisoformat('2024-01-01T00:00:00').date()","handlingStrategy":"validation","validationCode":"s = s.strip()\nif 'T' in s or ':' in s:\n    raise ValueError('use datetime.fromisoformat for datetime strings')\nif len(s) not in (7, 8, 10):\n    raise ValueError(f'unexpected isoformat length: {len(s)}')\nd = date.fromisoformat(s)","typeGuard":"def is_date_only_iso(s: str) -> bool:\n    return isinstance(s, str) and len(s.strip()) in (7, 8, 10) and 'T' not in s","tryCatchPattern":null,"preventionTips":["Route datetime strings to datetime.fromisoformat(...).date()","Strip whitespace/newlines before parsing","Slice s[:10] only for known-good extended-format ISO datetimes"],"tags":["datetime","valueerror","iso-8601","parsing"],"backgroundTag":null,"analyzedSha":"bc6749cc3b5ae4a5e88a6cc2d5b3bebbe354eae6","analyzedAt":"2026-08-14T22:01:13.976Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}