{"record":{"id":"002d74844abb7045","repo":"redis/go-redis","slug":"redis-failed-to-create-pubsub-pool-w-002d74","errorCode":null,"errorMessage":"redis: failed to create pubsub pool: %w","messagePattern":"redis: failed to create pubsub pool: %w","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"critical","filePath":"sentinel.go","lineNumber":597,"sourceCode":"\trdb.init()\n\n\t// Initialize push notification processor using shared helper\n\t// Use void processor by default for RESP2 connections\n\trdb.pushProcessor = initializePushProcessor(opt)\n\n\t// Generate unique pool names for metrics\n\tuniqueID := generateUniqueID()\n\tmainPoolName := opt.Addr + \"_\" + uniqueID\n\tpubsubPoolName := opt.Addr + \"_\" + uniqueID + \"_pubsub\"\n\n\tvar err error\n\trdb.connPool, err = newConnPool(opt, rdb.dialHook, mainPoolName)\n\tif err != nil {\n\t\tpanic(fmt.Errorf(\"redis: failed to create connection pool: %w\", err))\n\t}\n\trdb.pubSubPool, err = newPubSubPool(opt, rdb.dialHook, pubsubPoolName)\n\tif err != nil {\n\t\tpanic(fmt.Errorf(\"redis: failed to create pubsub pool: %w\", err))\n\t}\n\n\t// Create the dedicated pipeline pool unconditionally, mirroring NewClient\n\t// via the shared buildPipelinePool helper. PipelinePoolSize < 0 opts out.\n\tif opt.PipelinePoolSize >= 0 {\n\t\tref, err := rdb.buildPipelinePool(mainPoolName + \"_pipeline\")\n\t\tif err != nil {\n\t\t\tpanic(fmt.Errorf(\"redis: failed to create pipeline connection pool: %w\", err))\n\t\t}\n\t\trdb.pipelinePool = ref\n\t}\n\n\t// Register pools for OTel async gauge metrics, matching NewClient (the\n\t// failover client previously registered none, so pool gauges were silent\n\t// for the identical standalone setup). The pipeline pool is nil when not\n\t// configured.\n\totel.RegisterPools(rdb.connPool, rdb.pubSubPool, rdb.getPipelinePool(), opt.Addr)\n","sourceCodeStart":579,"sourceCodeEnd":615,"githubUrl":"https://github.com/redis/go-redis/blob/c5cad058c72f58370553b48566302303cf8a2e89/sentinel.go#L579-L615","documentation":"NewFailoverClient also creates a dedicated Pub/Sub connection pool; failure in newPubSubPool causes a panic wrapping the underlying error with this message. Like the main pool error, this points at invalid pool options rather than a live network failure, since pool construction is local setup.","triggerScenarios":"NewFailoverClient / NewUniversalClient with sentinel options where newPubSubPool fails — typically the same invalid dialer or pool-option conditions as the main-pool failure, but surfacing in the pubsub pool step.","commonSituations":"Shared options struct reused across clients after one field was mutated to an invalid value, custom hooks that break pool setup, or memory/resource constraints during eager buffer allocation.","solutions":["Recover and inspect the wrapped error for the root cause","Verify the same FailoverOptions work with a plain NewClient to isolate sentinel-specific handling","Fix the offending option (Dialer, buffer sizes, PoolSize) before constructing the client"],"exampleFix":"// before\nrdb := redis.NewFailoverClient(opt) // panics: failed to create pubsub pool\n// after\nif opt.ReadBufferSize <= 0 { opt.ReadBufferSize = 32 * 1024 }\nrdb := redis.NewFailoverClient(opt)","handlingStrategy":"try-catch","validationCode":"if opt == nil { return errors.New(\"nil FailoverOptions\") }\nif opt.PoolSize < 0 { return fmt.Errorf(\"invalid PoolSize %d\", opt.PoolSize) }","typeGuard":null,"tryCatchPattern":"func newFailoverSafe(opt *redis.FailoverOptions) (rdb *redis.Client, err error) {\n    defer func() {\n        if r := recover(); r != nil { err = fmt.Errorf(\"NewFailoverClient: %v\", r) }\n    }()\n    rdb = redis.NewFailoverClient(opt)\n    return rdb, nil\n}","preventionTips":["Don't reuse a mutable FailoverOptions struct across clients after mutation","Keep buffer-size and pool options at library defaults unless profiling says otherwise","Wrap construction in a recover helper and log the wrapped cause"],"tags":["redis","sentinel","connection-pool","pubsub","panic"],"backgroundTag":"connection-pool-creation-failed","analyzedSha":"c5cad058c72f58370553b48566302303cf8a2e89","analyzedAt":"2026-09-01T06:50:53.388Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T10:18:20.063Z"}