Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

handle ISO8601 for time.Time JSON values #298

Closed
adamdecaf opened this issue Oct 10, 2018 · 7 comments
Closed

handle ISO8601 for time.Time JSON values #298

adamdecaf opened this issue Oct 10, 2018 · 7 comments

Comments

@adamdecaf
Copy link
Member

Our API docs currently state (as part of POST /files/create's response):

{
  "fileCreationDate": "102318",
  "fileCreationTime": "1601"
}

Source: https://api.moov.io/#operation/addFile

However, this format might be annoying for folks. Should we support RFC 3339 and YYMMDD / HHMM?

Our api returns RFC 3339 now, which is Go's default).

$ curl -s -H "cookie: moov_auth=..." https://api.moov.io/v1/ach/files/docrlxnuinuoouhilfws | jq '.file.fileHeader' | grep fileCreation
  "fileCreationDate": "2018-10-08T00:00:00Z",
  "fileCreationTime": "2018-10-08T00:00:00Z", 

Examples:

@wadearnold
Copy link
Member

We use to store it as a default Go time in the library but those time values are used for looking up the transaction later. That's why we now use the specification. I would recommend that we marshal in and out of the javascript standard of ISO-8601

Date, time and timezone
ISO 8601 notation to be used for Date time
ISO 8601 uses the 24-hour clock system. The basic format is [hh][mm][ss] and the extended format is [hh]:[mm]:[ss].
ISO_8601

Datetime with time zone is necessary for calculating cutoff times. We may want to default to Eastern TIme zone unless an offset is supplied.

yyyy-mm-ddThh:mm:ss.nnnnnn+|-hh:mm
2008-09-15T15:53:00+05:00

@adamdecaf
Copy link
Member Author

It looks like ISO 8601 was long ago removed from Go due to incorrect parsing. golang/go#734

@adamdecaf
Copy link
Member Author

Also, a few of the popular javascript libraries support RFC 3339 parsing - https://stackoverflow.com/a/11318911

@adamdecaf
Copy link
Member Author

adamdecaf commented Oct 30, 2018

https://stackoverflow.com/questions/522251/whats-the-difference-between-iso-8601-and-rfc-3339-date-formats

They aren't swappable with each other, ugh. We could support ISO 8601 by adding a base.Time struct.

type Time struct {
	*time.Time
}

func (t Time) MarshalJSON() ([]byte, error) {
	// ...	
}

func (t *Time) UnmarshalJSON(data []byte) error {
	// ...
}

Example: https://github.com/joeshaw/iso8601/blob/master/iso8601.go

We should add something like ^ into the base repository with more tests.

@adamdecaf
Copy link
Member Author

I started on this in a time.go for our base repository (root level)

// Copyright 2018 The Moov Authors
// Use of this source code is governed by an Apache License
// license that can be found in the LICENSE file.

import (
	"time"
)

type Time struct {
	*time.Time
}

// 2018-10-30T17:48:48+00:00
// 2018-10-30T17:48:48Z

// javascript
// 2018-10-30T18:24:56.945Z

// Go format
// Mon Jan 2 15:04:05 -0700 MST 2006

// MarshalJSON implements the json.Marshaler interface.
// The time is a quoted string in ISO 8601 format.
func (t Time) MarshalJSON() ([]byte, error) {
	str, err := t.Format(

	// if y := t.Year(); y < 0 || y >= 10000 {
	// 	// RFC 3339 is clear that years are 4 digits exactly.
	// 	// See golang.org/issue/4556#c15 for more discussion.
	// 	return nil, errors.New("Time.MarshalJSON: year outside of range [0,9999]")
	// }

	// b := make([]byte, 0, len(RFC3339Nano)+2)
	// b = append(b, '"')
	// b = t.AppendFormat(b, RFC3339Nano)
	// b = append(b, '"')
	// return b, nil
}

// UnmarshalJSON implements the json.Unmarshaler interface.
// The time is expected to be a quoted string in RFC 3339 format.
func (t *Time) UnmarshalJSON(data []byte) error {
	// // Ignore null, like in the main JSON package.
	// if string(data) == "null" {
	// 	return nil
	// }
	// // Fractional seconds are handled implicitly by Parse.
	// var err error
	// *t, err = Parse(`"`+RFC3339+`"`, string(data))
	// return err
}

@wadearnold
Copy link
Member

This seems safe

@adamdecaf adamdecaf changed the title Do we accept YYMMDD / HHMM and/or RFC 3339 for time.Time values? handle ISO8601 for time.Time JSON values Oct 31, 2018
@adamdecaf
Copy link
Member Author

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants