cephfs admin: add TimeStamp type for JSON unmarshaling

The date & time format used by ceph differs from the default used by Go
for time.Time types. Define a new type, embedding time.Time, that can
parse and expressing date+time strings the ceph way.

Signed-off-by: John Mulligan <jmulligan@redhat.com>
This commit is contained in:
John Mulligan 2020-09-02 13:50:01 -04:00 committed by John Mulligan
parent cdc0264a6b
commit ed23d71ff8
2 changed files with 83 additions and 0 deletions

39
cephfs/admin/timestamp.go Normal file
View File

@ -0,0 +1,39 @@
// +build !luminous,!mimic
package admin
import (
"encoding/json"
"time"
)
// golang's date parsing approach is rather bizarre
var cephTSLayout = "2006-01-02 15:04:05"
// TimeStamp abstracts some of the details about date+time stamps
// returned by ceph via JSON.
type TimeStamp struct {
time.Time
}
// String returns a string representing the date+time as presented
// by ceph.
func (ts TimeStamp) String() string {
return ts.Format(cephTSLayout)
}
// UnmarshalJSON implements the json Unmarshaler interface.
func (ts *TimeStamp) UnmarshalJSON(b []byte) error {
var raw string
if err := json.Unmarshal(b, &raw); err != nil {
return err
}
// AFAICT, ceph always returns the time in UTC so Parse, as opposed to
// ParseInLocation, is appropriate here.
t, err := time.Parse(cephTSLayout, raw)
if err != nil {
return err
}
*ts = TimeStamp{t}
return nil
}

View File

@ -0,0 +1,44 @@
// +build !luminous,!mimic
package admin
import (
"encoding/json"
"testing"
"time"
"github.com/stretchr/testify/assert"
)
func TestTimeStampUnmarshal(t *testing.T) {
t.Run("valid", func(t *testing.T) {
j1 := []byte(`"2020-01-03 18:03:21"`)
var ts TimeStamp
err := json.Unmarshal(j1, &ts)
assert.NoError(t, err)
assert.Equal(t, 2020, ts.Year())
assert.Equal(t, time.Month(1), ts.Month())
assert.Equal(t, 3, ts.Day())
})
t.Run("badType", func(t *testing.T) {
j1 := []byte(`["2020-01-03 18:03:21"]`)
var ts TimeStamp
err := json.Unmarshal(j1, &ts)
assert.Error(t, err)
})
t.Run("badValue", func(t *testing.T) {
j1 := []byte(`"just another manic monday"`)
var ts TimeStamp
err := json.Unmarshal(j1, &ts)
assert.Error(t, err)
})
}
func TestTimeStampString(t *testing.T) {
s := "2020-11-06 11:33:56"
ti, err := time.Parse(cephTSLayout, s)
if assert.NoError(t, err) {
ts := TimeStamp{ti}
assert.Equal(t, s, ts.String())
}
}