336

I am trying to convert a Go struct to JSON using the json package but all I get is {}. I am certain it is something totally obvious but I don't see it.

package main import ( "fmt" "encoding/json" ) type User struct { name string } func main() { user := &User{name:"Frank"} b, err := json.Marshal(user) if err != nil { fmt.Printf("Error: %s", err) return; } fmt.Println(string(b)) } 

Then when I try to run it I get this:

$ 6g test.go && 6l -o test test.6 && ./test {} 
0

2 Answers 2

562

You need to export the User.name field so that the json package can see it. Rename the name field to Name.

package main import ( "fmt" "encoding/json" ) type User struct { Name string } func main() { user := &User{Name: "Frank"} b, err := json.Marshal(user) if err != nil { fmt.Println(err) return } fmt.Println(string(b)) } 

Output:

{"Name":"Frank"} 
Sign up to request clarification or add additional context in comments.

7 Comments

Note that you can add `json:"name"` to the end of the struct field definition to preserve the output name.
I see. I kinda like the language but I think some syntactical elements go to far. If the name of a struct member determines the behavior then this is just wrong.
Well, having the name determine the behavior can be debated if it is good or bad :) but it sure make it easy to know if a field is exported or not without having to check somewhere else.
@magiconair: The capitalization of the first rune determines visibility, is a much more reasonable idea than, "the name of a struct member determines the behavior". The visibility metadata needs to be stored somewhere and needs syntax to express it. Eventually it was determined that co opting the capitalization of the first char works best with fewest trade-offs. Before the Go1 release other schemes were tried and rejected.
I've come a long way since and like the language including the exporting by capitalization very much now.
|
14

You can define your own custom MarshalJSON and UnmarshalJSON methods and intentionally control what should be included, ex:

package main import ( "fmt" "encoding/json" ) type User struct { name string } func (u *User) MarshalJSON() ([]byte, error) { return json.Marshal(&struct { Name string `json:"name"` }{ Name: u.name, }) } func main() { user := &User{name: "Frank"} b, err := json.Marshal(user) if err != nil { fmt.Println(err) return } fmt.Println(string(b)) } 

Comments

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.