162 lines
4.0 KiB
Go
162 lines
4.0 KiB
Go
package redisc_test
|
|
|
|
import (
|
|
"fmt"
|
|
"log"
|
|
"time"
|
|
|
|
"github.com/gomodule/redigo/redis"
|
|
"github.com/mna/redisc"
|
|
)
|
|
|
|
// Create and use a cluster.
|
|
func Example() {
|
|
// create the cluster
|
|
cluster := redisc.Cluster{
|
|
StartupNodes: []string{":7000", ":7001", ":7002"},
|
|
DialOptions: []redis.DialOption{redis.DialConnectTimeout(5 * time.Second)},
|
|
CreatePool: createPool,
|
|
}
|
|
defer cluster.Close()
|
|
|
|
// initialize its mapping
|
|
if err := cluster.Refresh(); err != nil {
|
|
log.Fatalf("Refresh failed: %v", err)
|
|
}
|
|
|
|
// grab a connection from the pool
|
|
conn := cluster.Get()
|
|
defer conn.Close()
|
|
|
|
// call commands on it
|
|
s, err := redis.String(conn.Do("GET", "some-key"))
|
|
if err != nil {
|
|
log.Fatalf("GET failed: %v", err)
|
|
}
|
|
log.Println(s)
|
|
|
|
// grab a non-pooled connection
|
|
conn2, err := cluster.Dial()
|
|
if err != nil {
|
|
log.Fatalf("Dial failed: %v", err)
|
|
}
|
|
defer conn2.Close()
|
|
|
|
// make it handle redirections automatically
|
|
rc, err := redisc.RetryConn(conn2, 3, 100*time.Millisecond)
|
|
if err != nil {
|
|
log.Fatalf("RetryConn failed: %v", err)
|
|
}
|
|
|
|
_, err = rc.Do("SET", "some-key", 2)
|
|
if err != nil {
|
|
log.Fatalf("SET failed: %v", err)
|
|
}
|
|
}
|
|
|
|
func createPool(addr string, opts ...redis.DialOption) (*redis.Pool, error) {
|
|
return &redis.Pool{
|
|
MaxIdle: 5,
|
|
MaxActive: 10,
|
|
IdleTimeout: time.Minute,
|
|
Dial: func() (redis.Conn, error) {
|
|
return redis.Dial("tcp", addr, opts...)
|
|
},
|
|
TestOnBorrow: func(c redis.Conn, t time.Time) error {
|
|
_, err := c.Do("PING")
|
|
return err
|
|
},
|
|
}, nil
|
|
}
|
|
|
|
// Execute scripts.
|
|
func ExampleConn() {
|
|
// create the cluster
|
|
cluster := redisc.Cluster{
|
|
StartupNodes: []string{":7000", ":7001", ":7002"},
|
|
DialOptions: []redis.DialOption{redis.DialConnectTimeout(5 * time.Second)},
|
|
CreatePool: createPool,
|
|
}
|
|
defer cluster.Close()
|
|
|
|
// initialize its mapping
|
|
if err := cluster.Refresh(); err != nil {
|
|
log.Fatalf("Refresh failed: %v", err)
|
|
}
|
|
|
|
// create a script that takes 2 keys and 2 values, and returns 1
|
|
var script = redis.NewScript(2, `
|
|
redis.call("SET", KEYS[1], ARGV[1])
|
|
redis.call("SET", KEYS[2], ARGV[2])
|
|
return 1
|
|
`)
|
|
|
|
// get a connection from the cluster
|
|
conn := cluster.Get()
|
|
defer conn.Close()
|
|
|
|
// bind it to the right node for the required keys, ahead of time
|
|
if err := redisc.BindConn(conn, "scr{a}1", "src{a}2"); err != nil {
|
|
log.Fatalf("BindConn failed: %v", err)
|
|
}
|
|
|
|
// script.Do, sends the whole script on first use
|
|
v, err := script.Do(conn, "scr{a}1", "scr{a}2", "x", "y")
|
|
if err != nil {
|
|
log.Fatalf("script.Do failed: %v", err)
|
|
}
|
|
fmt.Println("Do returned ", v)
|
|
|
|
// it is also possible to send only the hash, once it has been
|
|
// loaded on that node
|
|
if err := script.SendHash(conn, "scr{a}1", "scr{a}2", "x", "y"); err != nil {
|
|
log.Fatalf("script.SendHash failed: %v", err)
|
|
}
|
|
if err := conn.Flush(); err != nil {
|
|
log.Fatalf("Flush failed: %v", err)
|
|
}
|
|
|
|
// and receive the script's result
|
|
v, err = conn.Receive()
|
|
if err != nil {
|
|
log.Fatalf("Receive failed: %v", err)
|
|
}
|
|
fmt.Println("Receive returned ", v)
|
|
}
|
|
|
|
// Automatically retry in case of redirection errors.
|
|
func ExampleRetryConn() {
|
|
// create the cluster
|
|
cluster := redisc.Cluster{
|
|
StartupNodes: []string{":7000", ":7001", ":7002"},
|
|
DialOptions: []redis.DialOption{redis.DialConnectTimeout(5 * time.Second)},
|
|
CreatePool: createPool,
|
|
}
|
|
defer cluster.Close()
|
|
|
|
// initialize its mapping
|
|
if err := cluster.Refresh(); err != nil {
|
|
log.Fatalf("Refresh failed: %v", err)
|
|
}
|
|
|
|
// get a connection from the cluster
|
|
conn := cluster.Get()
|
|
defer conn.Close()
|
|
|
|
// create the retry connection - only Do, Close and Err are
|
|
// supported on that connection. It will make up to 3 attempts
|
|
// to get a valid response, and will wait 100ms before a retry
|
|
// in case of a TRYAGAIN redis error.
|
|
retryConn, err := redisc.RetryConn(conn, 3, 100*time.Millisecond)
|
|
if err != nil {
|
|
log.Fatalf("RetryConn failed: %v", err)
|
|
}
|
|
|
|
// call commands
|
|
v, err := retryConn.Do("GET", "key")
|
|
if err != nil {
|
|
log.Fatalf("GET failed: %v", err)
|
|
}
|
|
fmt.Println("GET returned ", v)
|
|
}
|