首页 文章

具有Spring Data Rest功能的Custom Spring MVC HTTP Patch请求

提问于
浏览
5

在自定义Spring MVC控制器中支持HTTP PATCH的最佳实践是什么?特别是在使用HATEOAS / HAL时?是否有更简单的方法来合并对象,而无需检查请求json(或编写和维护DTO)中是否存在每个字段,理想情况下是自动解组资源链接?

我知道Spring Data Rest中存在此功能,但是可以将其用于自定义控制器吗?

1 回答

  • 9

    我认为你不能在这里使用spring-data-rest功能 .

    spring-data-rest在内部使用json-patch库 . 基本上我认为工作流程如下:

    • 读取您的实体

    • 使用objectMapper将其转换为json

    • 应用补丁(这里需要json-patch)(我认为你的控制器应该把JsonPatchOperation列表作为输入)

    • 将修补后的json合并到您的实体中

    我认为困难的部分是第四点 . 但是,如果您不必拥有通用解决方案,那么可能会更容易 .

    如果你想了解一下spring-data-rest的作用 - 请看 org.springframework.data.rest.webmvc.config.JsonPatchHandler

    EDIT

    spring-data-rest中的补丁机制在最新的版本中发生了显着变化 . 最重要的是,它不再使用json-patch库,现在从头开始实现json补丁支持 .

    我可以设法在自定义控制器方法中重用主要补丁功能 .

    以下代码段说明了基于spring-data-rest 2.6的方法

    import org.springframework.data.rest.webmvc.IncomingRequest;
            import org.springframework.data.rest.webmvc.json.patch.JsonPatchPatchConverter;
            import org.springframework.data.rest.webmvc.json.patch.Patch;
    
            //...
            private final ObjectMapper objectMapper;
            //...
    
            @PatchMapping(consumes = "application/json-patch+json")
            public ResponseEntity<Void> patch(ServletServerHttpRequest request) {
              MyEntity entityToPatch = someRepository.findOne(id)//retrieve current state of your entity/object to patch
    
              Patch patch = convertRequestToPatch(request);
              patch.apply(entityToPatch, MyEntity.class);
    
              someRepository.save(entityToPatch);
              //...
            }      
    
            private Patch convertRequestToPatch(ServletServerHttpRequest request) {  
              try {
                InputStream inputStream =  new IncomingRequest(request).getBody();
                return new JsonPatchPatchConverter(objectMapper).convert(objectMapper.readTree(inputStream));
              } catch (IOException e) {
                throw new UncheckedIOException(e);
              }
            }
    

相关问题