go-simplejson icon indicating copy to clipboard operation
go-simplejson copied to clipboard

Why the app panic?

Open netjune opened this issue 5 years ago • 1 comments

package main

import (
	"fmt"
	js "github.com/bitly/go-simplejson"
)

func main() {
	child := js.New()
	child.Set("foo", "foo")
	child.Set("bar", "bar")

	parent := js.New()
	parent.Set("child_1", child)

	tmp_json := parent.Get("child_1")

	ss, _ := tmp_json.EncodePretty()
	fmt.Printf("==== ss: %s\n", ss)

	s1,err := tmp_json.Get("foo").String()
	if err != nil {
		panic(0)
	}
	fmt.Printf("=== s1: %s\n", s1)
}

netjune avatar Apr 17 '19 08:04 netjune

It is kind of a bug in the library, which people might expect to work out of the box. But it is a missing feature. You can take a look at how Set() and Get() are implemented to know why it's not working.

It is because the tmp_json is of type &Json{data:&Json{}} when it is supposed to be just &Json{}. EncodePretty works because the standard json library uses reflect (and does it correctly).

Two ways you can fix this in your code. (Workarounds)

  1. By using parent.Set("child_1", child.Interface()) instead of parent.Set("child_1", child).
  2. Or By using tmp_json.Interface().Get("foo").String()

i.e.

package main

import (
	"fmt"

	js "github.com/bitly/go-simplejson"
)

func main() {
	child := js.New()
	child.Set("bar", "bar")
	child.Set("foo", "foo")

	parent := js.New()

	// This
	parent.Set("child_interface", child.Interface())
	tmp_intf := parent.Get("child_interface")
	s1, err := tmp_intf.Get("foo").String()
	if err != nil {
		panic(err)
	}
	fmt.Printf("s1: %s\n", s1)

	// Or this
	parent.Set("child_json", child)
	tmp_json := parent.Get("child_json")
	s2, err := tmp_json.Interface().(*js.Json).Get("foo").String()
	if err != nil {
		panic(err)
	}
	fmt.Printf("s2: %s\n", s2)
}

phanirithvij avatar Jul 25 '21 10:07 phanirithvij