Skip to content

Commit 94cfffa

Browse files
authored
fix(options): Add buffer sizes to failover. Update README (#3468)
* fix(options): Add buffer sizes to failover. Update README * fix(spellcheck): add KiB in wordlist * fix(comment): fix defaul value in comment * fixes #3465
1 parent 2c29ded commit 94cfffa

File tree

8 files changed

+65
-23
lines changed

8 files changed

+65
-23
lines changed

.github/wordlist.txt

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -74,4 +74,5 @@ Azure
7474
StreamingCredentialsProvider
7575
oauth
7676
entraid
77-
MiB
77+
MiB
78+
KiB

README.md

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ In `go-redis` we are aiming to support the last three releases of Redis. Current
2020
- [Redis 7.2](https://raw.githubusercontent.com/redis/redis/7.2/00-RELEASENOTES) - using Redis Stack 7.2 for modules support
2121
- [Redis 7.4](https://raw.githubusercontent.com/redis/redis/7.4/00-RELEASENOTES) - using Redis Stack 7.4 for modules support
2222
- [Redis 8.0](https://raw.githubusercontent.com/redis/redis/8.0/00-RELEASENOTES) - using Redis CE 8.0 where modules are included
23+
- [Redis 8.2](https://raw.githubusercontent.com/redis/redis/8.2/00-RELEASENOTES) - using Redis CE 8.2 where modules are included
2324

2425
Although the `go.mod` states it requires at minimum `go 1.18`, our CI is configured to run the tests against all three
2526
versions of Redis and latest two versions of Go ([1.23](https://go.dev/doc/devel/release#go1.23.0),
@@ -77,6 +78,7 @@ key value NoSQL database that uses RocksDB as storage engine and is compatible w
7778
- [Redis Ring](https://redis.uptrace.dev/guide/ring.html).
7879
- [Redis Performance Monitoring](https://redis.uptrace.dev/guide/redis-performance-monitoring.html).
7980
- [Redis Probabilistic [RedisStack]](https://redis.io/docs/data-types/probabilistic/)
81+
- [Customizable read and write buffers size.](#custom-buffer-sizes)
8082

8183
## Installation
8284

@@ -372,6 +374,21 @@ For example:
372374
```
373375
You can find further details in the [query dialect documentation](https://redis.io/docs/latest/develop/interact/search-and-query/advanced-concepts/dialects/).
374376
377+
#### Custom buffer sizes
378+
Prior to v9.12, the buffer size was the default go value of 4096 bytes. Starting from v9.12,
379+
go-redis uses 256KiB read and write buffers by default for optimal performance.
380+
For high-throughput applications or large pipelines, you can customize buffer sizes:
381+
382+
```go
383+
rdb := redis.NewClient(&redis.Options{
384+
Addr: "localhost:6379",
385+
ReadBufferSize: 1024 * 1024, // 1MiB read buffer
386+
WriteBufferSize: 1024 * 1024, // 1MiB write buffer
387+
})
388+
```
389+
390+
**Important**: If you experience any issues with the default buffer sizes, please try setting them to the go default of 4096 bytes.
391+
375392
## Contributing
376393
We welcome contributions to the go-redis library! If you have a bug fix, feature request, or improvement, please open an issue or pull request on GitHub.
377394
We appreciate your help in making go-redis better for everyone.
@@ -412,6 +429,7 @@ vals, err := rdb.Eval(ctx, "return {KEYS[1],ARGV[1]}", []string{"key"}, "hello")
412429
res, err := rdb.Do(ctx, "set", "key", "value").Result()
413430
```
414431
432+
415433
## Run the test
416434
417435
go-redis will start a redis-server and run the test cases.

internal/pool/buffer_size_test.go

Lines changed: 14 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -34,12 +34,12 @@ var _ = Describe("Buffer Size Configuration", func() {
3434
Expect(err).NotTo(HaveOccurred())
3535
defer connPool.CloseConn(cn)
3636

37-
// Check that default buffer sizes are used (0.5MiB)
37+
// Check that default buffer sizes are used (256KiB)
3838
writerBufSize := getWriterBufSizeUnsafe(cn)
3939
readerBufSize := getReaderBufSizeUnsafe(cn)
4040

41-
Expect(writerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 0.5MiB buffer size
42-
Expect(readerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 0.5MiB buffer size
41+
Expect(writerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 256KiB buffer size
42+
Expect(readerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 256KiB buffer size
4343
})
4444

4545
It("should use custom buffer sizes when specified", func() {
@@ -79,28 +79,28 @@ var _ = Describe("Buffer Size Configuration", func() {
7979
Expect(err).NotTo(HaveOccurred())
8080
defer connPool.CloseConn(cn)
8181

82-
// Check that default buffer sizes are used (0.5MiB)
82+
// Check that default buffer sizes are used (256KiB)
8383
writerBufSize := getWriterBufSizeUnsafe(cn)
8484
readerBufSize := getReaderBufSizeUnsafe(cn)
8585

86-
Expect(writerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 0.5MiB buffer size
87-
Expect(readerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 0.5MiB buffer size
86+
Expect(writerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 256KiB buffer size
87+
Expect(readerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 256KiB buffer size
8888
})
8989

90-
It("should use 0.5MiB default buffer sizes for standalone NewConn", func() {
91-
// Test that NewConn (without pool) also uses 0.5MiB defaults
90+
It("should use 256KiB default buffer sizes for standalone NewConn", func() {
91+
// Test that NewConn (without pool) also uses 256KiB buffers
9292
netConn := newDummyConn()
9393
cn := pool.NewConn(netConn)
9494
defer cn.Close()
9595

9696
writerBufSize := getWriterBufSizeUnsafe(cn)
9797
readerBufSize := getReaderBufSizeUnsafe(cn)
9898

99-
Expect(writerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 0.5MiB buffer size
100-
Expect(readerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 0.5MiB buffer size
99+
Expect(writerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 256KiB buffer size
100+
Expect(readerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 256KiB buffer size
101101
})
102102

103-
It("should use 0.5MiB defaults even when pool is created directly without buffer sizes", func() {
103+
It("should use 256KiB defaults even when pool is created directly without buffer sizes", func() {
104104
// Test the scenario where someone creates a pool directly (like in tests)
105105
// without setting ReadBufferSize and WriteBufferSize
106106
connPool = pool.NewConnPool(&pool.Options{
@@ -114,12 +114,12 @@ var _ = Describe("Buffer Size Configuration", func() {
114114
Expect(err).NotTo(HaveOccurred())
115115
defer connPool.CloseConn(cn)
116116

117-
// Should still get 0.5MiB defaults because NewConnPool sets them
117+
// Should still get 256KiB defaults because NewConnPool sets them
118118
writerBufSize := getWriterBufSizeUnsafe(cn)
119119
readerBufSize := getReaderBufSizeUnsafe(cn)
120120

121-
Expect(writerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 0.5MiB buffer size
122-
Expect(readerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 0.5MiB buffer size
121+
Expect(writerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 256KiB buffer size
122+
Expect(readerBufSize).To(Equal(proto.DefaultBufferSize)) // Default 256KiB buffer size
123123
})
124124
})
125125

internal/proto/reader.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,8 @@ import (
1212
"github.com/redis/go-redis/v9/internal/util"
1313
)
1414

15-
// DefaultBufferSize is the default size for read/write buffers (0.5MiB)
16-
const DefaultBufferSize = 512 * 1024
15+
// DefaultBufferSize is the default size for read/write buffers (256 KiB).
16+
const DefaultBufferSize = 256 * 1024
1717

1818
// redis resp protocol data type.
1919
const (

options.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -135,14 +135,14 @@ type Options struct {
135135
// Larger buffers can improve performance for commands that return large responses.
136136
// Smaller buffers can improve memory usage for larger pools.
137137
//
138-
// default: 0.5MiB (524288 bytes)
138+
// default: 256KiB (262144 bytes)
139139
ReadBufferSize int
140140

141141
// WriteBufferSize is the size of the bufio.Writer buffer for each connection.
142142
// Larger buffers can improve performance for large pipelines and commands with many arguments.
143143
// Smaller buffers can improve memory usage for larger pools.
144144
//
145-
// default: 0.5MiB (524288 bytes)
145+
// default: 256KiB (262144 bytes)
146146
WriteBufferSize int
147147

148148
// PoolFIFO type of connection pool.

osscluster.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -96,14 +96,14 @@ type ClusterOptions struct {
9696
// Larger buffers can improve performance for commands that return large responses.
9797
// Smaller buffers can improve memory usage for larger pools.
9898
//
99-
// default: 0.5MiB (524288 bytes)
99+
// default: 256KiB (262144 bytes)
100100
ReadBufferSize int
101101

102102
// WriteBufferSize is the size of the bufio.Writer buffer for each connection.
103103
// Larger buffers can improve performance for large pipelines and commands with many arguments.
104104
// Smaller buffers can improve memory usage for larger pools.
105105
//
106-
// default: 0.5MiB (524288 bytes)
106+
// default: 256KiB (262144 bytes)
107107
WriteBufferSize int
108108

109109
TLSConfig *tls.Config

ring.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -128,14 +128,14 @@ type RingOptions struct {
128128
// Larger buffers can improve performance for commands that return large responses.
129129
// Smaller buffers can improve memory usage for larger pools.
130130
//
131-
// default: 0.5MiB (524288 bytes)
131+
// default: 256KiB (262144 bytes)
132132
ReadBufferSize int
133133

134134
// WriteBufferSize is the size of the bufio.Writer buffer for each connection.
135135
// Larger buffers can improve performance for large pipelines and commands with many arguments.
136136
// Smaller buffers can improve memory usage for larger pools.
137137
//
138-
// default: 0.5MiB (524288 bytes)
138+
// default: 256KiB (262144 bytes)
139139
WriteBufferSize int
140140

141141
TLSConfig *tls.Config

sentinel.go

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -90,6 +90,20 @@ type FailoverOptions struct {
9090
WriteTimeout time.Duration
9191
ContextTimeoutEnabled bool
9292

93+
// ReadBufferSize is the size of the bufio.Reader buffer for each connection.
94+
// Larger buffers can improve performance for commands that return large responses.
95+
// Smaller buffers can improve memory usage for larger pools.
96+
//
97+
// default: 256KiB (262144 bytes)
98+
ReadBufferSize int
99+
100+
// WriteBufferSize is the size of the bufio.Writer buffer for each connection.
101+
// Larger buffers can improve performance for large pipelines and commands with many arguments.
102+
// Smaller buffers can improve memory usage for larger pools.
103+
//
104+
// default: 256KiB (262144 bytes)
105+
WriteBufferSize int
106+
93107
PoolFIFO bool
94108

95109
PoolSize int
@@ -138,6 +152,9 @@ func (opt *FailoverOptions) clientOptions() *Options {
138152
MinRetryBackoff: opt.MinRetryBackoff,
139153
MaxRetryBackoff: opt.MaxRetryBackoff,
140154

155+
ReadBufferSize: opt.ReadBufferSize,
156+
WriteBufferSize: opt.WriteBufferSize,
157+
141158
DialTimeout: opt.DialTimeout,
142159
ReadTimeout: opt.ReadTimeout,
143160
WriteTimeout: opt.WriteTimeout,
@@ -178,6 +195,9 @@ func (opt *FailoverOptions) sentinelOptions(addr string) *Options {
178195
MinRetryBackoff: opt.MinRetryBackoff,
179196
MaxRetryBackoff: opt.MaxRetryBackoff,
180197

198+
ReadBufferSize: opt.ReadBufferSize,
199+
WriteBufferSize: opt.WriteBufferSize,
200+
181201
DialTimeout: opt.DialTimeout,
182202
ReadTimeout: opt.ReadTimeout,
183203
WriteTimeout: opt.WriteTimeout,
@@ -224,6 +244,9 @@ func (opt *FailoverOptions) clusterOptions() *ClusterOptions {
224244
MinRetryBackoff: opt.MinRetryBackoff,
225245
MaxRetryBackoff: opt.MaxRetryBackoff,
226246

247+
ReadBufferSize: opt.ReadBufferSize,
248+
WriteBufferSize: opt.WriteBufferSize,
249+
227250
DialTimeout: opt.DialTimeout,
228251
ReadTimeout: opt.ReadTimeout,
229252
WriteTimeout: opt.WriteTimeout,

0 commit comments

Comments
 (0)