JSON to Go Struct Generator

Generate Go structs with json tags from a JSON sample: numbers split into int and float64, nested objects become their own structs, and unknown shapes fall back to interface{}.

Hand-writing Go structs is mostly tag work: the field name has to become PascalCase while the json tag keeps the exact key from the payload, and with enough underscores in the JSON one tag gets mistyped. The failure is quiet — the field simply stays at its zero value after unmarshalling, and you end up re-reading the API docs to find out why. Paste a sample and the struct definition arrives with every json tag already matching the original key, in the same order as the JSON so you can check it line by line.

Everything runs in the browser and the sample is never sent to a server. The generator infers from this one document and follows fixed rules, returning interface{} rather than guessing when it cannot tell, so the result compiles; decisions such as pointers and omitempty are still yours to make.

Type mapping and json tags

Numbers are split by whether they are whole: a value like 1 becomes int and 1.5 becomes float64. JSON has no integer type, and JavaScript collapses 1.0 to 1 before the generator sees it, so a field written as 1.0 also becomes int. Booleans become bool, strings string, null interface{}, and an empty array []interface{}. Every field carries a json tag holding the original key, which is why user_name deserializes correctly even though the field itself is named UserName. The generator never adds omitempty and never emits pointer types. The root struct is named AutoGenerated unless you set Root type name in the toolbar.

Pointers, zero values and what the output cannot express

Because null becomes interface{} and there are no pointers or omitempty tags, the generated struct cannot distinguish three cases: the key was absent, the key was explicitly null, and the value is the zero value. For a PATCH endpoint, or anywhere the difference matters, change the field to *int or *string, add omitempty to the tag, or use a wrapper such as sql.NullString. If you only read the data for display, interface{} is workable — but reading it requires a type assertion, and a missing assertion fails at runtime rather than at compile time.

Nested structs, arrays and naming collisions

Nested objects become separate structs named with the same PascalCase rule. When the root is an array, one struct is generated from the first element and no slice alias is added, so declare []RootType where you use it. Underscores and hyphens are handled in field and struct names; keys containing dots or spaces produce illegal identifiers, and user_name next to user-name collapses into a single field name, which is a duplicate-field compile error. Big integers have already lost precision after JSON.parse, so switch those fields to string or json.Number before you rely on them.

Advertisement

Frequently asked questions

How does the generator decide between int and float64?
It checks whether the parsed number is a whole number: integers become int, everything else float64 — and 1.0 is a whole number, so it becomes int as well. Force float64 by hand for money and ratios, or use a decimal library type, otherwise a value that happens to be whole today can be truncated later.
Why does null produce interface{} rather than a pointer?
The generator does not guess at the type behind a null, so it falls back to the empty interface. The code compiles, but you must type-assert to read the value, and you cannot tell an absent key from an explicit null. When that distinction matters, edit the field to a pointer type and add omitempty, or use the matching Null wrapper type.
Why is there only one struct when the root is an array?
Only the first element is inspected and the output is a single struct definition with no slice alias, so write []YourStruct at the call site. If the elements have uneven shapes, the first element may lack fields that later records carry; feed in your most complete record, or add the missing fields by hand.
Does renaming a field break the json tag?
No. The tag keeps the original JSON key and the Go field name is irrelevant to unmarshalling — that is exactly why the generator emits a tag for every field. Binding breaks only if you edit the tag or the API changes the key. Use a "-" tag to ignore a field, and add omitempty yourself if the field should be omitted when empty.

Related tools

Advertisement