Repository: go-redis/redis
Pull request #1039 (2019-05-31 10:16:27)

Handle -1 in DurationCmd
Fixes https://github.com/go-redis/redis/issues/1026


Patch:
diff --git a/Makefile b/Makefile
index 0323b37..0358028 100644
--- a/Makefile
+++ b/Makefile
@@ -1,7 +1,7 @@
 all: testdeps
 	go test ./...
 	go test ./... -short -race
-	go test ./... -run=NONE -bench=.
+	go test ./... -run=NONE -bench=. -benchmem
 	env GOOS=linux GOARCH=386 go test ./...
 	go vet
 	go get github.com/gordonklaus/ineffassign
diff --git a/command.go b/command.go
index 6f05895..4223e01 100644
--- a/command.go
+++ b/command.go
@@ -439,7 +439,14 @@ func (cmd *DurationCmd) readReply(rd *proto.Reader) error {
 	if cmd.err != nil {
 		return cmd.err
 	}
-	cmd.val = time.Duration(n) * cmd.precision
+	switch n {
+	// -2 if the key does not exist
+	// -1 if the key exists but has no associated expire
+	case -2, -1:
+		cmd.val = time.Duration(n)
+	default:
+		cmd.val = time.Duration(n) * cmd.precision
+	}
 	return nil
 }
 
@@ -1220,7 +1227,7 @@ func xPendingParser(rd *proto.Reader, n int64) (interface{}, error) {
 //------------------------------------------------------------------------------
 
 type XPendingExt struct {
-	ID         string
+	Id         string
 	Consumer   string
 	Idle       time.Duration
 	RetryCount int64
@@ -1290,7 +1297,7 @@ func xPendingExtSliceParser(rd *proto.Reader, n int64) (interface{}, error) {
 			}
 
 			ret = append(ret, XPendingExt{
-				ID:         id,
+				Id:         id,
 				Consumer:   consumer,
 				Idle:       time.Duration(idle) * time.Millisecond,
 				RetryCount: retryCount,
@@ -1370,7 +1377,7 @@ func zSliceParser(rd *proto.Reader, n int64) (interface{}, error) {
 type ZWithKeyCmd struct {
 	baseCmd
 
-	val *ZWithKey
+	val ZWithKey
 }
 
 var _ Cmder = (*ZWithKeyCmd)(nil)
@@ -1381,11 +1388,11 @@ func NewZWithKeyCmd(args ...interface{}) *ZWithKeyCmd {
 	}
 }
 
-func (cmd *ZWithKeyCmd) Val() *ZWithKey {
+func (cmd *ZWithKeyCmd) Val() ZWithKey {
 	return cmd.val
 }
 
-func (cmd *ZWithKeyCmd) Result() (*ZWithKey, error) {
+func (cmd *ZWithKeyCmd) Result() (ZWithKey, error) {
 	return cmd.Val(), cmd.Err()
 }
 
@@ -1399,7 +1406,7 @@ func (cmd *ZWithKeyCmd) readReply(rd *proto.Reader) error {
 	if cmd.err != nil {
 		return cmd.err
 	}
-	cmd.val = v.(*ZWithKey)
+	cmd.val = v.(ZWithKey)
 	return nil
 }
 
@@ -1424,8 +1431,7 @@ func zWithKeyParser(rd *proto.Reader, n int64) (interface{}, error) {
 	if err != nil {
 		return nil, err
 	}
-
-	return &z, nil
+	return z, nil
 }
 
 //------------------------------------------------------------------------------
@@ -1788,23 +1794,7 @@ func (cmd *GeoPosCmd) readReply(rd *proto.Reader) error {
 func geoPosSliceParser(rd *proto.Reader, n int64) (interface{}, error) {
 	positions := make([]*GeoPos, 0, n)
 	for i := int64(0); i < n; i++ {
-		_, err := rd.ReadReply(func(rd *proto.Reader, n int64) (interface{}, error) {
-			var pos GeoPos
-			var err error
-
-			pos.Longitude, err = rd.ReadFloatReply()
-			if err != nil {
-				return nil, err
-			}
-
-			pos.Latitude, err = rd.ReadFloatReply()
-			if err != nil {
-				return nil, err
-			}
-
-			positions = append(positions, &pos)
-			return nil, nil
-		})
+		v, err := rd.ReadReply(geoPosParser)
 		if err != nil {
 			if err == Nil {
 				positions = append(positions, nil)
@@ -1812,10 +1802,33 @@ func geoPosSliceParser(rd *proto.Reader, n int64) (interface{}, error) {
 			}
 			return nil, err
 		}
+		switch v := v.(type) {
+		case *GeoPos:
+			positions = append(positions, v)
+		default:
+			return nil, fmt.Errorf("got %T, expected *GeoPos", v)
+		}
 	}
 	return positions, nil
 }
 
+func geoPosParser(rd *proto.Reader, n int64) (interface{}, error) {
+	var pos GeoPos
+	var err error
+
+	pos.Longitude, err = rd.ReadFloatReply()
+	if err != nil {
+		return nil, err
+	}
+
+	pos.Latitude, err = rd.ReadFloatReply()
+	if err != nil {
+		return nil, err
+	}
+
+	return &pos, nil
+}
+
 //------------------------------------------------------------------------------
 
 type CommandInfo struct {
diff --git a/commands.go b/commands.go
index ffba8fd..653e4ab 100644
--- a/commands.go
+++ b/commands.go
@@ -67,8 +67,8 @@ type Cmdable interface {
 	Expire(key string, expiration time.Duration) *BoolCmd
 	ExpireAt(key string, tm time.Time) *BoolCmd
 	Keys(pattern string) *StringSliceCmd
-	Migrate(host, port, key string, db int, timeout time.Duration) *StatusCmd
-	Move(key string, db int) *BoolCmd
+	Migrate(host, port, key string, db int64, timeout time.Duration) *StatusCmd
+	Move(key string, db int64) *BoolCmd
 	ObjectRefCount(key string) *IntCmd
 	ObjectEncoding(key string) *StringCmd
 	ObjectIdleTime(key string) *DurationCmd
@@ -189,27 +189,27 @@ type Cmdable interface {
 	XTrimApprox(key string, maxLen int64) *IntCmd
 	BZPopMax(timeout time.Duration, keys ...string) *ZWithKeyCmd
 	BZPopMin(timeout time.Duration, keys ...string) *ZWithKeyCmd
-	ZAdd(key string, members ...*Z) *IntCmd
-	ZAddNX(key string, members ...*Z) *IntCmd
-	ZAddXX(key string, members ...*Z) *IntCmd
-	ZAddCh(key string, members ...*Z) *IntCmd
-	ZAddNXCh(key string, members ...*Z) *IntCmd
-	ZAddXXCh(key string, members ...*Z) *IntCmd
-	ZIncr(key string, member *Z) *FloatCmd
-	ZIncrNX(key string, member *Z) *FloatCmd
-	ZIncrXX(key string, member *Z) *FloatCmd
+	ZAdd(key string, members ...Z) *IntCmd
+	ZAddNX(key string, members ...Z) *IntCmd
+	ZAddXX(key string, members ...Z) *IntCmd
+	ZAddCh(key string, members ...Z) *IntCmd
+	ZAddNXCh(key string, members ...Z) *IntCmd
+	ZAddXXCh(key string, members ...Z) *IntCmd
+	ZIncr(key string, member Z) *FloatCmd
+	ZIncrNX(key string, member Z) *FloatCmd
+	ZIncrXX(key string, member Z) *FloatCmd
 	ZCard(key string) *IntCmd
 	ZCount(key, min, max string) *IntCmd
 	ZLexCount(key, min, max string) *IntCmd
 	ZIncrBy(key string, increment float64, member string) *FloatCmd
-	ZInterStore(destination string, store *ZStore, keys ...string) *IntCmd
+	ZInterStore(destination string, store ZStore, keys ...string) *IntCmd
 	ZPopMax(key string, count ...int64) *ZSliceCmd
 	ZPopMin(key string, count ...int64) *ZSliceCmd
 	ZRange(key string, start, stop int64) *StringSliceCmd
 	ZRangeWithScores(key string, start, stop int64) *ZSliceCmd
-	ZRangeByScore(key string, opt *ZRangeBy) *StringSliceCmd
-	ZRangeByLex(key string, opt *ZRangeBy) *StringSliceCmd
-	ZRangeByScoreWithScores(key string, opt *ZRangeBy) *ZSliceCmd
+	ZRangeByScore(key string, opt ZRangeBy) *StringSliceCmd
+	ZRangeByLex(key string, opt ZRangeBy) *StringSliceCmd
+	ZRangeByScoreWithScores(key string, opt ZRangeBy) *ZSliceCmd
 	ZRank(key, member string) *IntCmd
 	ZRem(key string, members ...interface{}) *IntCmd
 	ZRemRangeByRank(key string, start, stop int64) *IntCmd
@@ -217,12 +217,12 @@ type Cmdable interface {
 	ZRemRangeByLex(key, min, max string) *IntCmd
 	ZRevRange(key string, start, stop int64) *StringSliceCmd
 	ZRevRangeWithScores(key string, start, stop int64) *ZSliceCmd
-	ZRevRangeByScore(key string, opt *ZRangeBy) *StringSliceCmd
-	ZRevRangeByLex(key string, opt *ZRangeBy) *StringSliceCmd
-	ZRevRangeByScoreWithScores(key string, opt *ZRangeBy) *ZSliceCmd
+	ZRevRangeByScore(key string, opt ZRangeBy) *StringSliceCmd
+	ZRevRangeByLex(key string, opt ZRangeBy) *StringSliceCmd
+	ZRevRangeByScoreWithScores(key string, opt ZRangeBy) *ZSliceCmd
 	ZRevRank(key, member string) *IntCmd
 	ZScore(key, member string) *FloatCmd
-	ZUnionStore(dest string, store *ZStore, keys ...string) *IntCmd
+	ZUnionStore(dest string, store ZStore, keys ...string) *IntCmd
 	PFAdd(key string, els ...interface{}) *IntCmd
 	PFCount(keys ...string) *IntCmd
 	PFMerge(dest string, keys ...string) *StatusCmd
@@ -431,7 +431,7 @@ func (c *cmdable) Keys(pattern string) *StringSliceCmd {
 	return cmd
 }
 
-func (c *cmdable) Migrate(host, port, key string, db int, timeout time.Duration) *StatusCmd {
+func (c *cmdable) Migrate(host, port, key string, db int64, timeout time.Duration) *StatusCmd {
 	cmd := NewStatusCmd(
 		"migrate",
 		host,
@@ -445,7 +445,7 @@ func (c *cmdable) Migrate(host, port, key string, db int, timeout time.Duration)
 	return cmd
 }
 
-func (c *cmdable) Move(key string, db int) *BoolCmd {
+func (c *cmdable) Move(key string, db int64) *BoolCmd {
 	cmd := NewBoolCmd("move", key, db)
 	c.process(cmd)
 	return cmd
@@ -1453,10 +1453,11 @@ func (c *cmdable) XGroupDelConsumer(stream, group, consumer string) *IntCmd {
 type XReadGroupArgs struct {
 	Group    string
 	Consumer string
-	Streams  []string // list of streams and ids, e.g. stream1 stream2 id1 id2
-	Count    int64
-	Block    time.Duration
-	NoAck    bool
+	// List of streams and ids.
+	Streams []string
+	Count   int64
+	Block   time.Duration
+	NoAck   bool
 }
 
 func (c *cmdable) XReadGroup(a *XReadGroupArgs) *XStreamSliceCmd {
@@ -1617,7 +1618,7 @@ func (c *cmdable) BZPopMin(timeout time.Duration, keys ...string) *ZWithKeyCmd {
 	return cmd
 }
 
-func (c *cmdable) zAdd(a []interface{}, n int, members ...*Z) *IntCmd {
+func (c *cmdable) zAdd(a []interface{}, n int, members ...Z) *IntCmd {
 	for i, m := range members {
 		a[n+2*i] = m.Score
 		a[n+2*i+1] = m.Member
@@ -1628,7 +1629,7 @@ func (c *cmdable) zAdd(a []interface{}, n int, members ...*Z) *IntCmd {
 }
 
 // Redis `ZADD key score member [score member ...]` command.
-func (c *cmdable) ZAdd(key string, members ...*Z) *IntCmd {
+func (c *cmdable) ZAdd(key string, members ...Z) *IntCmd {
 	const n = 2
 	a := make([]interface{}, n+2*len(members))
 	a[0], a[1] = "zadd", key
@@ -1636,7 +1637,7 @@ func (c *cmdable) ZAdd(key string, members ...*Z) *IntCmd {
 }
 
 // Redis `ZADD key NX score member [score member ...]` command.
-func (c *cmdable) ZAddNX(key string, members ...*Z) *IntCmd {
+func (c *cmdable) ZAddNX(key string, members ...Z) *IntCmd {
 	const n = 3
 	a := make([]interface{}, n+2*len(members))
 	a[0], a[1], a[2] = "zadd", key, "nx"
@@ -1644,7 +1645,7 @@ func (c *cmdable) ZAddNX(key string, members ...*Z) *IntCmd {
 }
 
 // Redis `ZADD key XX score member [score member ...]` command.
-func (c *cmdable) ZAddXX(key string, members ...*Z) *IntCmd {
+func (c *cmdable) ZAddXX(key string, members ...Z) *IntCmd {
 	const n = 3
 	a := make([]interface{}, n+2*len(members))
 	a[0], a[1], a[2] = "zadd", key, "xx"
@@ -1652,7 +1653,7 @@ func (c *cmdable) ZAddXX(key string, members ...*Z) *IntCmd {
 }
 
 // Redis `ZADD key CH score member [score member ...]` command.
-func (c *cmdable) ZAddCh(key string, members ...*Z) *IntCmd {
+func (c *cmdable) ZAddCh(key string, members ...Z) *IntCmd {
 	const n = 3
 	a := make([]interface{}, n+2*len(members))
 	a[0], a[1], a[2] = "zadd", key, "ch"
@@ -1660,7 +1661,7 @@ func (c *cmdable) ZAddCh(key string, members ...*Z) *IntCmd {
 }
 
 // Redis `ZADD key NX CH score member [score member ...]` command.
-func (c *cmdable) ZAddNXCh(key string, members ...*Z) *IntCmd {
+func (c *cmdable) ZAddNXCh(key string, members ...Z) *IntCmd {
 	const n = 4
 	a := make([]interface{}, n+2*len(members))
 	a[0], a[1], a[2], a[3] = "zadd", key, "nx", "ch"
@@ -1668,14 +1669,14 @@ func (c *cmdable) ZAddNXCh(key string, members ...*Z) *IntCmd {
 }
 
 // Redis `ZADD key XX CH score member [score member ...]` command.
-func (c *cmdable) ZAddXXCh(key string, members ...*Z) *IntCmd {
+func (c *cmdable) ZAddXXCh(key string, members ...Z) *IntCmd {
 	const n = 4
 	a := make([]interface{}, n+2*len(members))
 	a[0], a[1], a[2], a[3] = "zadd", key, "xx", "ch"
 	return c.zAdd(a, n, members...)
 }
 
-func (c *cmdable) zIncr(a []interface{}, n int, members ...*Z) *FloatCmd {
+func (c *cmdable) zIncr(a []interface{}, n int, members ...Z) *FloatCmd {
 	for i, m := range members {
 		a[n+2*i] = m.Score
 		a[n+2*i+1] = m.Member
@@ -1686,7 +1687,7 @@ func (c *cmdable) zIncr(a []interface{}, n int, members ...*Z) *FloatCmd {
 }
 
 // Redis `ZADD key INCR score member` command.
-func (c *cmdable) ZIncr(key string, member *Z) *FloatCmd {
+func (c *cmdable) ZIncr(key string, member Z) *FloatCmd {
 	const n = 3
 	a := make([]interface{}, n+2)
 	a[0], a[1], a[2] = "zadd", key, "incr"
@@ -1694,7 +1695,7 @@ func (c *cmdable) ZIncr(key string, member *Z) *FloatCmd {
 }
 
 // Redis `ZADD key NX INCR score member` command.
-func (c *cmdable) ZIncrNX(key string, member *Z) *FloatCmd {
+func (c *cmdable) ZIncrNX(key string, member Z) *FloatCmd {
 	const n = 4
 	a := make([]interface{}, n+2)
 	a[0], a[1], a[2], a[3] = "zadd", key, "incr", "nx"
@@ -1702,7 +1703,7 @@ func (c *cmdable) ZIncrNX(key string, member *Z) *FloatCmd {
 }
 
 // Redis `ZADD key XX INCR score member` command.
-func (c *cmdable) ZIncrXX(key string, member *Z) *FloatCmd {
+func (c *cmdable) ZIncrXX(key string, member Z) *FloatCmd {
 	const n = 4
 	a := make([]interface{}, n+2)
 	a[0], a[1], a[2], a[3] = "zadd", key, "incr", "xx"
@@ -1733,7 +1734,7 @@ func (c *cmdable) ZIncrBy(key string, increment float64, member string) *FloatCm
 	return cmd
 }
 
-func (c *cmdable) ZInterStore(destination string, store *ZStore, keys ...string) *IntCmd {
+func (c *cmdable) ZInterStore(destination string, store ZStore, keys ...string) *IntCmd {
 	args := make([]interface{}, 3+len(keys))
 	args[0] = "zinterstore"
 	args[1] = destination
@@ -1825,7 +1826,7 @@ type ZRangeBy struct {
 	Offset, Count int64
 }
 
-func (c *cmdable) zRangeBy(zcmd, key string, opt *ZRangeBy, withScores bool) *StringSliceCmd {
+func (c *cmdable) zRangeBy(zcmd, key string, opt ZRangeBy, withScores bool) *StringSliceCmd {
 	args := []interface{}{zcmd, key, opt.Min, opt.Max}
 	if withScores {
 		args = append(args, "withscores")
@@ -1843,15 +1844,15 @@ func (c *cmdable) zRangeBy(zcmd, key string, opt *ZRangeBy, withScores bool) *St
 	return cmd
 }
 
-func (c *cmdable) ZRangeByScore(key string, opt *ZRangeBy) *StringSliceCmd {
+func (c *cmdable) ZRangeByScore(key string, opt ZRangeBy) *StringSliceCmd {
 	return c.zRangeBy("zrangebyscore", key, opt, false)
 }
 
-func (c *cmdable) ZRangeByLex(key string, opt *ZRangeBy) *StringSliceCmd {
+func (c *cmdable) ZRangeByLex(key string, opt ZRangeBy) *StringSliceCmd {
 	return c.zRangeBy("zrangebylex", key, opt, false)
 }
 
-func (c *cmdable) ZRangeByScoreWithScores(key string, opt *ZRangeBy) *ZSliceCmd {
+func (c *cmdable) ZRangeByScoreWithScores(key string, opt ZRangeBy) *ZSliceCmd {
 	args := []interface{}{"zrangebyscore", key, opt.Min, opt.Max, "withscores"}
 	if opt.Offset != 0 || opt.Count != 0 {
 		args = append(
@@ -1917,7 +1918,7 @@ func (c *cmdable) ZRevRangeWithScores(key string, start, stop int64) *ZSliceCmd
 	return cmd
 }
 
-func (c *cmdable) zRevRangeBy(zcmd, key string, opt *ZRangeBy) *StringSliceCmd {
+func (c *cmdable) zRevRangeBy(zcmd, key string, opt ZRangeBy) *StringSliceCmd {
 	args := []interface{}{zcmd, key, opt.Max, opt.Min}
 	if opt.Offset != 0 || opt.Count != 0 {
 		args = append(
@@ -1932,15 +1933,15 @@ func (c *cmdable) zRevRangeBy(zcmd, key string, opt *ZRangeBy) *StringSliceCmd {
 	return cmd
 }
 
-func (c *cmdable) ZRevRangeByScore(key string, opt *ZRangeBy) *StringSliceCmd {
+func (c *cmdable) ZRevRangeByScore(key string, opt ZRangeBy) *StringSliceCmd {
 	return c.zRevRangeBy("zrevrangebyscore", key, opt)
 }
 
-func (c *cmdable) ZRevRangeByLex(key string, opt *ZRangeBy) *StringSliceCmd {
+func (c *cmdable) ZRevRangeByLex(key string, opt ZRangeBy) *StringSliceCmd {
 	return c.zRevRangeBy("zrevrangebylex", key, opt)
 }
 
-func (c *cmdable) ZRevRangeByScoreWithScores(key string, opt *ZRangeBy) *ZSliceCmd {
+func (c *cmdable) ZRevRangeByScoreWithScores(key string, opt ZRangeBy) *ZSliceCmd {
 	args := []interface{}{"zrevrangebyscore", key, opt.Max, opt.Min, "withscores"}
 	if opt.Offset != 0 || opt.Count != 0 {
 		args = append(
@@ -1967,8 +1968,7 @@ func (c *cmdable) ZScore(key, member string) *FloatCmd {
 	return cmd
 }
 
-// TODO: move keys to ZStore?
-func (c *cmdable) ZUnionStore(dest string, store *ZStore, keys ...string) *IntCmd {
+func (c *cmdable) ZUnionStore(dest string, store ZStore, keys ...string) *IntCmd {
 	args := make([]interface{}, 3+len(keys))
 	args[0] = "zunionstore"
 	args[1] = dest


Test patch:
diff --git a/bench_test.go b/bench_test.go
index 3af2e24..933f5cb 100644
--- a/bench_test.go
+++ b/bench_test.go
@@ -188,7 +188,7 @@ func BenchmarkZAdd(b *testing.B) {
 
 	b.RunParallel(func(pb *testing.PB) {
 		for pb.Next() {
-			err := client.ZAdd("key", &redis.Z{
+			err := client.ZAdd("key", redis.Z{
 				Score:  float64(1),
 				Member: "hello",
 			}).Err()
diff --git a/commands_test.go b/commands_test.go
index b8d7fd2..5f363df 100644
--- a/commands_test.go
+++ b/commands_test.go
@@ -374,7 +374,11 @@ var _ = Describe("Commands", func() {
 
 			ttl = client.TTL("key")
 			Expect(ttl.Err()).NotTo(HaveOccurred())
-			Expect(ttl.Val() < 0).To(Equal(true))
+			Expect(ttl.Val()).To(Equal(time.Duration(-1)))
+
+			ttl = client.TTL("nonexistent_key")
+			Expect(ttl.Err()).NotTo(HaveOccurred())
+			Expect(ttl.Val()).To(Equal(time.Duration(-2)))
 		})
 
 		It("should ExpireAt", func() {
@@ -796,7 +800,7 @@ var _ = Describe("Commands", func() {
 
 		It("should ZScan", func() {
 			for i := 0; i < 1000; i++ {
-				err := client.ZAdd("myset", &redis.Z{
+				err := client.ZAdd("myset", redis.Z{
 					Score:  float64(i),
 					Member: fmt.Sprintf("member%d", i),
 				}).Err()
@@ -2139,17 +2143,17 @@ var _ = Describe("Commands", func() {
 	Describe("sorted sets", func() {
 
 		It("should BZPopMax", func() {
-			err := client.ZAdd("zset1", &redis.Z{
+			err := client.ZAdd("zset1", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset1", &redis.Z{
+			err = client.ZAdd("zset1", redis.Z{
 				Score:  2,
 				Member: "two",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset1", &redis.Z{
+			err = client.ZAdd("zset1", redis.Z{
 				Score:  3,
 				Member: "three",
 			}).Err()
@@ -2157,7 +2161,7 @@ var _ = Describe("Commands", func() {
 
 			member, err := client.BZPopMax(0, "zset1", "zset2").Result()
 			Expect(err).NotTo(HaveOccurred())
-			Expect(member).To(Equal(&redis.ZWithKey{
+			Expect(member).To(Equal(redis.ZWithKey{
 				Z: redis.Z{
 					Score:  3,
 					Member: "three",
@@ -2175,7 +2179,7 @@ var _ = Describe("Commands", func() {
 				started <- true
 				bZPopMax := client.BZPopMax(0, "zset")
 				Expect(bZPopMax.Err()).NotTo(HaveOccurred())
-				Expect(bZPopMax.Val()).To(Equal(&redis.ZWithKey{
+				Expect(bZPopMax.Val()).To(Equal(redis.ZWithKey{
 					Z: redis.Z{
 						Member: "a",
 						Score:  1,
@@ -2193,7 +2197,7 @@ var _ = Describe("Commands", func() {
 				// ok
 			}
 
-			zAdd := client.ZAdd("zset", &redis.Z{
+			zAdd := client.ZAdd("zset", redis.Z{
 				Member: "a",
 				Score:  1,
 			})
@@ -2210,7 +2214,7 @@ var _ = Describe("Commands", func() {
 		It("should BZPopMax timeout", func() {
 			val, err := client.BZPopMax(time.Second, "zset1").Result()
 			Expect(err).To(Equal(redis.Nil))
-			Expect(val).To(BeNil())
+			Expect(val).To(Equal(redis.ZWithKey{}))
 
 			Expect(client.Ping().Err()).NotTo(HaveOccurred())
 
@@ -2221,17 +2225,17 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should BZPopMin", func() {
-			err := client.ZAdd("zset1", &redis.Z{
+			err := client.ZAdd("zset1", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset1", &redis.Z{
+			err = client.ZAdd("zset1", redis.Z{
 				Score:  2,
 				Member: "two",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset1", &redis.Z{
+			err = client.ZAdd("zset1", redis.Z{
 				Score:  3,
 				Member: "three",
 			}).Err()
@@ -2239,7 +2243,7 @@ var _ = Describe("Commands", func() {
 
 			member, err := client.BZPopMin(0, "zset1", "zset2").Result()
 			Expect(err).NotTo(HaveOccurred())
-			Expect(member).To(Equal(&redis.ZWithKey{
+			Expect(member).To(Equal(redis.ZWithKey{
 				Z: redis.Z{
 					Score:  1,
 					Member: "one",
@@ -2257,7 +2261,7 @@ var _ = Describe("Commands", func() {
 				started <- true
 				bZPopMin := client.BZPopMin(0, "zset")
 				Expect(bZPopMin.Err()).NotTo(HaveOccurred())
-				Expect(bZPopMin.Val()).To(Equal(&redis.ZWithKey{
+				Expect(bZPopMin.Val()).To(Equal(redis.ZWithKey{
 					Z: redis.Z{
 						Member: "a",
 						Score:  1,
@@ -2275,7 +2279,7 @@ var _ = Describe("Commands", func() {
 				// ok
 			}
 
-			zAdd := client.ZAdd("zset", &redis.Z{
+			zAdd := client.ZAdd("zset", redis.Z{
 				Member: "a",
 				Score:  1,
 			})
@@ -2292,7 +2296,7 @@ var _ = Describe("Commands", func() {
 		It("should BZPopMin timeout", func() {
 			val, err := client.BZPopMin(time.Second, "zset1").Result()
 			Expect(err).To(Equal(redis.Nil))
-			Expect(val).To(BeNil())
+			Expect(val).To(Equal(redis.ZWithKey{}))
 
 			Expect(client.Ping().Err()).NotTo(HaveOccurred())
 
@@ -2303,28 +2307,28 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZAdd", func() {
-			added, err := client.ZAdd("zset", &redis.Z{
+			added, err := client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(added).To(Equal(int64(1)))
 
-			added, err = client.ZAdd("zset", &redis.Z{
+			added, err = client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: "uno",
 			}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(added).To(Equal(int64(1)))
 
-			added, err = client.ZAdd("zset", &redis.Z{
+			added, err = client.ZAdd("zset", redis.Z{
 				Score:  2,
 				Member: "two",
 			}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(added).To(Equal(int64(1)))
 
-			added, err = client.ZAdd("zset", &redis.Z{
+			added, err = client.ZAdd("zset", redis.Z{
 				Score:  3,
 				Member: "two",
 			}).Result()
@@ -2346,28 +2350,28 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZAdd bytes", func() {
-			added, err := client.ZAdd("zset", &redis.Z{
+			added, err := client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: []byte("one"),
 			}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(added).To(Equal(int64(1)))
 
-			added, err = client.ZAdd("zset", &redis.Z{
+			added, err = client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: []byte("uno"),
 			}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(added).To(Equal(int64(1)))
 
-			added, err = client.ZAdd("zset", &redis.Z{
+			added, err = client.ZAdd("zset", redis.Z{
 				Score:  2,
 				Member: []byte("two"),
 			}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(added).To(Equal(int64(1)))
 
-			added, err = client.ZAdd("zset", &redis.Z{
+			added, err = client.ZAdd("zset", redis.Z{
 				Score:  3,
 				Member: []byte("two"),
 			}).Result()
@@ -2389,7 +2393,7 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZAddNX", func() {
-			added, err := client.ZAddNX("zset", &redis.Z{
+			added, err := client.ZAddNX("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
@@ -2400,7 +2404,7 @@ var _ = Describe("Commands", func() {
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]redis.Z{{Score: 1, Member: "one"}}))
 
-			added, err = client.ZAddNX("zset", &redis.Z{
+			added, err = client.ZAddNX("zset", redis.Z{
 				Score:  2,
 				Member: "one",
 			}).Result()
@@ -2413,7 +2417,7 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZAddXX", func() {
-			added, err := client.ZAddXX("zset", &redis.Z{
+			added, err := client.ZAddXX("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
@@ -2424,14 +2428,14 @@ var _ = Describe("Commands", func() {
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(BeEmpty())
 
-			added, err = client.ZAdd("zset", &redis.Z{
+			added, err = client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(added).To(Equal(int64(1)))
 
-			added, err = client.ZAddXX("zset", &redis.Z{
+			added, err = client.ZAddXX("zset", redis.Z{
 				Score:  2,
 				Member: "one",
 			}).Result()
@@ -2444,14 +2448,14 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZAddCh", func() {
-			changed, err := client.ZAddCh("zset", &redis.Z{
+			changed, err := client.ZAddCh("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(changed).To(Equal(int64(1)))
 
-			changed, err = client.ZAddCh("zset", &redis.Z{
+			changed, err = client.ZAddCh("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
@@ -2460,7 +2464,7 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZAddNXCh", func() {
-			changed, err := client.ZAddNXCh("zset", &redis.Z{
+			changed, err := client.ZAddNXCh("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
@@ -2471,7 +2475,7 @@ var _ = Describe("Commands", func() {
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]redis.Z{{Score: 1, Member: "one"}}))
 
-			changed, err = client.ZAddNXCh("zset", &redis.Z{
+			changed, err = client.ZAddNXCh("zset", redis.Z{
 				Score:  2,
 				Member: "one",
 			}).Result()
@@ -2487,7 +2491,7 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZAddXXCh", func() {
-			changed, err := client.ZAddXXCh("zset", &redis.Z{
+			changed, err := client.ZAddXXCh("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
@@ -2498,14 +2502,14 @@ var _ = Describe("Commands", func() {
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(BeEmpty())
 
-			added, err := client.ZAdd("zset", &redis.Z{
+			added, err := client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(added).To(Equal(int64(1)))
 
-			changed, err = client.ZAddXXCh("zset", &redis.Z{
+			changed, err = client.ZAddXXCh("zset", redis.Z{
 				Score:  2,
 				Member: "one",
 			}).Result()
@@ -2518,7 +2522,7 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZIncr", func() {
-			score, err := client.ZIncr("zset", &redis.Z{
+			score, err := client.ZIncr("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
@@ -2529,7 +2533,7 @@ var _ = Describe("Commands", func() {
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]redis.Z{{Score: 1, Member: "one"}}))
 
-			score, err = client.ZIncr("zset", &redis.Z{Score: 1, Member: "one"}).Result()
+			score, err = client.ZIncr("zset", redis.Z{Score: 1, Member: "one"}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(score).To(Equal(float64(2)))
 
@@ -2539,7 +2543,7 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZIncrNX", func() {
-			score, err := client.ZIncrNX("zset", &redis.Z{
+			score, err := client.ZIncrNX("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
@@ -2550,7 +2554,7 @@ var _ = Describe("Commands", func() {
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]redis.Z{{Score: 1, Member: "one"}}))
 
-			score, err = client.ZIncrNX("zset", &redis.Z{
+			score, err = client.ZIncrNX("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
@@ -2563,7 +2567,7 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZIncrXX", func() {
-			score, err := client.ZIncrXX("zset", &redis.Z{
+			score, err := client.ZIncrXX("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
@@ -2574,14 +2578,14 @@ var _ = Describe("Commands", func() {
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(BeEmpty())
 
-			added, err := client.ZAdd("zset", &redis.Z{
+			added, err := client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(added).To(Equal(int64(1)))
 
-			score, err = client.ZIncrXX("zset", &redis.Z{
+			score, err = client.ZIncrXX("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Result()
@@ -2594,12 +2598,12 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZCard", func() {
-			err := client.ZAdd("zset", &redis.Z{
+			err := client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  2,
 				Member: "two",
 			}).Err()
@@ -2611,17 +2615,17 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZCount", func() {
-			err := client.ZAdd("zset", &redis.Z{
+			err := client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  2,
 				Member: "two",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  3,
 				Member: "three",
 			}).Err()
@@ -2641,12 +2645,12 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZIncrBy", func() {
-			err := client.ZAdd("zset", &redis.Z{
+			err := client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  2,
 				Member: "two",
 			}).Err()
@@ -2668,26 +2672,26 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZInterStore", func() {
-			err := client.ZAdd("zset1", &redis.Z{
+			err := client.ZAdd("zset1", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset1", &redis.Z{
+			err = client.ZAdd("zset1", redis.Z{
 				Score:  2,
 				Member: "two",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
-			err = client.ZAdd("zset2", &redis.Z{Score: 1, Member: "one"}).Err()
+			err = client.ZAdd("zset2", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset2", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset2", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset3", &redis.Z{Score: 3, Member: "two"}).Err()
+			err = client.ZAdd("zset3", redis.Z{Score: 3, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			zInterStore := client.ZInterStore(
-				"out", &redis.ZStore{Weights: []float64{2, 3}}, "zset1", "zset2")
+				"out", redis.ZStore{Weights: []float64{2, 3}}, "zset1", "zset2")
 			Expect(zInterStore.Err()).NotTo(HaveOccurred())
 			Expect(zInterStore.Val()).To(Equal(int64(2)))
 
@@ -2703,17 +2707,17 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZPopMax", func() {
-			err := client.ZAdd("zset", &redis.Z{
+			err := client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  2,
 				Member: "two",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  3,
 				Member: "three",
 			}).Err()
@@ -2727,7 +2731,7 @@ var _ = Describe("Commands", func() {
 			}}))
 
 			// adding back 3
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  3,
 				Member: "three",
 			}).Err()
@@ -2743,12 +2747,12 @@ var _ = Describe("Commands", func() {
 			}}))
 
 			// adding back 2 & 3
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  3,
 				Member: "three",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  2,
 				Member: "two",
 			}).Err()
@@ -2768,17 +2772,17 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZPopMin", func() {
-			err := client.ZAdd("zset", &redis.Z{
+			err := client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  2,
 				Member: "two",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  3,
 				Member: "three",
 			}).Err()
@@ -2792,7 +2796,7 @@ var _ = Describe("Commands", func() {
 			}}))
 
 			// adding back 1
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Err()
@@ -2808,13 +2812,13 @@ var _ = Describe("Commands", func() {
 			}}))
 
 			// adding back 1 & 2
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  1,
 				Member: "one",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  2,
 				Member: "two",
 			}).Err()
@@ -2835,11 +2839,11 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRange", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			zRange := client.ZRange("zset", 0, -1)
@@ -2856,11 +2860,11 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRangeWithScores", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			vals, err := client.ZRangeWithScores("zset", 0, -1).Result()
@@ -2892,35 +2896,35 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRangeByScore", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
-			zRangeByScore := client.ZRangeByScore("zset", &redis.ZRangeBy{
+			zRangeByScore := client.ZRangeByScore("zset", redis.ZRangeBy{
 				Min: "-inf",
 				Max: "+inf",
 			})
 			Expect(zRangeByScore.Err()).NotTo(HaveOccurred())
 			Expect(zRangeByScore.Val()).To(Equal([]string{"one", "two", "three"}))
 
-			zRangeByScore = client.ZRangeByScore("zset", &redis.ZRangeBy{
+			zRangeByScore = client.ZRangeByScore("zset", redis.ZRangeBy{
 				Min: "1",
 				Max: "2",
 			})
 			Expect(zRangeByScore.Err()).NotTo(HaveOccurred())
 			Expect(zRangeByScore.Val()).To(Equal([]string{"one", "two"}))
 
-			zRangeByScore = client.ZRangeByScore("zset", &redis.ZRangeBy{
+			zRangeByScore = client.ZRangeByScore("zset", redis.ZRangeBy{
 				Min: "(1",
 				Max: "2",
 			})
 			Expect(zRangeByScore.Err()).NotTo(HaveOccurred())
 			Expect(zRangeByScore.Val()).To(Equal([]string{"two"}))
 
-			zRangeByScore = client.ZRangeByScore("zset", &redis.ZRangeBy{
+			zRangeByScore = client.ZRangeByScore("zset", redis.ZRangeBy{
 				Min: "(1",
 				Max: "(2",
 			})
@@ -2929,44 +2933,44 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRangeByLex", func() {
-			err := client.ZAdd("zset", &redis.Z{
+			err := client.ZAdd("zset", redis.Z{
 				Score:  0,
 				Member: "a",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  0,
 				Member: "b",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{
+			err = client.ZAdd("zset", redis.Z{
 				Score:  0,
 				Member: "c",
 			}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
-			zRangeByLex := client.ZRangeByLex("zset", &redis.ZRangeBy{
+			zRangeByLex := client.ZRangeByLex("zset", redis.ZRangeBy{
 				Min: "-",
 				Max: "+",
 			})
 			Expect(zRangeByLex.Err()).NotTo(HaveOccurred())
 			Expect(zRangeByLex.Val()).To(Equal([]string{"a", "b", "c"}))
 
-			zRangeByLex = client.ZRangeByLex("zset", &redis.ZRangeBy{
+			zRangeByLex = client.ZRangeByLex("zset", redis.ZRangeBy{
 				Min: "[a",
 				Max: "[b",
 			})
 			Expect(zRangeByLex.Err()).NotTo(HaveOccurred())
 			Expect(zRangeByLex.Val()).To(Equal([]string{"a", "b"}))
 
-			zRangeByLex = client.ZRangeByLex("zset", &redis.ZRangeBy{
+			zRangeByLex = client.ZRangeByLex("zset", redis.ZRangeBy{
 				Min: "(a",
 				Max: "[b",
 			})
 			Expect(zRangeByLex.Err()).NotTo(HaveOccurred())
 			Expect(zRangeByLex.Val()).To(Equal([]string{"b"}))
 
-			zRangeByLex = client.ZRangeByLex("zset", &redis.ZRangeBy{
+			zRangeByLex = client.ZRangeByLex("zset", redis.ZRangeBy{
 				Min: "(a",
 				Max: "(b",
 			})
@@ -2975,14 +2979,14 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRangeByScoreWithScoresMap", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
-			vals, err := client.ZRangeByScoreWithScores("zset", &redis.ZRangeBy{
+			vals, err := client.ZRangeByScoreWithScores("zset", redis.ZRangeBy{
 				Min: "-inf",
 				Max: "+inf",
 			}).Result()
@@ -2998,7 +3002,7 @@ var _ = Describe("Commands", func() {
 				Member: "three",
 			}}))
 
-			vals, err = client.ZRangeByScoreWithScores("zset", &redis.ZRangeBy{
+			vals, err = client.ZRangeByScoreWithScores("zset", redis.ZRangeBy{
 				Min: "1",
 				Max: "2",
 			}).Result()
@@ -3011,14 +3015,14 @@ var _ = Describe("Commands", func() {
 				Member: "two",
 			}}))
 
-			vals, err = client.ZRangeByScoreWithScores("zset", &redis.ZRangeBy{
+			vals, err = client.ZRangeByScoreWithScores("zset", redis.ZRangeBy{
 				Min: "(1",
 				Max: "2",
 			}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]redis.Z{{Score: 2, Member: "two"}}))
 
-			vals, err = client.ZRangeByScoreWithScores("zset", &redis.ZRangeBy{
+			vals, err = client.ZRangeByScoreWithScores("zset", redis.ZRangeBy{
 				Min: "(1",
 				Max: "(2",
 			}).Result()
@@ -3027,11 +3031,11 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRank", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			zRank := client.ZRank("zset", "three")
@@ -3044,11 +3048,11 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRem", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			zRem := client.ZRem("zset", "two")
@@ -3067,11 +3071,11 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRemRangeByRank", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			zRemRangeByRank := client.ZRemRangeByRank("zset", 0, 1)
@@ -3087,11 +3091,11 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRemRangeByScore", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			zRemRangeByScore := client.ZRemRangeByScore("zset", "-inf", "(2")
@@ -3110,7 +3114,7 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRemRangeByLex", func() {
-			zz := []*redis.Z{
+			zz := []redis.Z{
 				{Score: 0, Member: "aaaa"},
 				{Score: 0, Member: "b"},
 				{Score: 0, Member: "c"},
@@ -3137,11 +3141,11 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRevRange", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			zRevRange := client.ZRevRange("zset", 0, -1)
@@ -3158,11 +3162,11 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRevRangeWithScoresMap", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			val, err := client.ZRevRangeWithScores("zset", 0, -1).Result()
@@ -3194,63 +3198,63 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRevRangeByScore", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			vals, err := client.ZRevRangeByScore(
-				"zset", &redis.ZRangeBy{Max: "+inf", Min: "-inf"}).Result()
+				"zset", redis.ZRangeBy{Max: "+inf", Min: "-inf"}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]string{"three", "two", "one"}))
 
 			vals, err = client.ZRevRangeByScore(
-				"zset", &redis.ZRangeBy{Max: "2", Min: "(1"}).Result()
+				"zset", redis.ZRangeBy{Max: "2", Min: "(1"}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]string{"two"}))
 
 			vals, err = client.ZRevRangeByScore(
-				"zset", &redis.ZRangeBy{Max: "(2", Min: "(1"}).Result()
+				"zset", redis.ZRangeBy{Max: "(2", Min: "(1"}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]string{}))
 		})
 
 		It("should ZRevRangeByLex", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 0, Member: "a"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 0, Member: "a"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 0, Member: "b"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 0, Member: "b"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 0, Member: "c"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 0, Member: "c"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			vals, err := client.ZRevRangeByLex(
-				"zset", &redis.ZRangeBy{Max: "+", Min: "-"}).Result()
+				"zset", redis.ZRangeBy{Max: "+", Min: "-"}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]string{"c", "b", "a"}))
 
 			vals, err = client.ZRevRangeByLex(
-				"zset", &redis.ZRangeBy{Max: "[b", Min: "(a"}).Result()
+				"zset", redis.ZRangeBy{Max: "[b", Min: "(a"}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]string{"b"}))
 
 			vals, err = client.ZRevRangeByLex(
-				"zset", &redis.ZRangeBy{Max: "(b", Min: "(a"}).Result()
+				"zset", redis.ZRangeBy{Max: "(b", Min: "(a"}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]string{}))
 		})
 
 		It("should ZRevRangeByScoreWithScores", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			vals, err := client.ZRevRangeByScoreWithScores(
-				"zset", &redis.ZRangeBy{Max: "+inf", Min: "-inf"}).Result()
+				"zset", redis.ZRangeBy{Max: "+inf", Min: "-inf"}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]redis.Z{{
 				Score:  3,
@@ -3265,15 +3269,15 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZRevRangeByScoreWithScoresMap", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			vals, err := client.ZRevRangeByScoreWithScores(
-				"zset", &redis.ZRangeBy{Max: "+inf", Min: "-inf"}).Result()
+				"zset", redis.ZRangeBy{Max: "+inf", Min: "-inf"}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]redis.Z{{
 				Score:  3,
@@ -3287,22 +3291,22 @@ var _ = Describe("Commands", func() {
 			}}))
 
 			vals, err = client.ZRevRangeByScoreWithScores(
-				"zset", &redis.ZRangeBy{Max: "2", Min: "(1"}).Result()
+				"zset", redis.ZRangeBy{Max: "2", Min: "(1"}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]redis.Z{{Score: 2, Member: "two"}}))
 
 			vals, err = client.ZRevRangeByScoreWithScores(
-				"zset", &redis.ZRangeBy{Max: "(2", Min: "(1"}).Result()
+				"zset", redis.ZRangeBy{Max: "(2", Min: "(1"}).Result()
 			Expect(err).NotTo(HaveOccurred())
 			Expect(vals).To(Equal([]redis.Z{}))
 		})
 
 		It("should ZRevRank", func() {
-			err := client.ZAdd("zset", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			zRevRank := client.ZRevRank("zset", "one")
@@ -3315,7 +3319,7 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZScore", func() {
-			zAdd := client.ZAdd("zset", &redis.Z{Score: 1.001, Member: "one"})
+			zAdd := client.ZAdd("zset", redis.Z{Score: 1.001, Member: "one"})
 			Expect(zAdd.Err()).NotTo(HaveOccurred())
 
 			zScore := client.ZScore("zset", "one")
@@ -3324,20 +3328,20 @@ var _ = Describe("Commands", func() {
 		})
 
 		It("should ZUnionStore", func() {
-			err := client.ZAdd("zset1", &redis.Z{Score: 1, Member: "one"}).Err()
+			err := client.ZAdd("zset1", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset1", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset1", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
-			err = client.ZAdd("zset2", &redis.Z{Score: 1, Member: "one"}).Err()
+			err = client.ZAdd("zset2", redis.Z{Score: 1, Member: "one"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset2", &redis.Z{Score: 2, Member: "two"}).Err()
+			err = client.ZAdd("zset2", redis.Z{Score: 2, Member: "two"}).Err()
 			Expect(err).NotTo(HaveOccurred())
-			err = client.ZAdd("zset2", &redis.Z{Score: 3, Member: "three"}).Err()
+			err = client.ZAdd("zset2", redis.Z{Score: 3, Member: "three"}).Err()
 			Expect(err).NotTo(HaveOccurred())
 
 			zUnionStore := client.ZUnionStore(
-				"out", &redis.ZStore{Weights: []float64{2, 3}}, "zset1", "zset2")
+				"out", redis.ZStore{Weights: []float64{2, 3}}, "zset1", "zset2")
 			Expect(zUnionStore.Err()).NotTo(HaveOccurred())
 			Expect(zUnionStore.Val()).To(Equal(int64(3)))
 
@@ -3622,9 +3626,9 @@ var _ = Describe("Commands", func() {
 					infoExt[i].Idle = 0
 				}
 				Expect(infoExt).To(Equal([]redis.XPendingExt{
-					{ID: "1-0", Consumer: "consumer", Idle: 0, RetryCount: 1},
-					{ID: "2-0", Consumer: "consumer", Idle: 0, RetryCount: 1},
-					{ID: "3-0", Consumer: "consumer", Idle: 0, RetryCount: 1},
+					{Id: "1-0", Consumer: "consumer", Idle: 0, RetryCount: 1},
+					{Id: "2-0", Consumer: "consumer", Idle: 0, RetryCount: 1},
+					{Id: "3-0", Consumer: "consumer", Idle: 0, RetryCount: 1},
 				}))
 
 				n, err := client.XGroupDelConsumer("stream", "group", "consumer").Result()