Java
2022.06.30
JavaでJSONを操作するには?読み込み・パース・変換方法まとめ
2023.11.10

プログラミングをしていると、「JSON」という言葉を目にする機会が多いですよね。

「JSONってなに?」
「JavaでJSONを読み込んだり、変換したりする方法は?」

といった疑問に対して、本記事ではJavaでJSONを操作する方法について初心者エンジニア向けに詳しく解説していきます。

※本記事で紹介するサンプルコードは、Java18で動作確認しています。

そもそもJSONとは?

JSONとは、「JavaScript Object Notation」の略称で、JavaScriptのオブジェクト記法をベースとしたデータ交換フォーマットのことです。

・構文が単純で可読性が高い
・テキスト形式でデータのやり取りが簡単
・JSONを扱うライブラリが豊富にあり、開発が楽


といった、特徴があります。 

現在ではJavaScriptだけでなく、Java、Python、PHP、C++などさまざまな言語でサポートされています。


JSONについてより詳しく知りたい方は、以下の記事をチェックしてみてください。

①JSONの表記形式

JSONの表記形式を見ていきましょう。記述は { “キー” : ”値” } の形式となっており、キーと値をセットで扱います。

具体的には次のように記述します。

{
    "ID": 1,"Name": "Suzuki","MailAddress": "Suzuki@XXXX.co.jp",
    "ID": 2,"Name": "Matsui","MailAddress": "Matsui@XXXX.co.jp"
}

キーと値をセットで扱うので、簡易的なデータベースとしても使用できます。

2.JavaでJSONを扱うためのライブラリ一覧


JavaでJSONを扱うには、既存ライブラリを使うのが一般的です。ここでは、よく知られているライブラリを紹介します。

ライブラリ名特徴
Jackson処理速度が速くJavaに最適なJSONパーサーのひとつ
GsonGoogle社製のJSONを扱うライブラリ
JSON in JavaJSONデータと、Map型やList型オブジェクトと変換するのが得意なライブラリ
JSON-PJava EE 7で導入された機能

それぞれのライブラリについて解説していきます。

①Jackson

Jacksonは広く使われていて、バージョンアップも頻繁に行われているライブラリです。JacksonでJSONを読み書きするときは、以下のふたつの方法があります。

・JSONのデータ構造と同じクラスを作り、JSONと紐付けて読み書きする
・JsonNode/ObjectNodeを使い、JSONのデータ構造を扱うクラスで読み書きする

②Gson

GsonはGoogle社製のライブラリで、JavaオブジェクトをJSON表現に変換できます。また逆に、JSON文字列をJavaオブジェクトに変換することも可能です。

③JSON in Java

JSON in JavaもJSONデータを簡単に扱えます。Map型やList型のオブジェクトとJSONデータに変換するのが得意なライブラリです。

④JSON-P

Java EE 7で導入された機能です。JSON-Pは、DOM APIと同等のオブジェクトモデルAPIと、Streaming API for XMLと同等の低レベルストリーミングAPIのふたつのAPIを提供しています。

3.JacksonでJSONを使う準備


前述のとおり、JSONを扱うライブラリは豊富にあります。ここからは、広く定着している「Jacksonライブラリ」を使って、JSONを操作する方法を解説していきます。

まずは、JacksonでJSONを使う準備からはじめましょう。

JacksonはJavaの標準APIに含まれていないので、インストールが必要です。インストール方法は、MavenやGradleなどのビルドツールを使う方法と、jarファイルをローカル環境にダウンロードし配置する方法の2通りあります。

ここでは、Mavenを使ってインストールする方法について解説していきます。

①前提条件

Mavanを使用するには、自身の開発環境にMavenをインストール・設定する必要があります。また、eclipseなどの統合開発環境で開発する場合、「Mavenプロジェクト」を選択しプロジェクトを作成すると、効率よく開発できます。

②pom.xmlを編集

Mavenを使う場合、まずはpom.xmlを編集しましょう。pom.xmlとは、「Project Object Model」の略で、プロジェクトの設定をXMLのタグとして記述します。今回はpom.xmlに、依存するライブラリの情報を記述します。

pom.xmlの<dependencies>要素の中に以下のコードを追加しましょう。

<dependency>
    <groupId>com.fasterxml.jackson.core</groupId>
    <artifactId>jackson-databind</artifactId>
    <version>2.13.3</version>
</dependency>

上記コードを追加すると、jackson-databindのほかに、jackson-anootationsとjackson-coreも追加されます。

4.JacksonでJSONを使ってみよう


それでは、JacksonライブラリでJSONを使ってみましょう。JSONデータを扱う際、Javaのクラスにマッピングする方法と、マッピングしない方法があります。ここでは、クラスにマッピングせずに、読み込み・参照する方法を解説します。

①サンプルデータ

この章のサンプルコードでは、以下のJSONデータを使用します。personaldata.jsonというファイル名でdataフォルダに保存します。

{
  "ID": 1,
  "Name": "Suzuki Seiya",
  "Gender": "Man",
  "Age": 24,
  "Physical": {
    "Height": 180.5,
    "Weight": 83.2
  },
  "Grades":[
    {"Year":2019,"Homerun":30},
    {"Year":2020,"Homerun":25},
    {"Year":2021,"Homerun":38}
  ]
}


②JSONファイルの読み込み

まずは、JSONファイルを読み込みます。サンプルコードを確認しましょう。

import java.io.IOException;
import java.nio.file.Paths;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;

public class App {
    public static void main(String[] args) throws JsonProcessingException, IOException  {
        ObjectMapper  objectMapper = new ObjectMapper();
        JsonNode json = objectMapper.readTree(Paths.get("./data/personaldata.json").toFile());
        System.out.println(json); 
    }
}

実行結果

{"ID":1,"Name":"Suzuki Seiya","Gender":"Man","Age":24,"Physical":{"Height":180.5,"Weight":83.2},"Grades":[{"Year":2019,"Homerun":30},{"Year":2020,"Homerun":25},{"Year":2021,"Homerun":38}]}

このプログラムは、ObjectMapperクラスのreadTreeメソッドを使ってJSONファイルを読み込み、JsonNode型のオブジェクトを生成しています。Jacksonでは数値や文字列、配列、オブジェクトなどをJsonNode型として定義できます。

③JSONファイルをパース

パースとは、データを解析し必要なデータを取り出すことです。次のプログラムは、JSONデータから必要なデータを取り出し、Javaプログラムで利用できるようにしています。

import java.io.IOException;
import java.nio.file.Paths;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;

public class App {
    public static void main(String[] args) throws JsonProcessingException, IOException  {
        ObjectMapper  objectMapper = new ObjectMapper();
        JsonNode json = objectMapper.readTree(Paths.get("./data/personaldata.json").toFile());
        
        String name = json.get("Name").textValue();     // Name キーの値を取得
        int age = json.get("Age").intValue();           // Age キーの値を取得
    
        System.out.println("名前:" + name);
        System.out.println("年齢:" + age + "歳");
    }
}

実行結果

名前:Suzuki Seiya
年齢:24歳

JSONファイルの”Name”キーと”Age”キーから値を取得し、出力表示しました。

④JSONファイルの参照

JSONファイルのデータを参照する際、以下のようにデータの形式に合わせてアクセスする必要があります。

String s = json.get("String型").textValue();
int i = json.get("int型").intValue();
double d  = json.get("double型").doubleValue();

また配列への参照は、Key名で参照したあとにインデックスを指定すると、配列値を参照できます。

サンプルコードで確認してみましょう。

import java.io.IOException;
import java.nio.file.Paths;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;

public class App {
    public static void main(String[] args) throws JsonProcessingException, IOException  {
        ObjectMapper  objectMapper = new ObjectMapper();
        JsonNode json = objectMapper.readTree(Paths.get("./data/personaldata.json").toFile());
        // Physical配列の Height keyを取得
        double height = json.get("Physical").get("Height").doubleValue();
        // Physical配列の Weight keyを取得     
        double weight = json.get("Physical").get("Weight").doubleValue();

        // Grades配列の 1件目のHomerun keyを取得
        int homerun19 = json.get("Grades").get(0).get("Homerun").intValue();
        // Grades配列の 2件目のHomerun keyを取得
        int homerun20 = json.get("Grades").get(1).get("Homerun").intValue();
        // Grades配列の 3件目のHomerun keyを取得
        int homerun21 = json.get("Grades").get(2).get("Homerun").intValue();

        System.out.println("身長:" + height + "cm");
        System.out.println("体重:" + weight + "Kg");
        System.out.println("2019年:" + homerun19 + "本");
        System.out.println("2020年:" + homerun20 + "本");
        System.out.println("2021年:" + homerun21 + "本");
    }
}

実行結果

身長:180.5cm
体重:83.2Kg
2019年:30本
2020年:25本
2021年:38本

JSONファイルのGrades配列にインデックス指定することで、配列値を参照できることがわかりますね。

⑤JSONを整形して出力

ObjectMapperクラスのwriterWithDefaultPrettyPrinterメソッドを使用すると、JSONデータがインデントされたフォーマットで出力されます。サンプルコードで確認しましょう。

import java.io.IOException;
import java.nio.file.Paths;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;

public class App {
    public static void main(String[] args) throws JsonProcessingException, IOException  {
        ObjectMapper objectMapper = new ObjectMapper();
        JsonNode json = objectMapper.readTree(Paths.get("./data/personaldata.json").toFile());

        String prettyJson = objectMapper.writerWithDefaultPrettyPrinter().writeValueAsString(json);
        System.out.println(prettyJson);
    }
}

実行結果

{
  "ID" : 1,
  "Name" : "Suzuki Seiya",
  "Gender" : "Man",
  "Age" : 24,
  "Physical" : {
    "Height" : 180.5,
    "Weight" : 83.2
  },
  "Grades" : [ {
    "Year" : 2019,
    "Homerun" : 30
  }, {
    "Year" : 2020,
    "Homerun" : 25
  }, {
    "Year" : 2021,
    "Homerun" : 38
  } ]
}

出力結果がインデントされ、きれいなフォーマットで出力されているのが確認できますね。

5.Jacksonでのさまざまな変換方法

ここからは、Jacksonでのさまざまな変換方法を紹介していきます。

①文字列からJSONへ変換する

プログラム中で作成したJSON形式の文字列を、JSONオブジェクトへ変換するサンプルコードを紹介します。

import java.io.IOException;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;

public class App {
    public static void main(String[] args) throws JsonProcessingException, IOException  {
        //JSON形式の文字列を作成
        String sjson = "{\"ID\": 2, \"Name\": \"Ohtani Shouhei\", \"Gender\": \"Man\", \"Age\": 27}"; 
        ObjectMapper  objectMapper = new ObjectMapper();
        JsonNode json = objectMapper.readTree(sjson);

        String name = json.get("Name").textValue();     // Name keyを取得
        int age = json.get("Age").intValue();           // Age keyを取得
    
        System.out.println("名前:" + name);
        System.out.println("年齢:" + age + "歳");
    }
}

実行結果

名前:Ohtani Shouhei
年齢:27歳

「4-①JSONファイルの読み込み」と同じ方法で変換できることがわかりますね。

②JSONから文字列へ変換する

JSONオブジェクトから文字列へ変換するサンプルコードです。

import java.io.IOException;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;

public class App {
    public static void main(String[] args) throws JsonProcessingException, IOException  {
        String sjson = "{\"ID\": 2, \"Name\": \"Ohtani Shouhei\", \"Gender\": \"Man\", \"Age\": 27}"; 
        ObjectMapper  objectMapper = new ObjectMapper();
        JsonNode json = objectMapper.readTree(sjson);

        System.out.println(json.toString());
        System.out.println(json.toPrettyString());
    }
}

実行結果

{"ID":2,"Name":"Ohtani Shouhei","Gender":"Man","Age":27}
{
  "ID" : 2,
  "Name" : "Ohtani Shouhei",
  "Gender" : "Man",
  "Age" : 27
}

toStringは、JSONオブジェクトを1行の文字列に変換します。

toPrettyStringは、JSONオブジェクトを改行されたきれいなフォーマットで文字列に変換します。

③JSONからJavaオブジェクトに変換する(decode)

Jacksonは、JSONからJavaオブジェクトに変換するメソッドを備えています。サンプルコードで確認してみましょう。

import java.io.IOException;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;

class BaseballPlayer{
    public int ID;
    public String Name;
    public String Gender;
    public int Age;
}

public class App {
    public static void main(String[] args) throws JsonProcessingException, IOException  {
        String sjson = "{\"ID\": 2, \"Name\": \"Ohtani Shouhei\", \"Gender\": \"Man\", \"Age\": 27}"; 
        ObjectMapper  objectMapper = new ObjectMapper();
        BaseballPlayer player = objectMapper.readValue(sjson, BaseballPlayer.class);
        System.out.println(player.Name + ", " + player.Gender + ", " + player.Age);
    }
}

実行結果

Ohtani Shouhei, Man, 27

ObjectMapperクラスのreadValueメソッドを使い、JSONオブジェクトからBaseballPlayerオブジェクトを生成しています。


このようにObjectMapperクラスを使用すると、簡単にクラスオブジェクトを生成できます。

④JavaオブジェクトからJSONに変換する(encode)

ここでは逆に、JavaオブジェクトからJSONに変換する方法を紹介します。サンプルコードを見てみましょう。

import java.io.IOException;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.SerializationFeature;

class BaseballPlayer{
    public int ID;
    public String Name;
    public String Gender;
    public int Age;
}

public class App {
    public static void main(String[] args) throws JsonProcessingException, IOException  {
        BaseballPlayer player = new BaseballPlayer();
        player.ID = 3;
        player.Name = "Maeda Kenta";
        player.Gender = "Man";
        player.Age = 34;
        
        ObjectMapper objectMapper = new ObjectMapper();
        objectMapper.enable(SerializationFeature.INDENT_OUTPUT);

        String sjson = objectMapper.writeValueAsString(player);
        System.out.println(sjson);
    }
}

実行結果

{
  "ID" : 3,
  "Name" : "Maeda Kenta",
  "Gender" : "Man",
  "Age" : 34
}

ObjectMapperクラスのwriteValueAsStringメソッドを使い、JavaクラスからJSONデータを生成し、出力表示しています。その際ObjectMapperクラスのenableメソッドを使っているので、JSONデータが整った形式で表示されています。

⑤配列JSONからListに変換する

Jacksonを使って、配列JSONをListに変換する方法を紹介します。

import java.io.IOException;
import java.util.Arrays;
import java.util.List;
import com.fasterxml.jackson.core.JsonProcessingException;
import com.fasterxml.jackson.databind.ObjectMapper;

class BaseballPlayer{
    public int ID;
    public String Name;
    public String Gender;
    public int Age;
}

public class App {
    public static void main(String[] args) throws JsonProcessingException, IOException  {
        String array_json = "" + 
        " [ " +
           " {\"ID\": 1, \"Name\": \"Suzuki Seiya\", \"Gender\": \"Man\", \"Age\": 27}," +
           " {\"ID\": 2, \"Name\": \"Ohtani Shouhei\", \"Gender\": \"Man\", \"Age\": 27}," +
           " {\"ID\": 3, \"Name\": \"Maeda Kenta\", \"Gender\": \"Man\", \"Age\": 34} " +
         " ] " +
          ""; 
        
        ObjectMapper  objectMapper = new ObjectMapper();

        List<BaseballPlayer> players = Arrays.asList(objectMapper.readValue(array_json, BaseballPlayer[].class));
        for (BaseballPlayer player : players) {
            System.out.println(player.Name + ", " + player.Gender + ", " + player.Age);
        }
    }
}

実行結果

Suzuki Seiya, Man, 27
Ohtani Shouhei, Man, 27
Maeda Kenta, Man, 34

サンプルコードは、プログラム中で配列JSONを作成しています。ObjectMapperクラスのreadValueメソッドを使って配列JSONを読み込み、Arrays.asListメソッドでリスト化しています。

この記事をシェア