JavaでのPretty-Print JSON


217

私は使っています そして、私はJSONデータをきれいに出力する必要があります(より人間が読めるようにします)

そのライブラリ内でこの機能を見つけることができませんでした。これは通常どのように達成されますか?

回答:


284

GSONはこれを適切な方法で実行できます。

Gson gson = new GsonBuilder().setPrettyPrinting().create();
JsonParser jp = new JsonParser();
JsonElement je = jp.parse(uglyJSONString);
String prettyJsonString = gson.toJson(je);

1
文字列を解析してJsonElementにするコードを含めました。通常は、JSONデータを使用して実行する以前の作業からすでに取得しています。ただし、使用方法を明確にするために、ここに含めたかったのです。
Ray Hulha、2014

この答えは私を助けたので。これがあなたが探しているものであれば、このステートメントをより少ない行に縮小するために、以下のコードを追加しました。public String prettifyJson(String json){JsonElement jsonElement = new JsonParser()。parse(json); 新しいGsonBuilder()。setPrettyPrinting()。create()。toJson(jsonElement);を返します。}
ahmad 2015

2
Rhinoに組み込まれたJSONパーサー(JDK 1.7以降)にアクセスするだけなので、追加のライブラリーを必要とせずにOPの質問に答えることができます。デバッグ出力をフォーマットするためだけにプロジェクトにライブラリを追加することは望ましくないと思います。 scriptEngine.eval("result = JSON.stringify(JSON.parse(jsonString), null, 2)");
アグネス

1
org.jsonの代替とは対照的に、GSONのきれいな印刷方法では、変換後に要素の順序がそのまま維持されます。
Aydin K.

1
へのポインタをありがとう。GsonBuilder使用しgson.toJson(object)ていたので、インスタンス化をからGson gson = new Gson();に変更するだけGson gson = new GsonBuilder().setPrettyPrinting().create(); で、コードは引き続き機能しましたが、オブジェクトを1行ではなくきれいに出力しました。
19

153

私はorg.json組み込みメソッドを使用して、データをきれいに出力しました。

JSONObject json = new JSONObject(jsonString); // Convert text to object
System.out.println(json.toString(4)); // Print it with specified indentation

JSONのフィールドの順序は、定義ごとにランダムです。特定の順序は、パーサーの実装の影響を受けます。


7
他の回答が示唆するように追加の依存関係をインポートする必要がないので、私もこのソリューションを好みます。
gdrt 2017

3
重要なインポートがない-import org.json.JSONObject;
MasterJoe2 2018年

とにかく、フィールドをランダムな順序で配置しないようにするには、追加した順にしたいですか?
Thomas Adrian

@ThomasAdrian org.json.JSONObjectでは不可能です。
Raghu Kiran

Underscore-javaは、jsonのフォーマット中に属性の順序を保持します。
Valentyn Kolesnikov

37

GSONはこれをサポートしているようですが、使用しているライブラリから切り替えるかどうかはわかりません。

ユーザーガイドから:

Gson gson = new GsonBuilder().setPrettyPrinting().create();
String jsonOutput = gson.toJson(someObject);

4
GSONの問題は複雑で、json-simpleの方がはるかに簡単です。
mabuzer

1
私はこの問題を1年以上調べていませんが、ソースコードを少し変更する場合は、code.google.com / p / json-simple / issues / detail?id = 22にいくつかの情報があります。 pretty-printでjson-simpleを拡張します。
BuffaloBuffalo

きれいな印刷フォーマットなしで文字列だけを取得:(
Cherry

文字列を\ r \ nで出力します
Stone Jack

ありがとう。toString()オーバーライドを1行で:new GsonBuilder()。setPrettyPrinting()。create()。toJson(this);
KeepAtIt

30

ジャクソンと(com.fasterxml.jackson.databind):

ObjectMapper mapper = new ObjectMapper();
System.out.println(mapper.writerWithDefaultPrettyPrinter().writeValueAsString(jsonObject))

From:プリティプリントのJSON出力を有効にする方法(Jackson)

私はこれがすでに回答に含まれていることを知っていますが、可能性として、依存関係としてすでにジャクソンを持っているため、必要なのは追加のコード行だけなので、ここで個別に書きたいと思います


21

JSON処理(JSR-353)実装にJava APIを使用している場合はJsonGenerator.PRETTY_PRINTING、を作成するときにプロパティを指定できますJsonGeneratorFactory

次の例は、もともと私のブログ投稿で公開されています。

import java.util.*;
import javax.json.Json;
import javax.json.stream.*;

Map<String, Object> properties = new HashMap<String, Object>(1);
properties.put(JsonGenerator.PRETTY_PRINTING, true);
JsonGeneratorFactory jgf = Json.createGeneratorFactory(properties);
JsonGenerator jg = jgf.createGenerator(System.out);

jg.writeStartObject()                    // {
    .write("name", "Jane Doe")           //    "name":"Jane Doe",
    .writeStartObject("address")         //    "address":{
        .write("type", 1)                //        "type":1,
        .write("street", "1 A Street")   //        "street":"1 A Street",
        .writeNull("city")               //        "city":null,
        .write("verified", false)        //        "verified":false
    .writeEnd()                          //    },
    .writeStartArray("phone-numbers")    //    "phone-numbers":[
        .writeStartObject()              //        {
            .write("number", "555-1111") //            "number":"555-1111",
            .write("extension", "123")   //            "extension":"123"
        .writeEnd()                      //        },
        .writeStartObject()              //        {
            .write("number", "555-2222") //            "number":"555-2222",
            .writeNull("extension")      //            "extension":null
        .writeEnd()                      //        }
    .writeEnd()                          //    ]
.writeEnd()                              // }
.close();

18

私の状況は、私のプロジェクトが、きれいな印刷をサポートしないレガシー(非JSR)JSONパーサーを使用していることです。ただし、きれいに印刷されたJSONサンプルを作成する必要がありました。これは、Java 7以降を使用している限り、追加のライブラリを追加しなくても可能です。

ScriptEngineManager manager = new ScriptEngineManager();
ScriptEngine scriptEngine = manager.getEngineByName("JavaScript");
scriptEngine.put("jsonString", jsonStringNoWhitespace);
scriptEngine.eval("result = JSON.stringify(JSON.parse(jsonString), null, 2)");
String prettyPrintedJson = (String) scriptEngine.get("result");

3
これは
素晴らしく

警告:ScriptEngineManagerはAPIではありません。
-nclark


8

既存の回答のほとんどは、外部ライブラリに依存しているか、特別なJavaバージョンが必要です。以下は、一般的なJava APIのみを使用してJSON文字列をきれいに出力する単純なコードです(Java 7以降で利用可能です。ただし、古いバージョンは試していません)。

基本的な考え方は、JSONの特殊文字に基づいてフォーマットをタイガーすることです。たとえば、 '{'または '['が確認された場合、コードは新しい行を作成し、インデントレベルを上げます。

免責事項:私はこれをいくつかの単純なJSONケース(基本的なキーと値のペア、リスト、ネストされたJSON)に対してのみテストしたので、引用符を含む文字列値や特殊文字(\ n、\ tなど)。

/**
 * A simple implementation to pretty-print JSON file.
 *
 * @param unformattedJsonString
 * @return
 */
public static String prettyPrintJSON(String unformattedJsonString) {
  StringBuilder prettyJSONBuilder = new StringBuilder();
  int indentLevel = 0;
  boolean inQuote = false;
  for(char charFromUnformattedJson : unformattedJsonString.toCharArray()) {
    switch(charFromUnformattedJson) {
      case '"':
        // switch the quoting status
        inQuote = !inQuote;
        prettyJSONBuilder.append(charFromUnformattedJson);
        break;
      case ' ':
        // For space: ignore the space if it is not being quoted.
        if(inQuote) {
          prettyJSONBuilder.append(charFromUnformattedJson);
        }
        break;
      case '{':
      case '[':
        // Starting a new block: increase the indent level
        prettyJSONBuilder.append(charFromUnformattedJson);
        indentLevel++;
        appendIndentedNewLine(indentLevel, prettyJSONBuilder);
        break;
      case '}':
      case ']':
        // Ending a new block; decrese the indent level
        indentLevel--;
        appendIndentedNewLine(indentLevel, prettyJSONBuilder);
        prettyJSONBuilder.append(charFromUnformattedJson);
        break;
      case ',':
        // Ending a json item; create a new line after
        prettyJSONBuilder.append(charFromUnformattedJson);
        if(!inQuote) {
          appendIndentedNewLine(indentLevel, prettyJSONBuilder);
        }
        break;
      default:
        prettyJSONBuilder.append(charFromUnformattedJson);
    }
  }
  return prettyJSONBuilder.toString();
}

/**
 * Print a new line with indention at the beginning of the new line.
 * @param indentLevel
 * @param stringBuilder
 */
private static void appendIndentedNewLine(int indentLevel, StringBuilder stringBuilder) {
  stringBuilder.append("\n");
  for(int i = 0; i < indentLevel; i++) {
    // Assuming indention using 2 spaces
    stringBuilder.append("  ");
  }
}

最初に読んだとき、私はこの提案に非常に不満でしたが、すべての回答を読んだ後、これが最良の解決策です。少なくとも、デバッグ出力のためだけのものであり、依存関係をドラッグしたくない場合は、後で削除することをお勧めします。どうもありがとうございました!
user2081279

7

1行で:

String niceFormattedJson = JsonWriter.formatJson(jsonString)

json-io libray(https://github.com/jdereg/json-io)は、JDK以外の依存関係のない小さな(75K)ライブラリです。

きれいに出力されるJSONに加えて、Javaオブジェクト(サイクルを含むJavaオブジェクトグラフ全体)をJSONにシリアル化したり、それらを読み込んだりできます。


7

これは、JSONLibライブラリで実現できます。

http://json-lib.sourceforge.net/apidocs/net/sf/json/JSONObject.html

toString(int indentationFactor)標準のtoString()方法ではなく、多重定義された方法を使用する場合(かつその場合のみ)。

次のバージョンのAPIでこれを確認しました。

<dependency>
  <groupId>org.json</groupId>
  <artifactId>json</artifactId>
  <version>20140107</version>
</dependency>

3
このライブラリーは質問に答えるのに役立つかもしれませんが、それがどのように機能するかに関するいくつかの説明とともに、問題にどのように適用できるかのを含めることはより良いでしょう。
Francesco Menzani 2015

1
フィードバックに感謝します。覚えていますが、私のような人々はボランティアであり、品質基準を満たすことを保証するサービスを提供するために報酬を受け取っていません。仕事の途中や家族で仕事をしていることが多いため、時間は限られています。そのため、読者は「編集」できるので、お互いの投稿をより役立つものにすることができます。
Sridhar Sarnobat

6

JSON-P 1.0仕様(JSR-353)に従うと、特定のJsonStructureJsonObjectまたはJsonArray)のより最新のソリューションは次のようになります。

import java.io.StringWriter;
import java.util.HashMap;
import java.util.Map;

import javax.json.Json;
import javax.json.JsonStructure;
import javax.json.JsonWriter;
import javax.json.JsonWriterFactory;
import javax.json.stream.JsonGenerator;

public class PrettyJson {

    private static JsonWriterFactory FACTORY_INSTANCE;

    public static String toString(final JsonStructure status) {

        final StringWriter stringWriter = new StringWriter();

        final JsonWriter jsonWriter = getPrettyJsonWriterFactory()
                .createWriter(stringWriter);

        jsonWriter.write(status);
        jsonWriter.close();

        return stringWriter.toString();
    }

    private static JsonWriterFactory getPrettyJsonWriterFactory() {
        if (null == FACTORY_INSTANCE) {
            final Map<String, Object> properties = new HashMap<>(1);
            properties.put(JsonGenerator.PRETTY_PRINTING, true);
            FACTORY_INSTANCE = Json.createWriterFactory(properties);
        }
        return FACTORY_INSTANCE;
    }

}


5

以下のようにGsonを使用できます

Gson gson = new GsonBuilder().setPrettyPrinting().create();
String jsonString = gson.toJson(object);

投稿から、Gsonを使用したJSONプリティプリント

または、以下のようにジャクソンを使用できます

ObjectMapper mapper = new ObjectMapper();
String perttyStr = mapper.writerWithDefaultPrettyPrinter().writeValueAsString(object);

投稿からプリティプリントJSON in Java(Jackson)

この助けを願っています!


4

org jsonを使用します。参照リンク

JSONObject jsonObject = new JSONObject(obj);
String prettyJson = jsonObject.toString(4);

Gsonの使用。参照リンク

Gson gson = new GsonBuilder().setPrettyPrinting().create();
String json = gson.toJson(obj);

ジャクソンの使用。参照リンク

ObjectMapper mapper = new ObjectMapper();
mapper.enable(SerializationFeature.INDENT_OUTPUT);
String json = mapper.writeValueAsString(obj);

Gensonを使用する。参照リンク

Genson prettyGenson = new GensonBuilder().useIndentation(true).create();
String prettyJson = prettyGenson.serialize(obj);

1

ジャクソンを使用してこれは私のために働きました:

mapper.writerWithDefaultPrettyPrinter().writeValueAsString(JSONString)

これmapperはどこから来たのですか?
Sertage

0

小さなjsonライブラリを使用できます

String jsonstring = ....;
JsonValue json = JsonParser.parse(jsonstring);
String jsonIndendedByTwoSpaces = json.toPrettyString("  ");

-2

Underscore-javaには静的メソッドがありU.formatJson(json)ます。2、3、4、タブ、コンパクトの5つのフォーマットタイプがサポートされています。私はプロジェクトのメンテナーです。実例

import com.github.underscore.lodash.U;

import static com.github.underscore.lodash.Json.JsonStringBuilder.Step.TABS;
import static com.github.underscore.lodash.Json.JsonStringBuilder.Step.TWO_SPACES;

public class MyClass {

    public static void main(String args[]) {
        String json = "{\"Price\": {"
        + "    \"LineItems\": {"
        + "        \"LineItem\": {"
        + "            \"UnitOfMeasure\": \"EACH\", \"Quantity\": 2, \"ItemID\": \"ItemID\""
        + "        }"
        + "    },"
        + "    \"Currency\": \"USD\","
        + "    \"EnterpriseCode\": \"EnterpriseCode\""
        + "}}";
        System.out.println(U.formatJson(json, TWO_SPACES)); 
        System.out.println(U.formatJson(json, TABS)); 
    }
}

出力:

{
  "Price": {
    "LineItems": {
      "LineItem": {
        "UnitOfMeasure": "EACH",
        "Quantity": 2,
        "ItemID": "ItemID"
      }
    },
    "Currency": "USD",
    "EnterpriseCode": "EnterpriseCode"
  }
}
{
    "Price": {
        "LineItems": {
            "LineItem": {
                "UnitOfMeasure": "EACH",
                "Quantity": 2,
                "ItemID": "ItemID"
            }
        },
        "Currency": "USD",
        "EnterpriseCode": "EnterpriseCode"
    }
}    
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.