微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

AJAX GET、POST和复杂请求代码样例

目录

1 概述

  1. 同步和异步
    • 前提条件:客户端和服务器端相互通信的前提下
    1. 同步:客户端必须等待服务器端的响应。在等待的期间客户端不能做其他操作。
    2. 异步:客户端不需要等待服务器端的响应。在服务器处理请求的过程中,客户端可以进行其他的操作。
  2. AJAX 是 ASynchronous JavaScript And XML 的简写,即 AJAX = 异步 JavaScript 和 XML。
  3. 其他基础知识参考博客 AJAX入门介绍

2 普通请求

  1. 前台
    <!DOCTYPE html>
    <html lang="zh-cn">
    
    <head>
        <Meta charset="UTF-8">
        <Meta name="viewport" content="width=device-width, initial-scale=1.0">
        <title>ajax请求测试</title>
    </head>
    
    <body>
        <input id="btn1" type="button" value="get无参请求"></input>
        <input id="btn2" type="button" value="get有参请求"></input>
        <input id="btn3" type="button" value="post无参请求"></input>
        <input id="btn4" type="button" value="post有参请求"></input>
    
        <script src="https://code.jquery.com/jquery-3.1.1.min.js"></script>
        <script>
            $(function () {
                $('#btn1').click(function () {
                    $.ajax({
                        type: "get",
                        url: "http://localhost:8080/ajax/get1",
                        data: {},
                        dataType: "json",
                        success: function (res) {
                            console.log(res);
                        },
                        error: function (err) {
                            console.log(JSON.stringify(err));
                        }
                    })
                });
                
                $('#btn2').click(function () {
                    $.ajax({
                        type: "get",
                        url: "http://localhost:8080/ajax/get2",
                        data: {
                            "name": "newlife",
                            "age": 18
                        },
                        dataType: "json",
                        success: function (res) {
                            console.log(res);
                        },
                        error: function (err) {
                            console.log(JSON.stringify(err));
                        }
                    })
                });
                
                $('#btn3').click(function () {
                    $.ajax({
                        type: "post",
                        url: "http://localhost:8080/ajax/post1",
                        /**
                         * 后台 java 用 @RequestBody 接收参数
                         * 即使参数为空vo,也不能写成 data: {}, 
                         * 因为 @RequestBody 接收的是 json 字符串
                         * 而 type: "post" 认发送的是 json 对象
                         * 因此造成参数类型不匹配错误,无法请求到预期结果!!!
                         * 
                         * 若是报 HttpMediaTypeNotSupportedException 错误
                         * 则加上 contentType: "application/json"
                         * 
                         * 总结:ajax 请求后台带有 @RequestBody 时
                         * contentType 、 dataType 和 JSON.stringify( obj ) 这三个最好都写上
                         */
                        // data: {},
                        data: JSON.stringify({}),
                        contentType: "application/json",
                        dataType: "json",
                        success: function (res) {
                            console.log(res);
                        },
                        error: function (err) {
                            console.log(JSON.stringify(err));
                        }
                    })
                });
                
                $('#btn4').click(function () {
                    $.ajax({
                        type: "post",
                        url: "http://localhost:8080/ajax/post2",
                        data: JSON.stringify({
                            "address": "luoyang",
                            "hobbies": "dance"
                        }),
                        contentType: "application/json",
                        dataType: "json",
                        success: function (res) {
                            console.log(res);
                        },
                        error: function (err) {
                            console.log(JSON.stringify(err));
                        }
                    })
                });
    
            })
        </script>
    </body>
    </html>
    
  2. 后台
    package cn;
    
    import org.springframework.web.bind.annotation.*;
    
    /**
     * @author likefeng
     * @date 2021/3/11 21:01
     */
    
    @RestController
    @RequestMapping("ajax")
    public class AjaxController {
    
        @CrossOrigin
        @GetMapping("get1")
        public String get1() {
            return "这是get无参方法";
        }
    
        @CrossOrigin
        @GetMapping("get2")
        public String get2(@RequestParam("name") String name, @RequestParam("age") String age) {
            return "my name is " + name + " and my age is " + age;
        }
    
        @CrossOrigin
        @PostMapping("post1")
        // UserVO 是一个空vo,里面啥属性也没
        public String post1(@RequestBody UserVO vo) {
            return "这是post无参方法";
        }
    
        @CrossOrigin
        @PostMapping("post2")
        // UserInVO里面有 address 和 hobbies 俩属性,都为String类型
        public String post2(@RequestBody UserInVO inVO) {
            return "my address is " + inVO.getAddress() + " and my hobby is " + inVO.getHobbies();
        }
    }
    

3 复杂请求

  1. 复杂请求介绍可参考 ajax跨域简单请求和复杂请求

  2. 最常见的情况,一是 Content-Type = application/json ; 二是向 header 中添加自定义信息,如 token 等。

  3. 复杂请求首先会先发送一次 options 预请求,用于试探服务端是否能接受真正的请求,如果 options 获得的回应是拒绝性质的,比如 404 \ 403 \ 500 等 http 状态,就会停止接下来 post、put 等请求的发出

  4. 解决办法

    1. springboot / ssm 项目,在配置文件 application.properties 中解决
      spring.mvc.dispatch-options-request=true
      
    2. springcloud 项目,在网关中解决
      // 在 public class TokenFilter extends ZuulFilter 类中
      public boolean shouldFilter() {
          HttpServletRequest request = RequestContext.getCurrentContext().getRequest();
          if (request.getmethod().equals(RequestMethod.OPTIONS.name())) {
              System.out.println("OPTIONS请求不做拦截操作");
              return false;
          }
          /**
           * 其他是否拦截的业务操作
           */
          return true;
      }
      
  5. 样例代码

    1. 前台
      <!DOCTYPE html>
      <html lang="zh-cn">
      <head>
          <Meta charset="UTF-8">
          <Meta name="viewport" content="width=device-width, initial-scale=1.0">
          <title>复杂请求测试3</title>
      </head>
      <body>
          <input id="btn5" type="button" value="复杂请求"></input>
      
          <script src="https://code.jquery.com/jquery-3.1.1.min.js"></script>
          <script>
              $(function () {
                  $('#btn5').click(function () {
                      $.ajax({
                          type: "post",
                          url: "http://localhost:8081/ajax/complexRequest",
                          /**
                           * 根据上面介绍可以,当 contentType: "application/json" 或者往 header 中添加自定义属性时,为复杂请求
                           * 注:下面 headers 中直接塞值 (eg. 塞 name) 或者使用 beforeSend() 塞值 (eg. 塞 token) 均可
                           * 
                           * beforeSend() 介绍如下
                           * beforeSend()是发送请求前可以修改 XMLHttpRequest 对象的函数,例如添加自定义HTTP头。
                           * 在 beforeSend() 中如果返回 false 则可以取消本次 ajax 请求。XMLHttpRequest 对象是惟一的形参。
                           */
                          headers: {
                              "name": "newlife"
                          },
                          beforeSend: function (XMLHttpRequest) {
                              XMLHttpRequest.setRequestHeader("token", "abc422-45afds-hkjdhk4");
                          },
                          data: JSON.stringify({
                              "address": "luoyang",
                              "hobbies": "dance"
                          }),
                          contentType: "application/json",
                          dataType: "json",
                          success: function (res) {
                              console.log(res);
                          },
                          error: function (err) {
                              console.log(JSON.stringify(err));
                          }
                      })
                  });
      
              })
          </script>
      </body>
      </html>
      
    2. 后台
      @RestController
      @RequestMapping("ajax")
      public class AjaxController {
          @CrossOrigin
          @PostMapping("complexRequest")
          // UserInVO里面有 address 和 hobbies 俩属性,都为String类型
          public List<String> complexRequest(@RequestBody UserInVO inVO, HttpServletRequest request) {
              List<String> result = new ArrayList<>();
              // 取前台 headers 中自定义属性 name
              result.add(("my name is " + request.getHeader("name")));
              // 取前台 data 中的数据
              result.add("my address is " + inVO.getAddress());
              result.add("my hobby is " + inVO.getHobbies());
              // 取 beforeSend 中自定义属性 token
              result.add("my token is " + request.getHeader("token"));
              return result;
          }
      }
      
    3. application.properties配置文件
      server.port=8081
      spring.mvc.dispatch-options-request=true
      
    4. 浏览器控制台输出结果
      (4) ["my name is newlife", "my address is luoyang", "my hobby is dance", "my token is abc422-45afds-hkjdhk4"]
      0: "my name is newlife"
      1: "my address is luoyang"
      2: "my hobby is dance"
      3: "my token is abc422-45afds-hkjdhk4"
      length: 4
      __proto__: Array(0)
      

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。

相关推荐