TL;DR
-
Jackson
を使うことで、単純に文字列では比較できないJSON
も比較できる- 単なる一致チェックにとどまらず、柔軟な比較も可能
やりたいこと
以下のような、期待値のJSON
が有ったとします。
expected.json
{
"foo": "foo",
"bar": 1,
"baz": true
}
一方で、Java
上で得られるJSON
は以下のような形式だったとします。
String actual = "{\"bar\":1,\"baz\":true,\"foo\":\"foo\"}";
このような場合に、この2つがJSON
として等しいことをテストします1。
やり方
題の通り、Jackson
を使ったやり方を紹介します。
Jackson
ではreadTree
でJsonNode
という型を読み出せます。
これはequals
を実装しているため、単純比較は特別な処理を書かなくても可能です。
import com.fasterxml.jackson.databind.JsonNode;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.junit.jupiter.api.Test;
import java.io.FileInputStream;;
import java.io.IOException;
import static org.junit.jupiter.api.Assertions.assertEquals;
public class JacksonJsonTest {
@Test
void test() throws IOException {
ObjectMapper mapper = new ObjectMapper();
String actual = "{\"bar\":1,\"baz\":true,\"foo\":\"foo\"}";
JsonNode actualNode = mapper.readTree(actual);
// ファイルからの期待値JSON読み込み
JsonNode expectedNode = mapper.readTree(new FileInputStream("src/test/resources/expected.json"));
assertEquals(expectedNode, actualNode);
}
}
このやり方の利点
調べた限り、このような比較を行うためのテスト用ライブラリなども有りそうでした。
それらに比べてJackson
が優れているのは、Spring
等にデフォルトで導入されている点です。
JSON
に関して何か処理が必要になった場合はまず導入されているJSON
ライブラリで実現できないかから確認することをお勧めします。
また、JsonNode
に実装されている関数を応用することで、ファジーな値比較や、特定プロパティのみの比較、特定プロパティの無視といった柔軟な比較も可能です。
このような機能性も利点の一つです。
-
具体的には、大きな
JSON
の出力結果をテストする際に、期待値は整形済みJSON
で管理したいが、出力は整形できないという状況で、この方法で比較を行いました。 ↩