2016年3月8日火曜日

[Jackson]Java8のDate and Time APIを使ってみる

JacksonでJava8のDate and Time APIを扱うためには、依存ライブラリにjackson-datatype-jsr310を追加し、
モジュールをObjectMapperに登録する必要があります。

このモジュールを使わなかった場合、Date and Time APIのクラスのプロパティの値が、
Jsonのプロパティとして出力されるので非常に残念な結果となります。

ライブラリの追加

Gradleの場合には、以下のようになります。
compile 'com.fasterxml.jackson.datatype:jackson-datatype-jsr310:2.7.2'

モジュールの追加

ObjectMapperのregisterModuleメソッドを使って、JavaTimeModuleを登録します。
final ObjectMapper objectMapper = new ObjectMapper();
objectMapper.registerModule(new JavaTimeModule());

実行結果

下のコードを使ってLocalDate型の値をシリアライズします。
final ObjectMapper objectMapper = new ObjectMapper();
objectMapper.registerModule(new JavaTimeModule());
System.out.println(objectMapper.writeValueAsString(LocalDate.now()));

実行結果は、以下のようになります。年月日が配列の各要素に分解されてシリアライズされます。
[ 2016, 3, 8 ]

シリアライズ時のフォーマットを変更する

シリアライズ時のフォーマットを変更する場合にはJavaTimeModuleを使わずに
jackson-datatype-jsr310に含まれるシリアライザーを直接使います。

[Jackson]特定の型に対してカスタムなシリアライザを設定する
と同じようにSimpleMoculeを使って、任意のシリアライザーを登録します。

今回は、LocalDateを使うのでjackson-datatype-jsr310に含まれるLocalDateSerializerを登録します。
LocalDateSerializerは、シリアライズ時に行うフォーマットを指定することができるのでDateTimeFormatterを使ってフォーマットを指定ます。
final ObjectMapper objectMapper = new ObjectMapper();

SimpleModule module = new SimpleModule();

// formatを指定してLocalDateSerializerを登録する。
module.addSerializer(new LocalDateSerializer(DateTimeFormatter.ofPattern("yyyyMMdd")));
objectMapper.registerModule(module);

System.out.println(objectMapper.writeValueAsString(LocalDate.now()));

実行すると以下のように指定したフォーマットでシリアライズされます。
"20160308"