ajax的post请求的前端传参格式以及springboot后端接收参数方式

一、数据准备(想看结论直接翻最后)

1、搭建一个springBoot的后端工程
1.1 创建一个简单的user实体类

在这里插入图片描述

1.2 template目录下添加index.html

在这里插入图片描述

1.3 配置静态资源访问路径
@Component
public class WebConfig implements WebMvcConfigurer {
    /**
     * springboot 无法直接访问静态资源,需要放开资源访问路径。
     * 添加静态资源文件,外部可以直接访问地址
     */
    @Override
    public void addResourceHandlers(ResourceHandlerRegistry registry) {
        registry.addResourceHandler("/**").addResourceLocations("classpath:/templates/");       
    }
}
1.4 controller编写,创建接收参数的controller
@RequestMapping("/user")
@RestController
public class UserController {
}

二、后端实体类接收参数

1、后端添加add方法(注意@RequestBody注解,表明这是一个请求体数据)
@PostMapping("/add")
public Object addUser(@RequestBody User user){
    return user;
}
2、 前端代码,这里使用了vue+elementui的form表单

在这里插入图片描述

add1: function () {
    var that = this;
    console.log(that.form.name, that.form.sex);
    axios({
        method: 'post',
        url: "http://localhost:7777/test-request/user/add",
        data: {
            name: that.form.name,
            sex: that.form.sex
        }
    }
         ).then(function (result) {
        that.result = result;
        alert(result)
    });
}

在我们不对axios的请求头进行设置的时候,axios的post请求默认请求头中Content-Type类型为application/json

3、错误情况
3.1 后端实体类接收参数,但是缺少注解@RequestbBody注解,前端使用默认的Content-Type类型(application/json)
@PostMapping("/add")
public Object addUser(User user){
	return user;
}

接口响应结果:

在这里插入图片描述

可以看出此时虽然不会报错,但后端无法解析前端传来的json数据,返回的数据均为null

3.2 后端使用@RequestParam方式接收参数,前端使用默认的Content-Type类型(application/json)
@PostMapping("/add")
public Object addUser(@RequestParam("name") String name,
                      @RequestParam("sex") String sex){

    User user=new User();
    user.setName(name);
    user.setSex(sex);
    return user;
}

后段响应结果

在这里插入图片描述

{“timestamp”:“2021-09-10T02:56:40.430+0000”,“status”:400,“error”:“Bad Request”,“message”:“Required String parameter ‘name’ is not present”,“path”:"/test-request/user/add"}

此时报错400,后端报错请求参数name找不到,但是前端明明传了name的值,说明后端还是无法解析此时的参数

3.3 后端去掉@RequestParm注解,Content-Type类型改为(application/x-www-form-urlencoded; charset=UTF-8)
@PostMapping("/add")
public Object addUser(String name,String sex){
    User user=new User();
    user.setName(name);
    user.setSex(sex);
    return user;
}
axios({
    headers: {'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8'},
    method: 'post',
    url: "http://localhost:7777/test-request/user/add",
    data: {
        name: that.form.name,
        sex: that.form.sex
        }
    }
    ).then(function (result) {
    alert(result)
});

这种方式不报错,但是后端还是不能够成功的接收到前端发过来的数据,

此时前端的数据格式为:

在这里插入图片描述

请求头也确实为application/x-www-form-urlencoded

在这里插入图片描述

3.4但是在换了一种请求方式之后,改用jquery的ajax之后
 $.ajax({
     type:"post",
     url:"http://localhost:7777/test-request/user/add",
     data:{
         name: that.form.name,
         sex: that.form.sex
     },
     success: function (data) {
         alert(data)
     }
 })

后端成功接收到了数据。

此时查请求头和请求数据格式如下:

在这里插入图片描述

在使用jquery的ajax时我们并没有设置他的请求中 Content-Type,说明它默认为form表单的数据类型

但是请求的表单数据已经变为了键值对类型数据,并不是axios中的那种json格式的数据

3.5 使用axios的qs将数据变为form类型的数据
axios.post("http://localhost:7777/test-request/user/add",
           qs.stringify({name: that.form.name,sex: that.form.sex}),
           {headers: {'Content-Type': 'application/x-www-form-urlencoded; charset=UTF-8'}})
    .then(function (result) {
        that.result = result;
        alert(result)
    });

此时后端可成功接收到参数,前端数据格式也变为了form类型的键值对数据格式

3.6 使用jquery的ajax,后端采用@RequestBody注解,使用实体类来进行接收

在3.4中发现ajax默认是使用application/x-www-form-urlencoded; charset=UTF-8来进行接收参数的,所以必须修改Content-Type的类型为application/json

如不修改则报错415,错误信息如下

{"timestamp":"2021-09-10T06:19:11.814+0000","status":415,"error":"Unsupported Media Type","message":"Content type 'application/x-www-form-urlencoded;charset=UTF-8' not supported","path":"/test-request/user/add"}

此时第一想到的一定是去修改请求头中的Content-Type为Application/json

$.ajax({
    type:"post",
    url:"http://localhost:7777/test-request/user/add",
    contentType: 'application/json',
    data:{
        name: that.form.name,
        sex: that.form.sex
    },
    success: function (data) {
        alert(data)
    }
})

再次发起请求,发现报错400,错误信息如下:

{"timestamp":"2021-09-10T06:24:09.435+0000","status":400,"error":"Bad Request","message":"JSON parse error: Unrecognized token 'name': was expecting 'null', 'true', 'false' or NaN; nested exception is com.fasterxml.jackson.core.JsonParseException: Unrecognized token 'name': was expecting 'null', 'true', 'false' or NaN\n at [Source: (PushbackInputStream); line: 1, column: 6]","path":"/test-request/user/add"}

此时的请求数据格式为:

在这里插入图片描述

数据变为了这种被编码过的并且是&拼接起来的数据,并不是合理的json数据

解决方案:将数据使用JSON.stringify()函数将数据转换为json字符串

var searchData={name: that.form.name,sex: that.form.sex};
$.ajax({
    type:"post",
    url:"http://localhost:7777/test-request/user/add",
    contentType: 'application/json',
    data:JSON.stringify(searchData),
    success: function (data) {
        alert(data)
    }
})

此时得到后端正确的响应信息,成功。此时的数据格式为:

在这里插入图片描述

三、总结

不带@RequestBod实体类接收带@RequestBod注解的实体类参数接收
ajax,参数进行JSON.stringify()处理,不添加contentType请求头,使用默认的无法接收数据,不报错无法接收数据,不报错无法接收数据,不报错
ajax,参数进行JSON.stringify()处理,添加contentType请求头为’application/json’无法接收数据,不报错可以正常接收无法接收数据,不报错
ajax,参数不进行JSON.stringify()处理,不添加contentType请求头,使用默认的可以正常接收报错415可以正常接收
ajax,参数不进行JSON.stringify()处理,添加contentType请求头’application/json’无法接收数据,不报错报错400无法接收数据,不报错

ContentType类型

application/x-www-form-urlencoded,这种格式会对表单数据进行url编码

multipart/form-data, 文件上传时候必须使用这种格式

application/json, post常用的格式,使用此种格式时候必须对数据进行json处理

@RequestBody

一个请求只能有一个该注解

后端@RequestBody注解对应的类在将前端的请求数据(包含请求体)包装为一个实体类,(即:@RequestBody后面的类),会根据json字符串中的key来匹配对应实体类的属性,如果匹配一致且json中的该key对应的值符合(或可转换为)

json字符串中的value的数据类型和实体类中的若不对应,则接收到的参数类型为null

application/json, post常用的格式,使用此种格式时候必须对数据进行json处理

@RequestBody

一个请求只能有一个该注解

后端@RequestBody注解对应的类在将前端的请求数据(包含请求体)包装为一个实体类,(即:@RequestBody后面的类),会根据json字符串中的key来匹配对应实体类的属性,如果匹配一致且json中的该key对应的值符合(或可转换为)

json字符串中的value的数据类型和实体类中的若不对应,则接收到的参数类型为null

### Spring Boot后端传参方法 #### 路径参数传递 (Path Parameters) 路径参数是指前端参数作为URL路径的一部分传递给服务器,而后端则通过`@PathVariable`注解来接收这些参数。这种方式适用于资源定位场景。 例如: - **前端请求示例** `GET /api/users/123` - **后端处理示例** ```java @GetMapping("/api/users/{id}") public String getUserById(@PathVariable("id") Long id) { // 处理逻辑 return "success"; } ``` 此代码片段展示了如何定义一个接受ID作为路径变量的方法[^3]。 #### 查询参数传递 (@RequestParam) 查询参数通常附加在URL后面,形式为键值对。对于GET请求而言,这是最常见的参数传递方式之一;而对于POST请求来说,则可以用来接收来自HTML表单的数据。 - **前端请求示例** `http://localhost:8080/user?id=1` - **后端处理示例** ```java @PostMapping("/user") public ResponseEntity<String> createUser( @RequestParam(value="name", required=false, defaultValue="John Doe") String name, @RequestParam(value="age", required=true) Integer age){ User user = new User(name, age); userService.save(user); return ResponseEntity.ok("User created successfully"); } ``` 这里使用了@RequestParam注解指定要从HTTP请求中提取哪些参数,并允许设置默认值和必填属性[^4]。 #### 表单数据传递 (@ModelAttribute 或者直接使用实体类) 当涉及到复杂的对象结构时,可以直接让Spring MVC自动绑定整个对象到控制器方法中的参数上。这特别适合于处理带有多个字段的Web表单提交情况。 - **前端表单示例** ```html <form action="/submitForm" method="post"> <input type="text" name="username"/> <input type="password" name="password"/> </form> ``` - **后端处理示例** ```java @PostMapping("/submitForm") public ModelAndView submitLoginForm(@ModelAttribute LoginForm loginForm){ System.out.println(loginForm.getUsername()); System.out.println(loginForm.getPassword()); return new ModelAndView("redirect:/home"); } // 或者更简洁的方式是直接使用实体类 @PostMapping("/createUser") public String createNewUser(User newUser){ userRepository.save(newUser); return "redirect:/users"; } ``` 上述例子显示了两种不同的方法来接收并处理由客户端发送过来的对象实例[^2]。 #### JSON 数据交互 (@RequestBody/@ResponseBody) 现代应用程序经常采用RESTful API设计模式,在这种情况下,前后端之间交换的信息通常是JSON格式字符串。为了简化开发过程,Spring提供了专门用于解析和序列化JSON消息体的支持——即`@RequestBody`与`@ResponseBody`两个注解配合Jackson库一起工作。 - **前端AJAX调用示例** ```javascript $.ajax({ url : '/save', contentType:'application/json;charset=UTF-8', data : JSON.stringify({title:"My Title", content:"Some Content"}), success:function(data,status,xhr){}, error:function(xhr,status,error){} }); ``` - **后端处理示例** ```java @RestController @RequestMapping("/articles") public class ArticleController { @PostMapping("") public void saveArticle(@RequestBody Article article){ articleService.save(article); } } ``` 这段Java代码表明了一个能够响应保存文章操作的服务接口,它会把接收到的内容反序列化成对应的JavaBean实例。
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

一个小白QAQ

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值