{"id":"0c7f0d18c4c8ebcd","repo":"go-redis/redis","slug":"redis-connection-pool-exhausted","errorCode":null,"errorMessage":"redis: connection pool exhausted","messagePattern":"redis: connection pool exhausted","errorType":"error_code","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/pool/pool.go","lineNumber":62,"sourceCode":"// These represent the logical state of a connection from a metrics perspective,\n// not the internal state machine state (ConnState).\nconst (\n\t// MetricStateIdle indicates the connection is idle in the pool,\n\t// ready to be acquired.\n\tMetricStateIdle = \"idle\"\n\n\t// MetricStateUsed indicates the connection is currently being used\n\t// by a client operation.\n\tMetricStateUsed = \"used\"\n)\n\nvar (\n\t// ErrClosed performs any operation on the closed client will return this error.\n\tErrClosed = errors.New(\"redis: client is closed\")\n\n\t// ErrPoolExhausted is returned from a pool connection method\n\t// when the maximum number of database connections in the pool has been reached.\n\tErrPoolExhausted = errors.New(\"redis: connection pool exhausted\")\n\n\t// ErrPoolTimeout timed out waiting to get a connection from the connection pool.\n\tErrPoolTimeout = errors.New(\"redis: connection pool timeout\")\n\n\t// ErrConnUnusableTimeout is returned when a connection is not usable and we timed out trying to mark it as unusable.\n\tErrConnUnusableTimeout = errors.New(\"redis: timed out trying to mark connection as unusable\")\n\n\t// errHookRequestedRemoval is returned when a hook requests connection removal.\n\terrHookRequestedRemoval = errors.New(\"hook requested removal\")\n\n\t// errConnNotPooled is returned when trying to return a non-pooled connection to the pool.\n\terrConnNotPooled = errors.New(\"connection not pooled\")\n\n\t// errConnEvictedIdle is passed to OnRemove hooks when a pooled connection is evicted on\n\t// Put because the idle pool is already at MaxIdleConns.\n\terrConnEvictedIdle = errors.New(\"connection evicted: idle pool at capacity\")\n\n\t// metricCallbackMu protects all global metric callback functions for thread-safe access.","sourceCodeStart":44,"sourceCodeEnd":80,"githubUrl":"https://github.com/go-redis/redis/blob/36d97525cd8076aed67cddf54778e9ea84550929/internal/pool/pool.go#L44-L80","documentation":"pool.ErrPoolExhausted is returned when the number of active connections has reached MaxActiveConns and a new connection is requested without waiting (pool.go:60-62, thrown at pool.go:627/649). Unlike ErrPoolTimeout this fails immediately (no queue wait) on the NewConn path when MaxActiveConns is bounded.","triggerScenarios":"More concurrent operations than MaxActiveConns, or a spike in demand while existing connections are checked out; also triggered when PoolSize/MaxActiveConns is misconfigured for the workload.","commonSituations":"Default PoolSize (10*runtime.NumCPU) too small for high concurrency, long-running commands (BLPOP, long scripts) hoarding connections, or connection leaks (conn not Put back).","solutions":["Increase Options.PoolSize (and MinIdleConns) to match peak concurrency.","Eliminate connection leaks — ensure transactions/pipelines complete and return conns.","Reduce concurrency or shorten long-running blocking commands.","Set MaxActiveConns appropriately or leave 0 to tie it to PoolSize."],"exampleFix":"// before\nopt := &redis.Options{Addr: addr} // small default pool\n// after\nopt := &redis.Options{\n    Addr:         addr,\n    PoolSize:     64,\n    MinIdleConns: 16,\n}","handlingStrategy":"validation","validationCode":"// Size the pool for peak concurrency before load.\nopts := &redis.Options{Addr: addr, PoolSize: runtime.GOMAXPROCS(0) * 16, MinIdleConns: 16}","typeGuard":null,"tryCatchPattern":"err := client.Get(ctx, key).Err()\nif errors.Is(err, redis.ErrPoolExhausted) {\n    // back off briefly and retry; or report load shedding\n    time.Sleep(backoff)\n}","preventionTips":["Set PoolSize to match peak concurrency; raise MinIdleConns.","Audit for connection leaks (unclosed transactions/pipelines).","Limit concurrency at the application layer to pool capacity."],"tags":["pool","capacity","configuration","concurrency"],"analyzedSha":"36d97525cd8076aed67cddf54778e9ea84550929","analyzedAt":"2026-08-06T01:08:27.376Z","schemaVersion":2}