英文:
Spring Rest Controller: Correct way to return entities from mapping methods?
问题
I have the following Rest Controller
class that handles HTTP
requests relating to my Client
entity?
For context - a client
(e.g. exercise client) can have one Trainer
. But a Trainer
can have many clients.
Am I returning the entities in the correct way from my controller? I am using the Spring ResponseEntity
class to wrap the Client related responses. Is there any other controller implementations I am missing in order to improve this code? - i.e.
Controller:
@RestController
@RequestMapping(value = "/clients")
public class ClientController {
private final ClientService clientService;
public ClientController(ClientService clientService) {
this.clientService = clientService;
}
@GetMapping("/{clientId}")
ResponseEntity<Client> getClientById(@PathVariable long clientId) {
Client Client = clientService.getClientById(clientId);
return new ResponseEntity<>(Client, HttpStatus.OK);
}
@GetMapping("/trainer/{trainerId}")
ResponseEntity<List<Client>> getClientsByTrainerId(@PathVariable long trainerId) {
List<Client> clients = clientService.getClientsByTrainerId(trainerId);
return new ResponseEntity<>(clients, HttpStatus.OK);
}
@PostMapping
public ResponseEntity<Client> createClient(@RequestBody ClientDTO clientDTO) {
Client newClient = clientService.createNewClient(clientDTO);
return new ResponseEntity<>(newClient, HttpStatus.CREATED);
}
@PutMapping("/{clientId}")
ResponseEntity<Client> updateClient(@PathVariable Long clientId, @RequestBody ClientDTO clientDTO) {
Client editedClient = clientService.editClient(clientId, clientDTO);
return new ResponseEntity<>(editedClient, HttpStatus.OK);
}
}
**Edit: Add Delete method**
```java
@DeleteMapping("/{clientId}")
long deleteClient(@PathVariable long clientId) {
clientService.deleteClient(clientId);
return clientId;
}
英文:
I have the following Rest Controller
class that handles HTTP
requests relating to my Client
entity?
For context - a client
(e.g. exercise client) can have one Trainer
. But a Trainer
can have many clients.
Am I returning the entities in the correct way from my controller? I am using the Spring ResponseEntity
class to wrap the Client related responses.Is there any other controller implementations I am missing in order to improve this code? - i.e.
Controller:
@RestController
@RequestMapping(value = "/clients")
public class ClientController {
private final ClientService clientService;
public ClientController(ClientService clientService) {
this.clientService = clientService;
}
@GetMapping("/{clientId}")
ResponseEntity<Client> getClientById(@PathVariable long clientId) {
Client Client = clientService.getClientById(clientId);
return new ResponseEntity<>(Client, HttpStatus.OK);
}
@GetMapping("/trainer/{trainerId}")
ResponseEntity<List<Client>> getClientsByTrainerId(@PathVariable long trainerId) {
List<Client> clients = clientService.getClientsByTrainerId(trainerId);
return new ResponseEntity<>(clients, HttpStatus.OK);
}
@PostMapping
public ResponseEntity<Client> createClient(@RequestBody ClientDTO clientDTO) {
Client newClient = clientService.createNewClient(clientDTO);
return new ResponseEntity<>(newClient, HttpStatus.CREATED);
}
@PutMapping("/{clientId}")
ResponseEntity<Client> updateClient(@PathVariable Long clientId, @RequestBody ClientDTO clientDTO) {
Client editedClient = clientService.editClient(clientId, clientDTO);
return new ResponseEntity<>(editedClient, HttpStatus.OK);
}
}
Edit: Add Delete method
@DeleteMapping("/{clientId}")
long deleteClient(@PathVariable long clientId) {
clientService.deleteClient(clientId);
return clientId;
}
答案1
得分: 3
在上面的代码中,没有必要将返回类型设为ResponseEntity<>
。你可以声明控制器方法返回任何类型的对象,Spring足够智能,会根据需要将你的预期返回类型包装在ResponseEntity中。
例如:
@GetMapping("/{clientId}")
Client getClientById(@PathVariable long clientId) {
return clientService.getClientById(clientId);
}
如果你想返回除了200 OK之外的不同HTTP状态代码,你可以使用相应的注解。例如:
@PostMapping
@ResponseStatus(HttpStatus.CREATED)
public Client createClient(@RequestBody ClientDTO clientDTO) {
return clientService.createNewClient(clientDTO);
}
我唯一会让控制器方法返回ResponseEntitiy<>
的情况是,如果方法中有根据某些条件返回不同响应类型(状态代码)的逻辑。
另外,通常不建议直接在API端点中返回实体。大多数情况下,你需要将实体类型转换为DTO类型,以将事物的公共表示与持久表示分开。DTO可以具有你想要向客户端公开的任何形状,并且可以独立于域或持久形式进行变化。起初,这可能看起来像是不必要的代码重复的形式;有时两者永远不会分歧或具有不同的结构、名称等。但许多时候经验教导我们,域/持久实体与API契约会以不同的方式演变。
英文:
There's no need in the code above for the return types to be ResponseEntity<>
. You can declare controller methods to return any type of object, and Spring is smart enough to wrap your intended return type in a ResponseEntity as needed.
For example:
@GetMapping("/{clientId}")
Client getClientById(@PathVariable long clientId) {
return clientService.getClientById(clientId);
}
If you want to return a different HTTP status code besides 200 OK, you can use an annotation for that. For example:
@PostMapping
@ResponseStatus(HttpStatus.CREATED)
public Client createClient(@RequestBody ClientDTO clientDTO) {
return clientService.createNewClient(clientDTO);
}
The only time I ever make controller methods return ResponseEntitiy<>
is if I have logic in the method that returns different response types (status codes) based on some conditions.
As an aside, it's usually not a good idea to return your entities directly in API endpoints. Most of the time you're going to want to transform the entity types into DTO types, to separate the public representation of things from the persistent representations. The DTO can have whatever shape you want to expose to clients, and can vary independently from the domain or persistent form. At first this might seem like unnecessary form of code duplication; sometimes the two never diverge or have differing structure, names, etc. But many times experience has taught us that the domain/persistent entities evolve differenty from the API contract.
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论