{"record":{"id":"4a3e0e645b97d200","repo":"redis/redis-py","slug":"connectionerror-exc","errorCode":null,"errorMessage":"ConnectionError(exc)","messagePattern":"ConnectionError\\(exc\\)","errorType":"exception","errorClass":"ConnectionError","httpStatus":null,"severity":"error","filePath":"redis/asyncio/connection.py","lineNumber":878,"sourceCode":"                error_type=e,\n                retry_attempts=actual_retry_attempts,\n                is_internal=False,\n            )\n            raise e\n        except OSError as e:\n            e = ConnectionError(self._error_message(e))\n            await record_error_count(\n                server_address=getattr(self, \"host\", None),\n                server_port=getattr(self, \"port\", None),\n                network_peer_address=getattr(self, \"host\", None),\n                network_peer_port=getattr(self, \"port\", None),\n                error_type=e,\n                retry_attempts=actual_retry_attempts,\n                is_internal=False,\n            )\n            raise e\n        except Exception as exc:\n            raise ConnectionError(exc) from exc\n\n        try:\n            if not self.redis_connect_func:\n                # Use the default on_connect function\n                await self.on_connect_check_health(check_health=check_health)\n            else:\n                # Use the passed function redis_connect_func\n                (\n                    await self.redis_connect_func(self)\n                    if asyncio.iscoroutinefunction(self.redis_connect_func)\n                    else self.redis_connect_func(self)\n                )\n        except RedisError:\n            # clean up after any error in on_connect\n            await self.disconnect()\n            raise\n\n        # run any user callbacks. right now the only internal callback","sourceCodeStart":860,"sourceCodeEnd":896,"githubUrl":"https://github.com/redis/redis-py/blob/6a6b581b48225afa0b76912d1028c6035baee932/redis/asyncio/connection.py#L860-L896","documentation":"ConnectionError raised as a catch-all in Connection.connect_check_health (redis/asyncio/connection.py:877). After socket-level errors (OSError) and timeouts are handled specifically, any remaining exception during connect/on_connect is wrapped in ConnectionError and re-raised. This preserves a consistent error type for unexpected connection-time failures (TLS handshake errors, SSL issues, decoder faults, etc.).","triggerScenarios":"TLS/SSL handshake failures, errors thrown by a custom redis_connect_func, unexpected exceptions from on_connect (auth callback failures, parser init errors), or any non-OSError during connection establishment.","commonSituations":"TLS misconfiguration (bad cert, wrong CA); a custom redis_connect_func that raises; auth provider failures during the initial HELLO/AUTH; event-loop or transport errors.","solutions":["Inspect the chained __cause__ exception for the real underlying error","For TLS errors, verify ssl_ca_certs / ssl_certfile / ssl_keyfile / ssl_cert_reqs","If using a custom redis_connect_func, ensure it does not raise on healthy connections","Check auth/credential_provider setup and server reachability"],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":"# generic; verify TLS config and reachability first\nif ssl and not os.path.exists(ca_path):\n    raise ValueError('ca cert missing')","typeGuard":null,"tryCatchPattern":"try:\n    await client.ping()\nexcept ConnectionError as e:\n    cause = e.__cause__  # the real underlying error\n    log.error('connect failed: %r', cause)","preventionTips":["Inspect __cause__ on the wrapped ConnectionError for the real fault","Validate TLS material and host reachability before connecting","Ensure custom redis_connect_func does not raise on healthy servers"],"tags":["async","connection","tls","transport","catch-all"],"backgroundTag":null,"analyzedSha":"6a6b581b48225afa0b76912d1028c6035baee932","analyzedAt":"2026-08-10T12:52:44.840Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}