【问题标题】:Spring boot response body is showing empty in PostManSpring Boot 响应正文在 PostMan 中显示为空
【发布时间】:2021-10-04 19:57:31
【问题描述】:

我正在使用@Valid 注释来验证我的一些模型属性。它按预期工作,如果未按预期提供任何数据,则会返回 400 Bad Request 错误。但是响应正文总是空的。

我的控制器类

import java.util.ArrayList;
import java.util.List;

import javax.validation.Valid;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.DeleteMapping;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.PutMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;

import com.bnpp.leavemanagement.exception.DepartmentNotFoundException;
import com.bnpp.leavemanagement.exception.EmployeeAlreadyExistsException;
import com.bnpp.leavemanagement.exception.EmployeeNotFoundException;
import com.bnpp.leavemanagement.model.EmployeeModel;
import com.bnpp.leavemanagement.service.EmployeeService;

@RestController
@Validated
@RequestMapping("/employee")
public class EmployeeController 
{
    @Autowired
    EmployeeService empService;
    
    
    @PostMapping("/create")
    public ResponseEntity<EmployeeModel> createEmployee(@RequestBody @Valid EmployeeModel empNew) throws  EmployeeAlreadyExistsException, DepartmentNotFoundException, EmployeeNotFoundException
    {
        EmployeeModel resEmp = empService.addEmployee(empNew);
        return new ResponseEntity( resEmp, HttpStatus.CREATED);
    }

模型类属性

  @JsonProperty("firstName")
  @NotEmpty(message = "FirstName cannot be empty")
  private String firstName = null;

application.properties

spring.datasource.url=jdbc:h2:mem:leavemgmt
spring.datasource.driverClassName=org.h2.Driver
spring.datasource.username=sa
spring.datasource.password=
spring.jpa.database-platform=org.hibernate.dialect.H2Dialect
spring.h2.console.enabled=true

server.port=8443

server.ssl.key-alias=leavemanagement
server.ssl.key-store=classpath:leavemanagement.jks
server.ssl.key-store-type=JKS
server.ssl.key-store-password=password

server.error.include-message=always
server.error.include-binding-errors=always
server.error.include-exception=true
server.error.include-stacktrace=always

请帮助我了解如何在任何验证失败时在 Postman 中获取响应正文。

【问题讨论】:

  • 也分享你的服务层,
  • 也共享服务和存储库类
  • 对于初学者,请从不需要的控制器中删除 @Validated。方法参数上的@Valid 就足够了。
  • 我已按照指示从控制器中删除了@Validated,但场景仍然保持不变

标签: java spring spring-boot exception


【解决方案1】:

您需要在您的控制器中使用BindingResult 在您的响应中添加错误,如下所示:

 public ResponseEntity<EmployeeModel> createEmployee(@Valid @RequestBody EmployeeModel empNew,BindingResult bindingResult)
{
  if(bindingResult.hasErrors())
   {
     for(FieldError fieldError : bindingResult.getFieldErrors()) {
            //you can define your ErrorMOdel dto here and add  
          //fieldError properties then add the whole errorList in 
          //your response.
         //Finally, return the response from here
        }
   }

  //if there is no errors in your request: execute this part:
   EmployeeModel resEmp = empService.addEmployee(empNew);
        return new ResponseEntity( resEmp, HttpStatus.CREATED);

}

根据您的需要更新:
你可以这样定义你的EmployeeModel

public class EmployeeModel<T> implements Serializable
{
  //your previously defined entities here
     private List<T> errorList;  //this is new one to show errors

    //constructors, setters, getters
}

现在,当您遇到错误时,将之前的代码替换为:

if(bindingResult.hasErrors())
       {
         EmployeeModel response= new EmployeeModel();
         for(FieldError fieldError : bindingResult.getFieldErrors()) 
            {
               response.setErrorList(bindingResult.getFieldErrors());
            }
           return new ResponseEntity( response, 
            HttpStatus.BAD_REQUEST);
       }

您可以继续即兴创作:
您可以在EmpoloyeeModel中添加另一个字段作为状态,status在没有错误时将设置为success,否则设置为erroremployeeModel.setStatus("success") or.setStatus("error")视情况而定 更好的是,编写一个通用的 Response 类来保存所有类型的响应,如下所示:

@Data
@NoArgsConstructor
public class ServiceResponse<T> implements Serializable {
private HttpStatus status; //OK_Failure
private StatusCode statusCode; //code
private T body;
private List<T> errorList;
}

如果您在这方面遇到任何问题,请告诉我。

【讨论】:

  • 这看起来像是处理我遇到的场景的正确方法。但是我很困惑如何将响应类型映射到 EmployeeModel 类型,因为我不会像成功案例一样返回 EmployeeModel。如果问的不是太多,能否请您提供一个关于如何映射 EmployeeModelDTO 并返回错误响应对象的示例??
  • 我只是在下面提供的代码上下文中询问代码的外观,而无需更改我的返回类型 ResponseEntity//you can define your ErrorMOdel dto here and add //fieldError properties then add the whole errorList in //your response. //Finally, return the response from here
  • @harish,请检查我更新的答案。如果这有帮助,您可以接受它作为已接受的答案
猜你喜欢
  • 2022-01-13
  • 2020-08-26
  • 1970-01-01
  • 2020-06-04
  • 1970-01-01
  • 1970-01-01
  • 2020-08-27
  • 2021-12-01
  • 1970-01-01
相关资源
最近更新 更多