EdgeCaseBerg EdgeCaseBerg - 1 year ago 219
JSON Question

Format Timestamp in outgoing JSON in Golang?

I've been playing with Go recently and it's awesome. The thing I can't seem to figure out (after looking through documentation and blog posts) is how to get the

type to format into whatever format I'd like when it's encoded by

Here's a minimal Code example:

package main

type Document struct {
Name string
Content string
Stamp time.Time
Author string

func sendResponse(data interface{}, w http.ResponseWriter, r * http.Request){
_, err := json.Marshal(data)
j := json.NewEncoder(w)
if err == nil {
encodedErr := j.Encode(data)
if encodedErr != nil{
//code snipped
//code snipped

func main() {
http.HandleFunc("/document", control.HandleDocuments)
http.ListenAndServe("localhost:4000", nil)

func HandleDocuments(w http.ResponseWriter,r *http.Request) {
w.Header().Set("Content-Type", "application/json")
w.Header().Set("Access-Control-Allow-Origin", "*")

switch r.Method {
case "GET":
//logic snipped
testDoc := model.Document{"Meeting Notes", "These are some notes", time.Now(), "Bacon"}
sendResponse(testDoc, w,r)
case "POST":
case "PUT":
case "DELETE":

Ideally, I'd like to send a request and get the Stamp field back as something like
May 15, 2014
and not

But I'm not really sure how, I know I can add
to the Document type declaration to get the field to be encoded with the name stamp instead of Stamp, but I don't know what those types of things are called, so I'm not even sure what to google for to find out if there is some type of formatting option in that as well.

Does anyone have a link to the an example or good documentation page on the subject of those type mark ups (or whatever they're called) or on how I can tell the JSON encoder to handle

Just for reference, I have looked at these pages: here and here and of course, at the official docs

Answer Source

What you can do is, wrap time.Time as your own custom type, and make it implement the Marshaler interface:

type Marshaler interface {
    MarshalJSON() ([]byte, error)

So what you'd do is something like:

type JSONTime time.Time

func (t JSONTime)MarshalJSON() ([]byte, error) {
    //do your serializing here
    stamp := fmt.Sprintf("\"%s\"", time.Time(t).Format("Mon Jan _2"))
    return []byte(stamp), nil

and make document:

type Document struct {
    Name        string
    Content     string
    Stamp       JSONTime
    Author      string

and have your intialization look like:

 testDoc := model.Document{"Meeting Notes", "These are some notes", JSONTime(time.Now()), "Bacon"}    

And that's about it. If you want unmarshaling, there is the Unmarshaler interface too.

Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download