Skip to content

Commit 1ac385f

Browse files
Merge pull request #155 from Aireuropa/feature/redis_cluster
added redis cluster support
2 parents aa5bb57 + 5aded4f commit 1ac385f

30 files changed

+2038
-135
lines changed

.env.dist

+2-2
Original file line numberDiff line numberDiff line change
@@ -115,9 +115,9 @@ HEALTHCHECK_ALLOW_INSECURE=0
115115
# --- CACHE
116116
# --- REDIS SERVER
117117
REDIS_DB=0
118-
REDIS_HOST=
118+
REDIS_HOSTS=:6379
119119
REDIS_PASSWORD=
120-
REDIS_PORT=6379
120+
121121

122122
# --- TTL
123123
# Fallback storage TTL when saving the cache when no header is specified.

.github/workflows/main.yml

+2-2
Original file line numberDiff line numberDiff line change
@@ -111,7 +111,7 @@ jobs:
111111
./go-proxy-cache -debug -config=test/full-setup/config.yml &
112112
make test
113113
env:
114-
REDIS_HOST: redis
114+
REDIS_HOSTS: redis:6379
115115
NGINX_HOST_80: nginx:40080
116116
NGINX_HOST_443: nginx:40443
117117
NGINX_HOST_WS: nginx:40081
@@ -123,7 +123,7 @@ jobs:
123123
make cover
124124
make codecov
125125
env:
126-
REDIS_HOST: redis
126+
REDIS_HOSTS: redis:6379
127127
NGINX_HOST_80: nginx:40080
128128
NGINX_HOST_443: nginx:40443
129129
NGINX_HOST_WS: nginx:40081

.gitignore

+2
Original file line numberDiff line numberDiff line change
@@ -55,3 +55,5 @@ test/full-setup/certs/*/*.srl
5555
test/full-setup/certs/*/*.csr
5656
test/full-setup/certs/*/*.key
5757
dist/
58+
59+
go-proxy-cache

README.md

+2-1
Original file line numberDiff line numberDiff line change
@@ -171,7 +171,8 @@ server:
171171
redirect_status_code: 301
172172

173173
cache:
174-
host: localhost
174+
hosts:
175+
- localhost:6379
175176

176177
domains:
177178
example_com:

cache/engine/client/client.go

+33-49
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ import (
1313
"context"
1414
"fmt"
1515
"strings"
16+
"sync"
1617
"time"
1718

1819
goredislib "github.com/go-redis/redis/v8"
@@ -31,17 +32,18 @@ var ctx = context.Background()
3132

3233
// RedisClient - Redis Client structure.
3334
type RedisClient struct {
34-
*goredislib.Client
35-
*redsync.Redsync
36-
Name string
37-
Mutex map[string]*redsync.Mutex
38-
logger *log.Logger
35+
Client goredislib.UniversalClient
36+
Redsync *redsync.Redsync
37+
Name string
38+
Mutex map[string]*redsync.Mutex
39+
logger *log.Logger
3940
}
4041

4142
// Connect - Connects to DB.
4243
func Connect(connName string, config config.Cache, logger *log.Logger) *RedisClient {
43-
client := goredislib.NewClient(&goredislib.Options{
44-
Addr: config.Host + ":" + config.Port,
44+
45+
client := goredislib.NewUniversalClient(&goredislib.UniversalOptions{
46+
Addrs: config.Hosts,
4547
Password: config.Password,
4648
DB: config.DB,
4749
})
@@ -105,12 +107,26 @@ func (rdb *RedisClient) unlock(ctx context.Context, key string) error {
105107

106108
// PurgeAll - Purges all the existing keys on a DB.
107109
func (rdb *RedisClient) PurgeAll() (bool, error) {
110+
// multiple redis instances
111+
if rdb.Client.ClusterSlots(ctx).Err() == nil {
112+
clusterClient := rdb.Client.(*goredislib.ClusterClient)
113+
err := clusterClient.ForEachShard(ctx, func(ctx context.Context, client *goredislib.Client) error {
114+
return rdb.purgeAllKeys(client)
115+
})
116+
return err == nil, err
117+
}
118+
119+
// single redis instance
120+
err := rdb.purgeAllKeys(rdb.Client)
121+
return err == nil, err
122+
}
123+
124+
func (rdb *RedisClient) purgeAllKeys(client goredislib.UniversalClient) error {
108125
_, err := circuitbreaker.CB(rdb.Name, rdb.logger).Execute(func() (interface{}, error) {
109-
err := rdb.Client.FlushDB(ctx).Err()
126+
err := client.FlushDB(ctx).Err()
110127
return nil, err
111128
})
112-
113-
return err == nil, err
129+
return err
114130
}
115131

116132
// Ping - Tests the connection.
@@ -167,47 +183,15 @@ func (rdb *RedisClient) Del(ctx context.Context, key string) error {
167183
return err
168184
}
169185

170-
// DelWildcard - Removes the matching keys based on a pattern.
171-
func (rdb *RedisClient) DelWildcard(ctx context.Context, key string) (int, error) {
172-
k, err := circuitbreaker.CB(rdb.Name, rdb.logger).Execute(func() (interface{}, error) {
173-
keys, err := rdb.Client.Keys(ctx, key).Result()
174-
return keys, err
175-
})
176-
177-
if err != nil {
178-
return 0, nil
179-
}
180-
181-
return rdb.deleteKeys(ctx, key, k.([]string))
182-
}
183-
184-
// DelWildcard - Removes the matching keys based on a pattern.
185-
func (rdb *RedisClient) deleteKeys(ctx context.Context, keyID string, keys []string) (int, error) {
186-
l := len(keys)
187-
188-
if l == 0 {
189-
return 0, nil
190-
}
191-
192-
_, errDel := circuitbreaker.CB(rdb.Name, rdb.logger).Execute(rdb.doDeleteKeys(ctx, keyID, keys))
193-
194-
return l, errDel
186+
type Counter struct {
187+
mu sync.Mutex
188+
counter int
195189
}
196190

197-
func (rdb *RedisClient) doDeleteKeys(ctx context.Context, keyID string, keys []string) func() (interface{}, error) {
198-
return func() (interface{}, error) {
199-
if errLock := rdb.lock(ctx, keyID); errLock != nil {
200-
return nil, errLock
201-
}
202-
203-
err := rdb.Client.Del(ctx, keys...).Err()
204-
205-
if errUnlock := rdb.unlock(ctx, keyID); errUnlock != nil {
206-
return nil, errUnlock
207-
}
208-
209-
return nil, err
210-
}
191+
func (c *Counter) increment(num int) {
192+
c.mu.Lock()
193+
defer c.mu.Unlock()
194+
c.counter = c.counter + num
211195
}
212196

213197
// List - Returns the values in a list.

0 commit comments

Comments
 (0)