{"record":{"id":"f40cd87a664c206f","repo":"python/cpython","slug":"offset-must-be-a-non-negative-integer-got-r","errorCode":null,"errorMessage":"offset must be a non-negative integer (got {!r})","messagePattern":"offset must be a non-negative integer \\(got (.+?)\\)","errorType":"exception","errorClass":"TypeError","httpStatus":null,"severity":"error","filePath":"Lib/asyncio/base_events.py","lineNumber":1010,"sourceCode":"            return total_sent\n        finally:\n            if total_sent > 0 and hasattr(file, 'seek'):\n                file.seek(offset + total_sent)\n\n    def _check_sendfile_params(self, sock, file, offset, count):\n        if 'b' not in getattr(file, 'mode', 'b'):\n            raise ValueError(\"file should be opened in binary mode\")\n        if not sock.type == socket.SOCK_STREAM:\n            raise ValueError(\"only SOCK_STREAM type sockets are supported\")\n        if count is not None:\n            if not isinstance(count, int):\n                raise TypeError(\n                    \"count must be a positive integer (got {!r})\".format(count))\n            if count <= 0:\n                raise ValueError(\n                    \"count must be a positive integer (got {!r})\".format(count))\n        if not isinstance(offset, int):\n            raise TypeError(\n                \"offset must be a non-negative integer (got {!r})\".format(\n                    offset))\n        if offset < 0:\n            raise ValueError(\n                \"offset must be a non-negative integer (got {!r})\".format(\n                    offset))\n\n    async def _connect_sock(self, exceptions, addr_info, local_addr_infos=None):\n        \"\"\"Create, bind and connect one socket.\"\"\"\n        my_exceptions = []\n        exceptions.append(my_exceptions)\n        family, type_, proto, _, address = addr_info\n        sock = None\n        try:\n            try:\n                sock = socket.socket(family=family, type=type_, proto=proto)\n                sock.setblocking(False)\n                if local_addr_infos is not None:","sourceCodeStart":992,"sourceCodeEnd":1028,"githubUrl":"https://github.com/python/cpython/blob/bc6749cc3b5ae4a5e88a6cc2d5b3bebbe354eae6/Lib/asyncio/base_events.py#L992-L1028","documentation":"Raised by asyncio's sendfile parameter validation (_check_sendfile_params) when the `offset` argument to loop.sendfile() is not an int. `offset` is the byte position in the file to start sending from, and it must be an int (bools aside, anything else — float, string, None as a non-default — is rejected). This TypeError fires before any data is sent.","triggerScenarios":"Calling asyncio.sendfile(transport, file, offset) where offset is a float (e.g. 0.0), a string, or None. Note offset is positional and required to be an int; there is no 'None means default' escape hatch for it.","commonSituations":"Computing offset from file.tell() plus arithmetic that yields a float, or loading it from JSON/config where it arrives as a string or float.","solutions":["Coerce offset to int at the call site: offset = int(offset).","Use file.tell() (already an int) directly instead of recomputing a float offset.","Validate offset >= 0 as well, since a negative int will raise the companion ValueError."],"exampleFix":"// before\nawait loop.sendfile(transport, f, offset=1024.0, count=None)  # TypeError\n\n// after\nawait loop.sendfile(transport, f, offset=1024, count=None)","handlingStrategy":"validation","validationCode":"assert isinstance(offset, int) and not isinstance(offset, bool), 'offset must be an int'","typeGuard":"def is_valid_sendfile_offset(offset: object) -> bool:\n    return isinstance(offset, int) and not isinstance(offset, bool)","tryCatchPattern":"try:\n    await loop.sendfile(transport, f, offset, count)\nexcept TypeError as e:\n    if 'offset must be' not in str(e):\n        raise\n    offset = int(offset)\n    await loop.sendfile(transport, f, offset, count)","preventionTips":["Derive offset from file.tell() (always int) instead of recomputing it from float arithmetic.","Sanitize offsets arriving from JSON — json numbers may parse as float.","Wrap sendfile once in your own helper that coerces and validates offset/count."],"tags":["asyncio","sendfile","type-error","validation"],"backgroundTag":null,"analyzedSha":"bc6749cc3b5ae4a5e88a6cc2d5b3bebbe354eae6","analyzedAt":"2026-08-14T22:01:13.976Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}