V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
rhlyym
V2EX  ›  Java

有无懂哥解释下 @PostMapping 与 @PutMapping 注解本质上到底有什么区别

  •  
  •   rhlyym · 2023-10-20 15:48:57 +08:00 · 2319 次点击
    这是一个创建于 419 天前的主题,其中的信息可能已经有所发展或是发生改变。
    1. 有没有大佬告知下这两个在 spring boot 里面到底有什么本质的区别
    2. 对于 @PutMapping 他既可以通过 url 传参又可以通过请求体传参,这样的形式符合规范吗,为什么不像 @PostMapping 一样参数都在请求体里面,搞出 @PutMapping 不是多此一举吗
    19 条回复    2023-10-22 13:05:02 +08:00
    zilongzixue
        1
    zilongzixue  
       2023-10-20 15:55:05 +08:00
    @PostMapping 也可以在 url 传参,本质上就是 restful 命名,增删改查,你喜欢你用 deletemapping 都可以
    Ayanokouji
        2
    Ayanokouji  
       2023-10-20 16:30:30 +08:00
    点进去看看源码,都是 RequestMapping ,如果你还是不懂的话,建议学习 http ,什么位置传参跟 spring boot 关系不大
    @RequestMapping(
    method = {RequestMethod.PUT}
    )
    Oktfolio
        3
    Oktfolio  
       2023-10-20 16:44:20 +08:00
    REST 的语义化

    POST 一样可以在 url 传参

    PUT 语意就是完全替换资源或在资源不存在的情况下创建一个新的资源,PUT 方法的实现应该是幂等的,也就是多次执行结果都相同
    POST 方法则不一定是幂等的

    PUT 、DELETE 、PATCH 等语义化的方法都是在 POST 方法基础上加上参数识别的
    zzl22100048
        4
    zzl22100048  
       2023-10-20 16:45:28 +08:00
    根据 http 协议,http 所有方法没有区别,就是个标志;所有区别都是人为规定的
    ZZ74
        5
    ZZ74  
       2023-10-20 16:51:58 +08:00
    PUT 是 HTTP 协议的一种方法
    因为狗屎 RESTFUL ,非要 给 HTTP 请求搞 “赋能”
    Spring 一看 行吧 就给你加个注解 反正对我没啥成本
    sumarker
        6
    sumarker  
       2023-10-20 16:55:21 +08:00
    接口只能接特定类型的请求,本意是为了让 restful 请求“规范”,
    但一般都会嫌麻烦或者其他各种原因,@postmapping 一把梭
    Oktfolio
        7
    Oktfolio  
       2023-10-20 16:57:26 +08:00
    @Oktfolio #3
    更正一下,都是 HTTP 协议的方法,本身是没有上面说的含义的,是 RESTful 对其赋予了含义。

    在 HTTP/1.1 不需要使用 POST _method 来模拟,在 HTTP/1.0 中需要

    SpringMVC 中对应获取 _method 的代码在 HiddenHttpMethodFilter 中
    snickers
        8
    snickers  
       2023-10-20 16:57:38 +08:00
    PUT 请求具有幂等性,执行多次 PUT 请求的结果应该相同,POST 请求不具有幂等性
    Masoud2023
        9
    Masoud2023  
       2023-10-20 17:11:22 +08:00
    你没理解 restful 语义。

    @XXXMapping 都只是处理对应 method 的请求,点进去你会发现基本都是 `@RequestMapping(method ={RequestMethod.XXX} )`

    GET/POST/PUT/DELETE 之类的 method 语义,充其量也只是语义而已。

    不是说 GET 就不能放个 body 进去,也不是说 POST 就不能 url 传参,也就是 query param 。

    只要你想,怎么用那也都算 http 请求,只是一般没有人这么用,并且一些轮子,get 请求根本发不出去 body ,我没记错的话 restTemplate 处理这种就会有问题。

    你如果想看一些讨论的话可以去 stackoverflow ,https://stackoverflow.com/questions/978061/http-get-with-request-body

    归根结底只是一种君子协议,你可以选择不做君子,但是到时候你也不要怪君子不讲人情。

    我也比较认同“restful 是一坨屎”这个观点,实际上真让一些人写 restful ,恐怕也没几个人能写好这种东西。

    回到你的问题上,PutMapping 和 PostMapping 也都是可以传 query param 的,并且这种设计其实日常用的蛮多的,比如修改帖子内容,完全可以把帖子 id 放到 query param ,然后让 body 只保留 entity ,这是一种非常 fantastic 的设计,PutMapping 不是多此一举,他只是更加符合语义的一种写法。

    能看出来你可能是新手,我建议别理解了,直接无脑 GET/POST 就行了,取数据就 GET ,存、改、删就 POST ,没什么不行的。
    nothingistrue
        10
    nothingistrue  
       2023-10-20 17:29:36 +08:00
    @PostMapping 只能接受 http method = POST 的请求, @PutMapping 只能接受 http method = PUT 的请求。单独 @PostMapping 的请求,如果你拿 PUP 去请求,回收到 405 Method Not Allowed 。反之亦然。

    @PostMapping 跟 @PutMapping 就上面那点区别。这是强制性的编码逻辑,不是非强制性的规范。虽然楼上几个确实在回复楼主真正该问的,但是对于原始问题的回答,是错的。

    楼主真正该问的,是 http method 中,POST 和 PUT 的区别。这俩在「 URL]和[参数载体」上,是一模一样的,没有区别。POST 、PUT 的参数,都是可以即用 URL ,也可以用请求体的,具体怎么用看个人喜好。它们的区别,主要在接口本身的用途上,简单的说:POST 是推送新数据,PUT 是修改现有数据。
    nothingistrue
        11
    nothingistrue  
       2023-10-20 17:46:22 +08:00
    虽然 PUT 、POST 的传参方式,看个人喜好,但是额外遵守一个规范,对个人和团队都有好处。

    一般来说:ID 这种明显的目录性质的参数,应通过 URL 本体携带(? 前面的部分),动态查询条件应通过 queryParam (?后面的部分)携带,而数据则应通过请求体携带。POST 是推送新数据,新数据是没有 ID 的,故所有内容都通过参数体携带。PUT 是修改数据,这需要首先指定 ID 然后指定要修改的数据,所以他需要同时有 URL 参数和请求提参数。

    当然,如果 PUT 请求的 ?后面还带了业务参数,那不影响功能,但是个大坑。
    nerkeler
        12
    nerkeler  
       2023-10-20 17:55:25 +08:00
    你以为 @GetMapping 就不能传请求体了吗
    netabare
        13
    netabare  
       2023-10-20 18:00:44 +08:00   ❤️ 1
    本质的区别就是一个是 POST ,一个是 PUT ,这是 RESTful 定义的,和 Spring 注解没啥关系。

    再不然看源码也好。「既可以……又可以……」更多是编程语言具体实现的问题,可以这么做不代表它是合理的。
    ThreeK
        14
    ThreeK  
       2023-10-20 18:02:18 +08:00
    俩个维度东西啊。
    请求方式 :put post 区别。
    传参方式: 能 uri 、body 体
    mango88
        15
    mango88  
       2023-10-20 18:10:09 +08:00
    用法跟他的规范关系不大,可以选择遵守 也可以 post 一把梭
    Chinsung
        16
    Chinsung  
       2023-10-20 18:11:33 +08:00
    本质?本质就是一个接受的是 http post 请求,一个接受的是 http put 请求
    learningman
        17
    learningman  
       2023-10-20 19:17:28 +08:00 via Android
    你乐意的话定义个 abc method 也是可以的
    me1onsoda
        18
    me1onsoda  
       2023-10-21 12:14:30 +08:00
    @snickers 幂不幂等只和你写的代码有关系,和协议无关吧
    goalidea
        19
    goalidea  
       2023-10-22 13:05:02 +08:00
    这就跟很早以前男女都都上一个茅坑,现在规范( restful )了分了男厕所,女厕所,母婴厕所一个道理
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   1488 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 82ms · UTC 16:53 · PVG 00:53 · LAX 08:53 · JFK 11:53
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.