MarshalJSON in an array of structures with a custom field in Go

I have the following types:

type IPFilePair struct {
    IP net.IP
    FileName string
}

type IPFilePairs []*IPFilePair

I am trying to combine JSON with json.Marshal(sample_ipfilepairs), but since IPit is not a string, it changes it to something strange.

What is the correct way to make the JSON of this output IPas a string?

+5
source share
1 answer

I think that if you have access to the definition IPFilePair, create a local typedef from net.IPthat you add MarshanJSON()to this method:

package main

import (
    "encoding/json"
    "net"
    "fmt"
)

type netIP net.IP

type IPFilePair struct {
    IP netIP
    FileName string
}

type IPFilePairs []*IPFilePair

func (ip netIP) MarshalJSON() ([]byte, error) {
    return json.Marshal(net.IP(ip).String())
}

func main() {
    pair1 := IPFilePair{netIP{127, 0, 0, 1}, "file1"}
    pair2 := IPFilePair{netIP{127, 0, 0, 2}, "file2"}
    sample_ipfilepairs := IPFilePairs{&pair1, &pair2}

    b, _ := json.Marshal(sample_ipfilepairs)
    fmt.Println(string(b))
}

It is output:

[{"IP":"127.0.0.1","FileName":"file1"},{"IP":"127.0.0.2","FileName":"file2"}]

Of course, if you ever need to undo it back to the same Go data structure, you need to implement UnmarshalJSON()on netIPwith net.ParseIP.

I am of course curious if anyone knows an easier way to accomplish this.

+9
source

All Articles