Request Mapping Annotations
Learn @GetMapping, @PostMapping, @PutMapping, and @DeleteMapping, and how they map HTTP verbs to controller methods in Spring Boot.
Introduction
In the previous lesson, you built your first REST controller and used @GetMapping to handle a single endpoint. A real API, though, needs to support the full range of HTTP verbs — GET to read data, POST to create it, PUT to replace it, and DELETE to remove it. Spring Boot gives you a dedicated annotation for each of these, all built on top of the more general @RequestMapping. This lesson covers each one in detail, along with how they combine at the class and method level.
- How @RequestMapping works and why verb-specific annotations exist.
- @GetMapping, @PostMapping, @PutMapping, and @DeleteMapping in practice.
- How class-level and method-level mappings combine into a full URL.
- How to map more than one path to a single handler method.
@RequestMapping: The Original Annotation
@RequestMapping is the general-purpose annotation Spring MVC has used since before Spring Boot existed. It can map any HTTP method to a handler by specifying the method attribute explicitly.
@RestControllerpublic class GreetingController {
@RequestMapping(value = "/greeting", method = RequestMethod.GET) public String greeting() { return "Hello from Spring Boot!"; }}This works fine, but it is verbose. Every mapping needs both a value and a method attribute, and it is easy to forget the method entirely — in which case @RequestMapping matches all HTTP verbs, which is rarely what you want on a REST endpoint.
The Verb-Specific Shortcuts
Spring provides four annotations that are simply @RequestMapping pre-configured for one HTTP method each. They are shorter to write and make the intent of each method obvious at a glance.
| Annotation | HTTP Verb | Typical Use |
|---|---|---|
| @GetMapping | GET | Read one resource or a list of resources |
| @PostMapping | POST | Create a new resource |
| @PutMapping | PUT | Replace an existing resource entirely |
| @DeleteMapping | DELETE | Remove a resource |
| @PatchMapping | PATCH | Partially update a resource |
@RestController@RequestMapping("/api/books")public class BookController {
@GetMapping public String listBooks() { return "Returning all books"; }
@PostMapping public String createBook() { return "Book created"; }
@PutMapping("/{id}") public String replaceBook(@PathVariable Long id) { return "Book " + id + " replaced"; }
@DeleteMapping("/{id}") public String deleteBook(@PathVariable Long id) { return "Book " + id + " deleted"; }}Click Run to see what this code prints.
Combining Class and Method Mappings
In the BookController example above, @RequestMapping("/api/books") is placed on the class itself. Spring prepends this base path to every method-level mapping inside the class, so @GetMapping (with no path) resolves to GET /api/books, and @PutMapping("/{id}") resolves to PUT /api/books/{id}. This pattern — a class-level base path plus method-level suffixes — is how almost every real Spring Boot controller is organized, because it keeps related endpoints grouped together and avoids repeating the resource path on every method.
Give each controller a single class-level @RequestMapping representing one resource ("/api/books", "/api/students"). If you find yourself mapping two unrelated resources in the same controller, that's usually a sign to split it into two controllers.
Multiple Paths on One Method
Occasionally you need one handler to respond to more than one URL — for example, supporting both a legacy path and a new one. Every mapping annotation accepts an array of paths.
@GetMapping({"/status", "/health"})public String status() { return "OK";}Click Run to see what this code prints.
Common Mistakes
- Using bare @RequestMapping everywhere instead of the verb-specific annotations — it hides intent and makes the API harder to scan.
- Forgetting that a class-level @RequestMapping path is a prefix, then duplicating it again inside every method mapping.
- Mapping the same verb and path to two different methods in the same controller, which causes an ambiguous mapping error at startup.
- Leaving the method attribute off @RequestMapping so it silently accepts every HTTP verb.
Best Practices
- Prefer @GetMapping, @PostMapping, @PutMapping, and @DeleteMapping over generic @RequestMapping for individual handlers.
- Put a single class-level @RequestMapping on each controller to establish the resource's base path.
- Follow REST conventions: GET for reads, POST for creates, PUT for full replacement, DELETE for removal, PATCH for partial updates.
- Keep method-level paths short and specific — let the class-level mapping carry the shared prefix.
Frequently Asked Questions
Yes. @GetMapping, @PostMapping, @PutMapping, and @DeleteMapping are all meta-annotations that wrap @RequestMapping with the method attribute already set, so they behave identically but read more clearly.
Spring Boot fails to start and throws an IllegalStateException reporting an ambiguous mapping, because it cannot decide which method should handle the request.
Yes, via @PatchMapping. PUT conventionally replaces a resource entirely, while PATCH updates only the fields you send. Many APIs use PUT for simplicity; larger APIs often support both.
No, it is optional. Without it, each method's mapping is treated as an absolute path from the application root. Adding it is a convention that keeps related endpoints grouped under a shared prefix.
Key Takeaways
- @GetMapping, @PostMapping, @PutMapping, and @DeleteMapping are shortcuts for @RequestMapping with a fixed HTTP method.
- A class-level @RequestMapping acts as a base path that every method-level mapping in that class extends.
- Mapping annotations accept an array of paths when a handler must respond to more than one URL.
- Following REST verb conventions makes your API predictable to any client that consumes it.
Summary
You now know how to route each HTTP verb to the right controller method using @GetMapping, @PostMapping, @PutMapping, and @DeleteMapping, and how class-level and method-level mappings combine. Next, you'll learn how to pull data out of the URL itself and from query strings using @PathVariable and @RequestParam.