Skip to content

Instantly share code, notes, and snippets.

@benhoyt
Created July 7, 2020 05:06
Show Gist options
  • Star 1 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save benhoyt/05e22f0d52f7feaf88b0a37f8b739f91 to your computer and use it in GitHub Desktop.
Save benhoyt/05e22f0d52f7feaf88b0a37f8b739f91 to your computer and use it in GitHub Desktop.
Little Go tool to flatten JSON input
// Flatten JSON input
//
// Example:
//
// $ echo '{"user":"Ben","ints":[true,false,null],"sub":{"x":1,"y":2}}' | go run flattenjson.go
// _.ints[0] = true
// _.ints[1] = false
// _.ints[2] = null
// _.sub.x = 1
// _.sub.y = 2
// _.user = "Ben"
package main
import (
"encoding/json"
"fmt"
"os"
"sort"
)
func main() {
decoder := json.NewDecoder(os.Stdin)
var obj interface{}
err := decoder.Decode(&obj)
if err != nil {
fmt.Fprintf(os.Stderr, "input is not valid JSON: %s\n", err)
os.Exit(1)
}
flatten(obj, "_")
}
func flatten(obj interface{}, prefix string) {
switch obj := obj.(type) {
case bool:
fmt.Printf("%s = %t\n", prefix, obj)
case float64:
fmt.Printf("%s = %g\n", prefix, obj)
case string:
fmt.Printf("%s = %q\n", prefix, obj)
case []interface{}:
for i, v := range obj {
flatten(v, fmt.Sprintf("%s[%d]", prefix, i))
}
case map[string]interface{}:
keys := make([]string, 0, len(obj))
for k := range obj {
keys = append(keys, k)
}
sort.Strings(keys)
for _, k := range keys {
flatten(obj[k], fmt.Sprintf("%s.%s", prefix, k))
}
default:
fmt.Printf("%s = null\n", prefix)
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment