瀏覽代碼

Add support for marshaling durations.

Gustavo Niemeyer 12 年之前
父節點
當前提交
a5844a8f8f
共有 5 個文件被更改,包括 34 次插入4 次删除
  1. 11 0
      decode.go
  2. 8 1
      decode_test.go
  3. 6 1
      encode.go
  4. 8 1
      encode_test.go
  5. 1 1
      suite_test.go

+ 11 - 0
decode.go

@@ -3,6 +3,7 @@ package yaml
 import (
 	"reflect"
 	"strconv"
+	"time"
 )
 
 const (
@@ -279,6 +280,8 @@ func (d *decoder) alias(n *node, out reflect.Value) (good bool) {
 	return good
 }
 
+var durationType = reflect.TypeOf(time.Duration(0))
+
 func (d *decoder) scalar(n *node, out reflect.Value) (good bool) {
 	var tag string
 	var resolved interface{}
@@ -321,6 +324,14 @@ func (d *decoder) scalar(n *node, out reflect.Value) (good bool) {
 				out.SetInt(int64(resolved))
 				good = true
 			}
+		case string:
+			if out.Type() == durationType {
+				d, err := time.ParseDuration(resolved)
+				if err == nil {
+					out.SetInt(int64(d))
+					good = true
+				}
+			}
 		}
 	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
 		switch resolved := resolved.(type) {

+ 8 - 1
decode_test.go

@@ -1,10 +1,11 @@
 package yaml_test
 
 import (
-	. "launchpad.net/gocheck"
+	. "gopkg.in/check.v1"
 	"gopkg.in/yaml.v1"
 	"math"
 	"reflect"
+	"time"
 )
 
 var unmarshalIntTest = 123
@@ -364,6 +365,12 @@ var unmarshalTests = []struct {
 		"a: 50cent_of_dollar",
 		map[string]interface{}{"a": "50cent_of_dollar"},
 	},
+
+	// Duration
+	{
+		"a: 3s",
+		map[string]time.Duration{"a": 3 * time.Second},
+	},
 }
 
 type inlineB struct {

+ 6 - 1
encode.go

@@ -4,6 +4,7 @@ import (
 	"reflect"
 	"sort"
 	"strconv"
+	"time"
 )
 
 type encoder struct {
@@ -85,7 +86,11 @@ func (e *encoder) marshal(tag string, in reflect.Value) {
 	case reflect.String:
 		e.stringv(tag, in)
 	case reflect.Int, reflect.Int8, reflect.Int16, reflect.Int32, reflect.Int64:
-		e.intv(tag, in)
+		if in.Type() == durationType {
+			e.stringv(tag, reflect.ValueOf(in.Interface().(time.Duration).String()))
+		} else {
+			e.intv(tag, in)
+		}
 	case reflect.Uint, reflect.Uint8, reflect.Uint16, reflect.Uint32, reflect.Uint64, reflect.Uintptr:
 		e.uintv(tag, in)
 	case reflect.Float32, reflect.Float64:

+ 8 - 1
encode_test.go

@@ -2,11 +2,12 @@ package yaml_test
 
 import (
 	"fmt"
-	. "launchpad.net/gocheck"
 	"gopkg.in/yaml.v1"
+	. "gopkg.in/check.v1"
 	"math"
 	"strconv"
 	"strings"
+	"time"
 )
 
 var marshalIntTest = 123
@@ -212,6 +213,12 @@ var marshalTests = []struct {
 		}{1, inlineB{2, inlineC{3}}},
 		"a: 1\nb: 2\nc: 3\n",
 	},
+
+	// Duration
+	{
+		map[string]time.Duration{"a": 3 * time.Second},
+		"a: 3s\n",
+	},
 }
 
 func (s *S) TestMarshal(c *C) {

+ 1 - 1
suite_test.go

@@ -1,7 +1,7 @@
 package yaml_test
 
 import (
-	. "launchpad.net/gocheck"
+	. "gopkg.in/check.v1"
 	"testing"
 )