2013-04-14 9 views
5

Ho le seguenti tipologie:MarshalJSON su array di struct con il campo non standard in Go

type IPFilePair struct { 
    IP net.IP 
    FileName string 
} 

type IPFilePairs []*IPFilePair 

sto cercando di schierare il JSON di questo usando json.Marshal(sample_ipfilepairs) ma perché IP non è una stringa, si cambia in qualcosa di strano

Qual è il modo corretto per rendere il JSON di questa uscita IP come una stringa?

risposta

9

Penso che se si ha accesso alla definizione di IPFilePair, creando typedef locale del net.IP che si aggiunge MarshanJSON() alla è la strada da percorrere:

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)) 
} 

Questo uscite:

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

Di Certo, se hai mai bisogno di unmarshal che torna nella stessa struttura dati Go, ti consigliamo di implementare UnmarshalJSON() su netIP utilizzando net.ParseIP.

Sono certo curioso se qualcuno sa di un modo più semplice per realizzare questo.

+0

Dolce, questo ha funzionato. – Aaronneyer

+0

È un peccato non aggiungere semplicemente il metodo 'MarshalJSON' direttamente a' net.IP', ma credo che sia una delle restrizioni necessarie per essere in grado di compilare moduli separati dal programma completo. –

+0

@JamesHenstridge. Concordato. Questo è il modo migliore in cui io sappia come farlo, ma speravo in qualcuno che parlava in modo più fluente di me che io venissi e mostrassi una soluzione più semplice. –