JSON in Java umwandeln
Dieses Tool erzeugt aus einem Beispieldokument in Ihrem Browser Records oder POJOs. Optionale numerische Felder werden geboxt – Integer statt int –, weil ein primitiver Typ kein null aufnehmen kann; ein fehlender Schlüssel wird daher zu 0 deserialisiert und ist von einer echten 0 nicht mehr zu unterscheiden.
Das Dokument endet zu früh – es scheint abgeschnitten.
^
Wie funktioniert JSON in Java umwandeln?
Die primitiven Typen von Java machen die Frage nach optionalen Feldern zu einer konkreten statt einer Stilfrage, und wer sie falsch beantwortet, erzeugt einen Bug, der sich wirklich schwer finden lässt.
Ein primitiver Typ kann nicht fehlen
int count deserialisiert einen fehlenden count-Schlüssel zu 0. Keine Exception, keine Warnung – und nachgelagert gibt es keine Möglichkeit, einen Datensatz, bei dem count nie gesendet wurde, von einem zu unterscheiden, bei dem count wirklich 0 war. Dasselbe gilt für boolean, das zu false wird, und double, das zu 0.0 wird. Optionale und nullable Felder werden deshalb geboxt: Integer, Long, Double, Boolean – alle können null aufnehmen und erlauben Ihnen, die Frage überhaupt zu stellen.
Generics können keine primitiven Typen aufnehmen
List<int> kompiliert nicht. Jedes Listenelement wird geboxt, egal ob optional oder nicht – deshalb wird ein Array aus Ganzzahlen zu List<Integer>.
record oder POJO
Ein record ist auf Java 17 und später die bessere Voreinstellung: unveränderlich, kein Boilerplate, equals, hashCode und toString gratis, und Jackson unterstützt Records seit 2.12. Ein POJO mit privaten Feldern sowie Gettern und Settern ist das, was eine Codebase auf Java 8 oder ein Framework verlangt, das einen argumentlosen Konstruktor braucht – also stehen beide zur Verfügung.
Jackson-Annotationen tragen den ursprünglichen Schlüssel
Die Java-Konvention ist camelCase, JSON-Schlüssel sind das häufig nicht. Statt sich darauf zu verlassen, dass irgendwo anders eine PropertyNamingStrategy konfiguriert ist, bekommt jede Komponente ein explizites @JsonProperty mit dem exakten Schlüssel aus dem Dokument. Die Klasse bindet dann korrekt, ganz gleich, worauf der ObjectMapper eingestellt ist.
Ein öffentlicher Typ pro Datei
Java erlaubt genau einen öffentlichen Top-Level-Typ pro Quelldatei; ein Dokument, das mehrere Typen erzeugt, kompiliert daher nicht als einzelnes Einfügen. Die Ausgabe weist in einem Header-Kommentar darauf hin: Speichern Sie jeden Typ als <TypeName>.java, oder verschachteln Sie ihn in einer äußeren Klasse. Eine Datei auszugeben, die javac ablehnt, ohne es zu erwähnen, ist die Art kleiner Unaufrichtigkeit, die zehn Minuten kostet.
Beispiel
[
{ "user_id": 1, "retries": 0, "tags": ["a"] },
{ "user_id": 2, "tags": [] }
]Generiert
public record User(
@JsonProperty("user_id") int userId,
@JsonProperty("retries") Integer retries,
@JsonProperty("tags") List<String> tags
) {}Welche Optionen und Sonderfälle unterstützt JSON in Java umwandeln?
| Parameter | Typ | Standard | Verhalten & Sonderfälle |
|---|---|---|---|
| Form | record / POJO | record | record für Java 17+ für ein unveränderliches DTO ohne Boilerplate. POJO für Java 8 oder für alles, was einen Konstruktor ohne Argumente und Setter benötigt. |
| Paket | Bezeichner | (keine) | Fügt eine Package-Deklaration hinzu. Lassen Sie es leer für eine Scratch-Datei; setzen Sie es so, dass es mit dem Verzeichnis übereinstimmt, in dem die Datei gespeichert wird. |
| Jackson | Boolesch | on | Emitiert @JsonProperty mit dem exakten JSON-Schlüssel, sodass die Bindung nicht von einer anderswo konfigurierten ObjectMapper-Naming-Strategie abhängt. |
| Optionals boxen | Boolesch | on | Ein optionaler int wird zu Integer. Wenn dies deaktiviert wird, wird ein fehlender Schlüssel als 0 deserialisiert, was nicht von einer echten Null unterscheidbar ist. |
| string | Java-Typ | String | Erkannte Formate werden nicht auf Instant, LocalDate oder UUID abgebildet. Jackson erfordert, dass JavaTimeModule für die ersten beiden registriert ist, und wirft einen Fehler bei jedem Record, dessen Format abweicht. |
| integer | Java-Typ | int / long | long, wenn irgendein Beispiel 2,147,483,647 überschreitet. Eine JSON-Zahl trägt keine deklarierte Breite, daher wird die Breite aus den Werten gelesen. |
| array | Java-Typ | List<T> | Elemente sind immer geboxt, da Generics keine Primitiven halten können. Ein gemischtes Array wird zu List<Object>. |
| Verschachteltes Objekt | Typ | eigener Typ | Wird zu seinem eigenen Record oder Klasse, vor dem deklariert, der es verwendet. Identische Formen teilen einen Typ anstelle der Generierung nummerierter Duplikate. |
Häufig gestellte Fragen
Warum ist das eine Feld int und das andere Integer?
Der Integer tauchte in manchen Datensätzen auf und in anderen nicht. Ein primitives int kann kein null aufnehmen, also deserialisiert Jackson einen fehlenden Schlüssel zu 0 – und nichts Nachgelagertes kann das von einem Datensatz unterscheiden, der wirklich 0 gesendet hat. Ein Integer kann null sein, was das Fehlen sichtbar macht. Felder, die in jedem Datensatz vorkommen, bleiben primitiv – das ist billiger und einfacher.
Kann ich die ganze Ausgabe in eine Datei einfügen?
Nicht, wenn mehr als ein Typ erzeugt wurde. Java erlaubt genau einen öffentlichen Top-Level-Typ pro Quelldatei, javac lehnt es also ab. Speichern Sie jeden Typ als <TypeName>.java, oder machen Sie die verschachtelten zu static nested classes innerhalb einer äußeren Klasse. Oben in der Ausgabe steht, welcher Fall bei Ihnen vorliegt.
record oder POJO?
record, wenn Sie auf Java 17 oder später sind und das Objekt Daten sind, die von irgendwoher kommen: Es ist unveränderlich, liefert equals, hashCode und toString korrekt mit, und Jackson unterstützt Records seit 2.12. POJO, wenn Sie auf Java 8 sind, wenn ein Framework einen argumentlosen Konstruktor und Setter verlangt (älteres JPA, manche Spring-Konfigurationen), oder wenn das Objekt nach dem Konstruieren wirklich verändert werden muss.
Warum ist mein Zeitstempel ein String statt Instant?
Weil Jackson es ohne registriertes JavaTimeModule nicht in Instant parsen kann und weil es beim ersten Datensatz, dessen Format vom Erwarteten abweicht, eine Ausnahme wirft. Echte APIs senden Unix-Sekunden, Unix-Millisekunden, ISO 8601 mit und ohne Offset und gelegentlich etwas Regionales. Das erkannte Format ist in der Referenz oben vermerkt, damit Sie den Typ bewusst ändern und – falls das Format es verlangt – einen Converter ergänzen können.
Brauche ich Lombok?
Nein, und der Generator erzeugt absichtlich kein @Data oder @Builder. Auf Java 17+ deckt ein record das ab, wofür früher Lomboks @Value da war – ohne Annotation-Prozessor im Build. Die POJO-Ausgabe ist pures Java mit echten Gettern und Settern und kompiliert überall. Verwendet Ihr Projekt bereits Lombok, können Sie die Accessoren selbst austauschen, aber nötig ist das nirgends.
Wird mein JSON hochgeladen?
Nein. Parsen, Typinferenz und Rendern laufen alle in Ihrem Browser – öffnen Sie beim Einfügen das Netzwerk-Panel, und Sie werden sehen, dass nichts gesendet wird. Die Beispiele, die Leute in einen Klassengenerator einfügen, sind meist echte Antworten von einem System, gegen das sie integrieren – genau das Material, das nicht durch einen unbekannten Server sollte.
Welche verwandten Tools sollten Sie als Nächstes nutzen?
- JSON in CSV umwandelnDatensätze in eine Tabelle umwandeln, Verschachtelung inklusive
- CSV in JSON umwandelnTabellen-Export in Datensätze umwandeln, Anführungszeichen inklusive
- JSON in String umwandelnEin Dokument zum Einbetten als String-Literal maskieren
- JSON-Escapes auflösenEin Dokument aus Maskierungen in einer Logzeile zurückholen