Working with JSON in Java
No JSON in the JDK; Jackson/Gson concepts of mapping objects.
No JSON in the box
As of Java 25, the JDK has no standard JSON API. Projects use libraries: Jackson (Spring Boot's default) or Gson. Both map JSON to Java objects and back.
Data binding
**mapper.readValue(json, User.class)** creates a User and fills it by matching JSON property names to fields, setters or record components, converting numbers and nested objects. **writeValueAsString goes the other way. Gson: gson.fromJson / gson.toJson**.
record User(String name, int age) { }
var mapper = new ObjectMapper();
User u = mapper.readValue(json, User.class);
String out = mapper.writeValueAsString(u);JSON by hand
What does this print?
String city = "Rock \"n\" Roll";
String json = "{\"city\":\"" + city + "\"}";
System.out.println(json);{"city":"Rock "n" Roll"}{"city":"Rock \"n\" Roll"}Compile error
Show the answer
{"city":"Rock "n" Roll"} — concatenation copies the inner quotes unescaped, so the JSON string ends early: invalid JSON. A library escapes them as \" for you.
Renaming and ignoring
Annotations bridge naming differences: **@JsonProperty("user_id") maps a field to a different JSON name, @JsonIgnore** leaves a field out.
class Account {
@JsonProperty("user_id") long userId;
@JsonIgnore String passwordHash;
}When the API adds a field
By default Jackson fails on unknown properties: the API adds "nickname" and your client throws **UnrecognizedPropertyException. Make clients tolerant with @JsonIgnoreProperties(ignoreUnknown = true)** (or disable FAIL_ON_UNKNOWN_PROPERTIES).
@JsonIgnoreProperties(ignoreUnknown = true)
record User(String name, int age) { }Why tolerate unknown fields?
Why is ignoring unknown JSON fields a good default for API clients?
Think about it, then reveal the answer
APIs evolve: servers add fields all the time. Tolerant clients keep working when a new field appears, so the API team can ship without breaking everyone.
JSON everywhere
REST APIs, config files, message queues and logs all speak JSON. Spring Boot wires Jackson in automatically, and a surprising number of production bugs come from hand-built JSON strings or clients that crash on a new field.
Key takeaways
- No JSON parser in the JDK (as of Java 25)
- Jackson: ObjectMapper.readValue / writeValueAsString
- Gson: gson.fromJson / gson.toJson
- Annotations rename or ignore properties
JSON was popularised by Douglas Crockford in the early 2000s; he says he "discovered" it rather than invented it, because it was already valid JavaScript.
Practice questions
What does objectMapper.readValue(json, User.class) do?
- Checks whether the JSON is valid and returns a boolean
- Creates a User and fills it by matching JSON property names to its fields, setters or record components
- Converts the User class into a JSON schema
- Returns the JSON as a Map<String, Object> only
Check your answer
Creates a User and fills it by matching JSON property names to its fields, setters or record components. Deserialization (data binding) reads each JSON property and assigns it to the matching Java property, converting types like numbers and nested objects.
The API added a new "nickname" field and your Jackson client now fails with UnrecognizedPropertyException. What's the best fix?
- Annotate the class with @JsonIgnoreProperties(ignoreUnknown = true)
- Catch the exception and return null
- Parse the JSON by hand with split(",")
- Ask the API team to never add fields
Check your answer
Annotate the class with @JsonIgnoreProperties(ignoreUnknown = true). Ignoring unknown properties (or disabling FAIL_ON_UNKNOWN_PROPERTIES) makes clients tolerant of new fields, so the API can evolve without breaking them.