SpringMVC使用(一)——@RequestMapping处理请求

本文转自:http://my.oschina.net/zhdkn/blog/316530

对于各种注解而言,排第一的当然是“@Controller”,表明某类是一个controller。

“@RequestMapping”请求路径映射,如果标注在某个controller的类级别上,则表明访问此类路径下的方法都要加上其配置的路径;最常用是标注在方法上,表明哪个具体的方法来接受处理某次请求。

?
1
2
3
4
5
6
7
8
9
10
11
12
13
14
@Controller
@RequestMapping (value= "/book" )
public class BookController {
     
     @RequestMapping (value= "/title" )
     public String getTitle(){
         return "title" ;
     }
     
     @RequestMapping (value= "/content" )
     public String getContent(){
         return "content" ;
     }
}

由于BookController类加了value="/book"的“@RequestMapping”的注解,所有相关路径都要加上"/book",即请求的url分别为:

  1. http://localhost:8080/book/title
  2. http://localhost:8080/book/content

"@RequestMapping"的value值前后是否有“/”对请求的路径没有影响,即value="book" 、"/book"、"/book/"其效果是一样的


"@RequestMapping" 的属性

  • value: 指定请求的实际url
    1. 普通的具体值。如前面的value="/book"。
    2. 含某变量的一类值
    ?
    1
    2
    3
    4
    5
    @RequestMapping (value= "/get/{bookId}" )
         public String getBookById( @PathVariable String bookId,Model model){
             model.addAttribute( "bookId" , bookId);
             return "book" ;
         }

    路径中的bookId可以当变量,@PathVariable 注解即提取路径中的变量值

    3.ant风格
    @RequestMapping(value="/get/id?"):可匹配“/get/id1”或“/get/ida”,但不匹配“/get/id”或“/get/idaa”;
    @RequestMapping(value="/get/id*"):可匹配“/get/idabc”或“/get/id”,但不匹配“/get/idabc/abc”;
    @RequestMapping(value="/get/id/*"):可匹配“/get/id/abc”,但不匹配“/get/idabc”;
    @RequestMapping(value="/get/id/**/{id}"):可匹配“/get/id/abc/abc/123”或“/get/id/123”,也就是Ant风格和URI模板变量风格可混用;

    4. 含正则表达式的一类值
    @RequestMapping(value="/get/{idPre:\\d+}-{idNum:\\d+}"):可以匹配“/get/123-1”,但不能匹配“/get/abc-1”,这样可以设计更加严格的规则。
    可以通过@PathVariable 注解提取路径中的变量(idPre,idNum)

    5. 或关系
    @RequestMapping(value={"/get","/fetch"} )即 /get或/fetch都会映射到该方法上

  • method:  指定请求的method类型, GET、POST、PUT、DELETE等;
    @RequestMapping(value="/get/{bookid}",method={RequestMethod.GET,RequestMethod.POST})

  • params
    @RequestMapping(params="action=del"),请求参数包含“action=del”,如:http://localhost:8080/book?action=del

  • headers
    @RequestMapping(value="/header/id", headers = "Accept=application/json"):表示请求的URL必须为“/header/id 且 请求头中必须有“Accept =application/json”参数即可匹配。
<think>嗯,用户这次问的是Spring框架中@GetMapping和@RequestMapping注解的区别和用法。从用户提供的站内引用来看,用户已经做了些功课,引用了4个资料,主要集中在注解的功能和关系上。用户可能正在学习SpringMVC,需要明确这两个核心注解的使用场景。用户引用的资料1和2明确指出@GetMapping是基于@RequestMapping的封装,专门处理GET请求,而引用3提到Spring新版本用@GetMapping等注解替代了老版@RequestMapping的部分功能。这些信息都是准确的,但用户可能需要更系统的对比。我上次给用户回答过类似问题吗?查看记录,用户之前问的是"Spring框架中关于注解的相关知识",这次具体聚焦到两个注解的区别。看来用户的学习路径是从宏观转向微观了。需要特别注意引用4提到"扩展"但内容不完整,这可能是用户遇到的资料缺口。我应该把常见扩展点也涵盖进去,比如参数处理URL变量匹配这些实战细节。用户提供的资料里有个有趣的细节:引用1提到@GetMapping源码确实是用@RequestMapping(method=GET)实现的。这个实现差异值得展开说明,因为涉及Spring的注解设计哲学——用特定注解简化配置。考虑到用户正在对比学习,应该用表格呈现核心区别会更直观。但要注意避免直接复制资料内容,而是结合工程实践补充:-在RESTful设计中@GetMapping的表意更明确-老项目迁移时@RequestMapping的兼容性优势-混用时可能出现的覆盖问题另外用户没问但可能需要的知识点:1派生注解的性能差异(其实没有)2能否自定义类似的组合注解3在SpringBoot中的特殊表现这些放在相关问题里提示比较合适。最后检查三点:1是否明确@GetMapping是组合注解的本质2是否强调method属性的关键作用3是否给出足够明确的代码示例尤其第二个代码示例要展示两者等效性,这是用户引用资料里没直接呈现的。</think> 好的,我们来详细解析 Spring 框架中 `@GetMapping` 和 `@RequestMapping` 这两个核心注解的功能、用法以及关键区别。 **核心概念与功能** 1. **`@RequestMapping` (更通用、更基础)** * **功能:** 这是个*元注解*,用于将*任意*类型的 HTTP 请求(GET、POST、PUT、DELETE、PATCH 等)映射到特定的控制器方法或类上。它是 Spring MVC 中最基础、最灵活的请求映射注解。 * **用法:** * 可以标注在控制器类上(作为通用前缀)或方法上。 * 必须指定 `method` 属性来定义处理的 HTTP 请求方法(例如 `RequestMethod.GET`)。 * 可以指定 `value` 或 `path` 属性来定义请求 URL 路径模式。 * 可以指定 `params`、`headers`、`consumes`、`produces` 等属性进行更精细的条件匹配。 * **示例 (映射 GET 请求):** ```java @Controller public class MyController { @RequestMapping(value = "/users", method = RequestMethod.GET) public String getUsers(Model model) { // ... 处理获取用户列表的逻辑 return "userList"; } } ``` 2. **`@GetMapping` (更具体、更方便)** * **功能:** 这是个*组合注解*(或称为*派生注解*),专门用于将 **HTTP GET** 请求映射到特定的控制器方法上。 * **本质:** 它是在 `@RequestMapping` 的基础上创建的,可以看作是 `@RequestMapping(method = RequestMethod.GET)` 的**快捷方式**和语法糖。查看源码即可确认[^1][^2]: ```java @Target(ElementType.METHOD) @Retention(RetentionPolicy.RUNTIME) @Documented @RequestMapping(method = RequestMethod.GET) // 核心在这里 public @interface GetMapping { // ... 其他属性继承自@RequestMapping (如 value, path) } ``` * **用法:** * 通常只标注在控制器方法上(虽然技术上也能标在类上,但不如 `@RequestMapping` 常见)。 * 只需要指定 `value` 或 `path` 属性来定义 GET 请求URL 路径模式。 * 同样可以指定 `params`、`headers`、`consumes`、`produces` 等属性进行更精细的条件匹配(因为这些属性是从 `@RequestMapping` 继承来的)。 * **示例:** ```java @RestController // 常用于RESTful API, 内部使用@Controller + @ResponseBody @RequestMapping("/api") // 类级别的@RequestMapping定义通用前缀 public class UserApiController { @GetMapping("/users") // 等价于 @RequestMapping(value = "/users", method = RequestMethod.GET) public List<User> getAllUsers() { // ... 获取所有用户数据 (返回JSON/XML等) return userService.findAllUsers(); } @GetMapping("/users/{id}") public User getUserById(@PathVariable Long id) { // ... 根据ID获取用户 (返回JSON/XML等) return userService.findUserById(id); } } ``` **核心区别总结** | 特性 | `@RequestMapping` | `@GetMapping` | | :--------------------------- | :----------------------------------------------------- | :------------------------------------------------------------------ | | **核心作用** | 通用的 HTTP 请求映射 | **专门**用于 HTTP **GET** 请求映射 | | **灵活性** | **极高**,可配置任意 HTTP 方法 (`method`属性必需) | **较低**,固定用于 GET 方法 | | **本质** | 元注解 (基础注解) | **组合注解** (基于 `@RequestMapping(method = RequestMethod.GET)` 派生)[^1][^2] | | **代码简洁性** | 需明确指定 `method = RequestMethod.GET` | 更**简洁**,只需关注 URL 路径 (不需要指定 `method`) | | **表达清晰度** | 需阅读 `method` 属性才能确定处理的方法 | **意图更明确**,看就知道处理 GET 请求 | | **引入版本** | Spring 早期版本就存在 | Spring **4.3** 引入[^3] | | **常用级别** | 类 (定义前缀) / 方法 | **主要**用于方法 | | **语义** | “这个 URL 路径 *可以* 处理某种类型的请求” | “这个 URL 路径 *专门* 用来处理 GET 请求” | | **是否可替代对方** | 可以(通过设置`method`) | **不能**(无法用于非 GET 请求) | | **类路径映射** | 很常见(作为前缀) | 不太常见(意义不大,仅限制该路径下所有方法的默认请求方法?通常用类级别的 `@RequestMapping`) | **最佳实践建议** 1. **优先使用特定方法注解 (`@GetMapping`, `@PostMapping`, `@PutMapping`, `@DeleteMapping`, `@PatchMapping`):** 在 Spring 4.3+ 中,为处理特定 HTTP 方法(GET、POST、PUT、DELETE、PATCH)时,**强烈推荐**使用这些专用的组合注解。它们让代码更简洁、意图更清晰、可读性更高[^2][^3]。这是目前的主流做法。 2. **保留 `@RequestMapping` 的场景:** * **处理URL路径的多种HTTP方法 (非RESTful风格):** 虽然不鼓励(更推荐RESTful风格,即不同方法对应不同注解),但如果真的需要在同个方法上处理 GET 和 POST 等(根据业务需求,这种情况在现代开发中较少见),则必须使用 `@RequestMapping(method = {RequestMethod.GET, RequestMethod.POST})`。 * **控制器类级别的通用路径前缀:** 使用 `@RequestMapping("/yourPrefix")` 标注控制器类仍然是非常标准且推荐的做法,为该类中所有方法提供个基础路径。 * **处理自定义HTTP方法 (非常罕见):** 理论上可以映射其他非标准HTTP方法(如果有需求)。 * **需要精细匹配 (`headers`, `consumes`, `produces`, `params`):** 当组合注解无法满足某些特殊匹配条件(需要同时指定多个且其中个在组合注解中没有)时。 **简单来说:** * `@GetMapping` 就是为了让你的 `@RequestMapping` 只处理 GET 请求的代码写得更简单、更易懂。 * 在新项目中,能直接用 `@GetMapping` (或其他 `XxxMapping`) 的地方就用它。 * `@RequestMapping` 依然不可或缺,尤其是在类级别定义路径和需要处理复杂映射逻辑的情况下。 **
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值