소스 검색

Add custom argument representation handling

Add the ability for types to control how they are sent when used as
arguments to redis commands.

This is useful for types which don't want to use their Stringer
representation when used as an argument to a redis command.

Examples of this is a time.Duration which the user wants to store
the number of seconds or a time.Time being stored as int instead of
a string.
Steven Hartland 9 년 전
부모
커밋
34750db78c
3개의 변경된 파일24개의 추가작업 그리고 0개의 파일을 삭제
  1. 4 0
      redis/conn.go
  2. 12 0
      redis/conn_test.go
  3. 8 0
      redis/redis.go

+ 4 - 0
redis/conn.go

@@ -370,6 +370,10 @@ func (c *conn) writeCommand(cmd string, args []interface{}) (err error) {
 			}
 		case nil:
 			err = c.writeString("")
+		case Argument:
+			var buf bytes.Buffer
+			fmt.Fprint(&buf, arg.RedisArg())
+			err = c.writeBytes(buf.Bytes())
 		default:
 			var buf bytes.Buffer
 			fmt.Fprint(&buf, arg)

+ 12 - 0
redis/conn_test.go

@@ -46,6 +46,14 @@ func dialTestConn(r io.Reader, w io.Writer) redis.DialOption {
 	})
 }
 
+type durationArg struct {
+	time.Duration
+}
+
+func (t durationArg) RedisArg() interface{} {
+	return t.Seconds()
+}
+
 var writeTests = []struct {
 	args     []interface{}
 	expected string
@@ -82,6 +90,10 @@ var writeTests = []struct {
 		[]interface{}{"SET", "key", nil},
 		"*3\r\n$3\r\nSET\r\n$3\r\nkey\r\n$0\r\n\r\n",
 	},
+	{
+		[]interface{}{"SET", "key", durationArg{time.Minute}},
+		"*3\r\n$3\r\nSET\r\n$3\r\nkey\r\n$2\r\n60\r\n",
+	},
 	{
 		[]interface{}{"ECHO", true, false},
 		"*3\r\n$4\r\nECHO\r\n$1\r\n1\r\n$1\r\n0\r\n",

+ 8 - 0
redis/redis.go

@@ -39,3 +39,11 @@ type Conn interface {
 	// Receive receives a single reply from the Redis server
 	Receive() (reply interface{}, err error)
 }
+
+// Argument is implemented by types which want to control how their value is
+// interpreted when used as an argument to a redis command.
+type Argument interface {
+	// RedisArg returns the interface that represents the value to be used
+	// in redis commands.
+	RedisArg() interface{}
+}