Jackson @JsonInclude(JsonInclude.Include.NON_NULL)と同等のGson

Sep 28 2020

これは実際にはこの質問のフォローアップです。Gson/ JacksonとSpringBootを使用してnullにする代わりに、フィールドプロパティなしでDTOクラスを再作成します。私はもともとGsonで動作するように投稿しましたが、Jacksonでしか実行でき@JsonInclude(JsonInclude.Include.NON_NULL)ませんでしたが、Gsonでこれに相当するものを見つけることができなかったため、プロジェクトのライブラリとして保持できます。

@JsonIncludeアノテーションを付けた@Expose(serialise = false、deserialise = false)を使用してみました。または、Gsonがデフォルトでそれを無視すると考えていたため、そのフィールドをnullに設定しましたが、そうではないようです。

最後に、@ Exposeアノテーションをから完全に削除して、Gsonがそれを無視するが、機能しないかどうかを確認しようとしました。

ここに問題の主要部分を貼り付けるだけでなく、元の投稿に追加された追加の詳細を保持します。

@Service
public class CategoryQueryServiceImpl implements CategoryQueryService {

@Autowired
private CategoryRepository categoryRepository;

@Autowired
private ReportRepository reportRepository;

ObjectMapper mapper = new ObjectMapper();

@Override
public CategoryQueryDto getCategory(UUID id) throws JsonProcessingException {

    if (categoryRepository.findById(id).isPresent()) {
        Category category = categoryRepository.findById(id).get();

        CategoryQueryDto categoryQueryDto = new CategoryQueryDto(category.getId(), category.getTitle());

          Gson gson = new GsonBuilder().excludeFieldsWithoutExposeAnnotation().create();
          String converter = gson.toJson(categoryQueryDto);
          categoryQueryDto = gson.fromJson(converter, CategoryQueryDto.class);


        // Jackson
        //String converter = mapper.writeValueAsString(categoryQueryDto);

        //categoryQueryDto = mapper.readValue(converter, CategoryQueryDto.class);


        return categoryQueryDto;


    } else {
        return null;
    }

}


@AllArgsConstructor
@NoArgsConstructor
@Data
public class CategoryQueryDto {

@Expose()
private UUID id;
@Expose()
private String title;

// Jackson
// @JsonInclude(JsonInclude.Include.NON_NULL)
private List<ReportQueryDto> reports = null;

public CategoryQueryDto(UUID id, String title) {
    this.id = id;
    this.title = title;
}

}

誰かがこれを行う方法について他のアイデアを持っている場合はお願いします。どうもありがとうございました。

回答

1 anuragsaxena Sep 28 2020 at 16:43

nullフィールドをシリアル化しないでください(これはGsonシリアル化のデフォルトの動作です)

Employee employeeObj = new Employee(1, "John", "Smith", null);
                 
Gson gson = new GsonBuilder()
        .setPrettyPrinting()
        .create(); 
 
System.out.println(gson.toJson(employeeObj));

出力:

{
  "id": 1,
  "firstName": "John",
  "lastName": "Smith"
}

nullフィールドのシリアル化(JSON出力にnull値が含まれるカスタムGsonシリアル化)

Employee employeeObj = new Employee(1, "John", "Smith", null);
                 
Gson gson = new GsonBuilder()
        .setPrettyPrinting()
        .serializeNulls()
        .create(); 
 
System.out.println(gson.toJson(employeeObj));

出力:

{
  "id": 1,
  "firstName": "John",
  "lastName": "Smith",
  "emailId": null
}
FrancislainyCampos Sep 29 2020 at 03:27

Spring Bootはデフォルトのシリアル化ライブラリとしてJacksonを使用しているため、Gsonのデフォルトの動作は行われていなかったようです。application.propertiesファイル内に以下の行を貼り付けてこれを上書きすると、問題が修正されました。

spring.mvc.converters.preferred-json-mapper=gson