重新创建不带字段 属性 的 DTO class,而不是使用 Gson/Jackson 和 Spring 引导将其设置为空

Recreate DTO class without field property instead of having it null using Gson/Jackson and Spring Boot

我有一个 DTO class returns 这个:

{
  "id": "fdbfb1ec-1f1e-4867-9cc8-73929fbcc07e",
  "title": "My another category",
  "reports": null
}

当我实际上希望我的某些 api 调用不包含报告密钥时,如下所示,而不是将其设置为空。

{
  "id": "fdbfb1ec-1f1e-4867-9cc8-73929fbcc07e",
  "title": "My another category",
}

我曾尝试使用 Gson 和 Expose 注释,认为这会删除我的密钥,但它似乎只是将其变为 null。我尝试使用 @Expose(serialize = false, deserialize = false) 或不带注释,因为我的 Gson 对象使用 excludeFieldsWithoutExposeAnnotation() 片段,但两者都给我相同的结果。但是,我可以看到我的字符串转换器排除了 reports 键并给我这个 {"id":"fdbfb1ec-1f1e-4867-9cc8-73929fbcc07e","title":"My another category"} 但不确定为什么 属性 在重新创建对象时仍然存在,如果这种情况的唯一解决方案不是通过 Gson 但有两个完全不同的 DTO,一个有 属性 而另一个没有?

@AllArgsConstructor
@NoArgsConstructor
@Data
public class CategoryQueryDto {

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

    @Expose(serialize = false, deserialize = false)
    private List<ReportQueryDto> reports;

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

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

}


@Override
public CategoryQueryDto getCategory(UUID id) {

    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);


        return categoryQueryDto;
    } else {
        return null;
    }

}

非常感谢。

更新

这是我在 Github https://github.com/francislainy/gatling_tool_backend

上的代码

尝试使用 Jackson 而不是 Gson 并遇到了同样的问题。

在我想显示的字段上使用 @JsonInclude(JsonInclude.Include.NON_NULL) 只有在不为 null 且有效时才显示。

@AllArgsConstructor
@NoArgsConstructor
@Data
public class CategoryQueryDto {

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

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

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

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

}

这是我和 Jackson 的控制器

@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());

        
        String converter = mapper.writeValueAsString(categoryQueryDto);

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


        return categoryQueryDto;


    } else {
        return null;
    }

}

POM

<dependency>
     <groupId>org.codehaus.jackson</groupId>
     <artifactId>jackson-core-asl</artifactId>
     <version>1.9.13</version>
     <scope>test</scope>
</dependency>