愛と勇気と缶ビール

ふしぎとぼくらはなにをしたらよいか

JacksonでJSONの一部だけdeserializeさせないための設定

リクエストボディで受け取ったJSON全体はオブジェクトにマッピングして欲しいけどもその一部分だけJSON文字列そのままにしておいて欲しい(= デシリアライズして欲しくない)というケースがある。例えば、JSON-RPCを実装していてparamsの型がmethod依存で変わってしまうような場合。

こうやって

import com.fasterxml.jackson.core.JsonParser;                                                                            
import com.fasterxml.jackson.databind.DeserializationContext;                                                                           
import com.fasterxml.jackson.databind.JsonDeserializer;

public class KeepAsJsonDeserializer extends JsonDeserializer<String> {                                                                                                                                                                                                            
    @Override                                                                                                                            
    public String deserialize(@NotNull JsonParser p, DeserializationContext ctxt) throws IOException {                                   
        return p.getCodec().readTree(p).toString();                                                                                      
    }                                                                                                                                    
}  

こうする

import com.fasterxml.jackson.databind.annotation.JsonDeserialize;

public class JSONRPCRequest {                                                                                                            
    String jsonrpc;                                                                                                                      
    String method;                                                                                                                       
    int id;                                                                                                                              
    @JsonDeserialize(using = KeepAsJsonDeserializer.class)                                                                               
    String params;                                                                                                                       
}     

よかったですね。