{"record":{"id":"326a947ddbbead2b","repo":"pytest-dev/pytest","slug":"pytest-approx-does-not-support-relative-toleranc","errorCode":null,"errorMessage":"pytest.approx() does not support relative tolerance for datetime comparisons. Use abs=timedelta(...) instead.","messagePattern":"pytest\\.approx\\(\\) does not support relative tolerance for datetime comparisons\\. Use abs=timedelta\\(\\.\\.\\.\\) instead\\.","errorType":"exception","errorClass":"TypeError","httpStatus":null,"severity":"error","filePath":"src/_pytest/approx.py","lineNumber":647,"sourceCode":"\nclass ApproxTimedelta(Approx[datetime | timedelta]):\n    \"\"\"Perform approximate comparisons where the expected value is a\n    datetime or timedelta.\n\n    Requires an explicit tolerance as a timedelta for abs, or a float for rel.\n    Relative tolerance is not supported for datetime comparisons.\n    \"\"\"\n\n    def __init__(\n        self,\n        expected: datetime | timedelta,\n        rel: float | Decimal | timedelta | None,\n        abs: float | Decimal | timedelta | None,\n        nan_ok: bool,\n    ) -> None:\n        __tracebackhide__ = True\n        if isinstance(expected, datetime) and rel is not None:\n            raise TypeError(\n                \"pytest.approx() does not support relative tolerance for \"\n                \"datetime comparisons. Use abs=timedelta(...) instead.\"\n            )\n        if nan_ok:\n            raise TypeError(\n                \"pytest.approx() does not support nan_ok for \"\n                \"datetime/timedelta comparisons.\"\n            )\n        if abs is None and rel is None:\n            raise TypeError(\n                \"pytest.approx() requires an explicit tolerance for \"\n                \"datetime/timedelta comparisons: \"\n                \"e.g. approx(expected, abs=timedelta(seconds=1)) \"\n                \"or approx(expected, rel=0.01)\"\n            )\n        if abs is not None and not isinstance(abs, timedelta):\n            raise TypeError(\n                f\"absolute tolerance for datetime/timedelta must be a \"","sourceCodeStart":629,"sourceCodeEnd":665,"githubUrl":"https://github.com/pytest-dev/pytest/blob/0d6fbdeffa57c796123f62f81f7dd370d9b7ecdc/src/_pytest/approx.py#L629-L665","documentation":"ApproxTimedelta.__init__ explicitly rejects a relative tolerance (rel) when the expected value is a datetime. Relative tolerance for an absolute timestamp is undefined (a 'fraction of' a datetime has no useful meaning and would yield a float, not a datetime), so pytest requires an absolute timedelta tolerance instead. The error message suggests the correct abs=timedelta(...) form.","triggerScenarios":"Calling approx(datetime.now(), rel=0.01); approx(datetime(2024,1,1), rel=0.001). Triggered at ApproxTimedelta.__init__ (src/_pytest/approx.py:646-650). Note: rel IS supported for timedelta expected values (where it represents a fraction of the duration), just not for datetime.","commonSituations":"Generalizing a timedelta test to datetime without changing the tolerance style; copy-pasting numeric rel syntax into datetime comparisons.","solutions":["Use an absolute timedelta tolerance: `approx(dt, abs=timedelta(seconds=1))`.","If comparing durations (timedelta expected), rel is fine: `approx(td, rel=0.01)`.","Convert datetimes to a common reference and compare the deltas with abs tolerance."],"exampleFix":"# before\napprox(datetime.now(), rel=0.01)\n# after\napprox(datetime.now(), abs=timedelta(seconds=1))","handlingStrategy":"type-guard","validationCode":"from datetime import datetime, timedelta\ndef datetime_approx_kwargs(expected):\n    if isinstance(expected, datetime):\n        return {'abs': timedelta(seconds=1)}  # never rel for datetime\n    return {'rel': 0.01}  # rel ok for timedelta\n# usage\nassert actual == approx(expected, **datetime_approx_kwargs(expected))","typeGuard":"from datetime import datetime, timedelta\ndef is_datetime(v) -> bool:\n    return isinstance(v, datetime)","tryCatchPattern":null,"preventionTips":["Never pass rel for datetime expected; use abs=timedelta(...).","In helpers, branch on isinstance(expected, datetime) before choosing tolerance.","Remember rel IS valid for timedelta (durations), just not datetime."],"tags":["pytest","approx","datetime","tolerance","relative"],"backgroundTag":null,"analyzedSha":"0d6fbdeffa57c796123f62f81f7dd370d9b7ecdc","analyzedAt":"2026-08-11T20:52:36.969Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-23T08:17:48.524Z"}