AJAX笔记(完结版)

目录

一、XML

二、AJAX特点

三、HTTP协议

三、Express服务端框架

四、Express服务端框架简单实现代码

五、IE缓存问题及超时与网络异常

六、手动取消请求及请求重复发送问题

七、jQuery与AJAX、Axios与AJAX(可用BootCDN引入jQuery、Axios)

八、fetch函数发送ajax请求

九、同源策略

(一)同源策略(ajax默认遵循同源策略)

(二)具体代码

#END(具体可看b站尚硅谷视频ovo)



一、XML

1. XML(可扩展标记语言):被设计用来传输和存储数据;

2. XML:支持自定义标签,无预定义标签。

3. HTML和XML的区别

1)HTML:超文本标记语言,用于显示数据,不区分大小写

      XML:可扩展标记语言,用于传输数据,区分大小写

2)HTML:预定义标记;

      XML:自定义标记。

二、AJAX特点

1. 优点:

1)可以直接与服务器端进行通信,而不需要刷新页面;

2)允许根据用户事件来更新部分内容页面;

2. 缺点:

1)没有浏览历史,不可回退;

2)存在跨域问题(即是否同源);

3)对SEO(SEO:搜素引擎优化)不友好。

三、HTTP协议

1. HTTP协议(超文本传输协议):详细规定了浏览器和万维网服务器之间互相通信的规则;

主要约定的内容:

请求:浏览器发送给服务器;

请求报文:浏览器发送给服务器的内容;

响应:服务器端返回给浏览器;

响应报文:服务器端返回给浏览器的内容。

2. 请求报文:

1)格式:

行          GET(请求类型)/ url路径   HTTP/1.1(HTTP版本)
头          Host:atguigu.com
            Cookie:name=guigu
           (格式:名字+:+空格+值)
空行(必须要)
体

2)头的作用:告知服务器请求体的类型

      设置url的方式:地址分割用,多个值用 & 连接。

3. 响应报文:

1)格式:

行     HTTP/1.1(HTTP版本)  响应状态码  响应状态字符串(与状态码对应)
头     Content-Type:text/html;charset=utf-8
       Content-length:2048
      (格式:名字+:+空格+值)
空行(必须要)
体(放html内容)

2)头的作用:对响应体内容做相关描述。

三、Express服务端框架

1. express:基于 node.js 平台;

2. 安装步骤:

文件最外层启动终端 -> 输入 npm init --yes  -> 输入 npm i express

安装 nodemon

npm install -g nodemon

3. 使用步骤:

1)引入express:const express = require(‘express’)

2)创建应用对象:const app = express()

3)创建路由规则:

request:对请求报文的封装;

response:对响应报文的封装。

app.get(‘/’,(request,response) => {

response.send(‘HELLO’);

});

4)监听端口启动服务:

app.listen(8000,()=> {

console.log(“服务已经启动,8000端口监听中...”);

})

5)在终端输入 node + 文件名(文件名一定要写上后缀名!!

四、Express服务端框架简单实现代码

实现点击按钮,将响应体内容显示在一个盒子中

1. express服务端框架代码:

//1.引入express
const { request, response } = require("express");
const express = require("express");
const res = require("express/lib/response");

//2.创建应用对象
const app = express();

//3.创建路由规则
app.all("/json-server", (request, response) => {
  //设置响应头 设置允许跨域
  response.setHeader("Access-Control-Allow-Origin", "*");
  //设置头 可以任意名
  response.setHeader("Access-Control-Allow-Headers", "*");
  //设置响应体
  //响应一个数据
  const data = {
    name: "sehun",
  };
  //对对象进行字符串转换
  let str = JSON.stringify(data);
  //send 只能接收字符串或者buffer
  response.send(str);
});
//app.all() 可以接收任意类型的请求

2. 页面代码:

  <body>
    <input type="button" value="点击发送请求" id="button" />
    <div class="result" id="result"></div>
  </body>
  <script>
    //获取button元素
    const btn = document.getElementById("button");
    const result = document.querySelector(".result");
    btn.onclick = function () {
      //1.创建对象
      const xhr = new XMLHttpRequest();
      //2.初始化 设置请求方法和url
      xhr.open("GET", "http://127.0.0.1:8000/server");
      //3.发送
      xhr.send();
      //4.事件绑定 处理服务端返回的结果
      // on...when... 当...时候
      // readystate 是 xhr 对象中的属性 表示状态 0 1 2 3 4
      // change 改变
      xhr.onreadystatechange = function () {
        //判断(服务端返回了所有结果)
        if (xhr.readyState === 4) {
          // 判断响应状态码 200 404 403 401 500
          // 2xx 都表示成功
          if (xhr.status >= 200 && xhr.status < 300) {
            // 处理结果 行 头 空行 体
            console.log(xhr.status); // 状态码
            console.log(xhr.statusText); // 状态字符串
            console.log(xhr.getAllResponseHeaders()); // 响应头
            console.log(xhr.response); // 响应体
            result.innerHTML = xhr.response;
          }
        }
      };
      console.log("test");
    };
  </script>

3. 实现结果:

五、IE缓存问题及超时与网络异常

1. 什么是IE缓存问题?

IE浏览器会对ajax请求的结果做一个缓存,不能及时反应ajax请求的变化,影响时效性

2. 解决方法:在 open() 初始化设置 url 时,?t=" + Date.now()

xhr.open("GET", "url地址?t=" + Date.now());

3. 具体代码:

 <body>
    <input type="button" value="点击发送请求" id="button" />
    <div class="result" id="result"></div>
  </body>
  <script>
    const btn = document.querySelector("#button");
    const result = document.querySelector(".result");
    btn.addEventListener("click", () => {
      console.log("test");
      const xhr = new XMLHttpRequest();
      xhr.open("GET", "http://127.0.0.1:8000/ie?t=" + Date.now());
      xhr.send();
      xhr.onreadystatechange = () => {
        if (xhr.readyState === 4) {
          if (xhr.status >= 200 && xhr.status < 300) {
            result.innerHTML = xhr.response;
          }
        }
      };
    });
  </script>
//针对 IE缓存 的规则
app.get("/ie", (request, response) => {
  //设置响应头 设置允许跨域
  response.setHeader("Access-Control-Allow-Origin", "*");
  //设置响应体
  response.send("Hello IE qaq");
});

4. 超时(自动取消请求)与网络异常处理:

1)进行延时设置, 设置 timeout 并在请求中使用 ontimeout 回调函数,当超过 timeout 所规定的时间时,则取消请求并执行 ontimeout 的函数内容;

2)使用 onerror 判别网络是否出现问题;

5. 具体实现:

<body>
    <input type="button" value="点击发送请求" id="button" />
    <div class="result" id="result"></div>
  </body>
  <script>
    const btn = document.querySelector("#button");
    const result = document.querySelector(".result");
    btn.addEventListener("click", () => {
      console.log("test");
      const xhr = new XMLHttpRequest();
      //延时设置 意味着在3/2s内没有结果请求就取消
      xhr.timeout = 1500;
      //超时回调
      xhr.ontimeout = () => {
        alert("网络异常,请稍后再试qaq");
      };
      //网络异常回调
      xhr.onerror = () => {
        alert("您的网络似乎出现了一些问题");
      };

      xhr.open("GET", "http://127.0.0.1:8000/delay");
      xhr.send();
      xhr.onreadystatechange = () => {
        if (xhr.readyState === 4) {
          if (xhr.status >= 200 && xhr.status < 300) {
            result.innerHTML = xhr.response;
          }
        }
      };
    });
  </script>
//延时响应规则
app.all("/delay", (request, response) => {
  //设置响应头 设置允许跨域
  response.setHeader("Access-Control-Allow-Origin", "*");
  //设置头 可以任意名
  response.setHeader("Access-Control-Allow-Headers", "*");
  //设置定时器
  setTimeout(() => {
    //设置响应体
    response.send("Hello 延时响应");
  }, 2000);
});

6. 结果如下:

1) 超时:

六、手动取消请求及请求重复发送问题

1. 取消请求(手动):利用 abort 手动取消请求

2. 代码实现:

<body>
    <input type="button" value="点击发送" id="btn1" />
    <input type="button" value="点击取消" id="btn2" />
  </body>
  <script>
    const btn1 = document.querySelector("#btn1");
    const btn2 = document.querySelector("#btn2");
    let x = null;
    btn1.onclick = () => {
      x = new XMLHttpRequest();
      x.open("GET", "http://127.0.0.1:8000/delay");
      x.send();
    };
    // abort 取消 -> 手动取消
    btn2.onclick = () => {
      x.abort();
    };
  </script>

3. 结果:

4. 请求重复发送问题:(避免服务器压力过大)

5. 代码实现

<body>
    <input type="button" value="点击发送" id="btn" />
  </body>
  <script>
    //获取元素
    const btn = document.querySelector("#btn");
    let x = null;
    //标识变量
    let sign = false; // 是否正在发送AJAX请求 true代表正在发送
    btn.onclick = () => {
      //判断标识变量
      //如果正在发送,则取消该请求,创建一个新的请求
      if (sign) {
        x.abort();
      }
      x = new XMLHttpRequest();
      //修改 标识变量的值
      sign = true;
      x.open("GET", "http://127.0.0.1:8000/delay");
      x.send();
      //判断请求是否完成
      x.onreadystatechange = () => {
        if (x.readyState === 4) {
          //修改标识变量
          sign = false;
        }
      };
    };
  </script>

6. 结果:

七、jQuery与AJAX、Axios与AJAX(可用BootCDN引入jQuery、Axios)

1. jQuery发送AJAX请求:GET、POST、通用型

2.代码:

<body>
    <div class="container">
      <h2 class="page-header">jQuery发送AJAX请求</h2>
      <input type="button" value="GET" class="btn btn-primary" />
      <input type="button" value="POST" class="btn btn-danger" />
      <input type="button" value="通用型方法ajax" class="btn btn-info" />
    </div>
  </body>
  <script>
    $("input")
      .eq(0)
      .click(() => {
        // 第一个参数代表 要发送给谁
        // 第二个参数代表 要发送什么参数值
        // 第三个参数 是一个回调
        // 第四个参数 是响应体类型
        $.get(
          "http://127.0.0.1:8000/jquery-server",
          { a: 100, b: 200 },
          (data) => {
            console.log(data);
          },
          "json"
        );
      });

    $("input")
      .eq(1)
      .click(() => {
        // 第一个参数代表 要发送给谁
        // 第二个参数代表 要发送什么参数值
        // 第三个参数 是一个回调
        $.post(
          "http://127.0.0.1:8000/jquery-server",
          { a: 100, b: 200 },
          (data) => {
            console.log(data);
          },
          "json"
        );
      });

    $("input")
      .eq(2)
      .click(() => {
        $.ajax({
          //url
          url: "http://127.0.0.1:8000/jquery-server",
          //参数
          data: { a: 100, b: 200 },
          //请求类型
          type: "GET",
          //响应体结果
          dataType: "json",
          //成功的回调
          success: (data) => {
            console.log(data);
          },
          //超时时间
          timeout: 2000,
          //失败的回调
          error: () => {
            console.log("error!");
          },
        });
      });
  </script>
//jquery 服务规则
app.all("/jquery-server", (request, response) => {
  //设置响应头 设置允许跨域
  response.setHeader("Access-Control-Allow-Origin", "*");
  // 转换为json
  const data = { name: "sehun" };
  //设置响应体
  //response.send("Hello jQuery AJAX");
  response.send(JSON.stringify(data));
});

3. 结果:

 4. Axios发送AJAX请求:GET、POST、通用型

5. 代码:

 <body>
    <input type="button" value="GET" />
    <input type="button" value="POST" />
    <input type="button" value="ajax" />
  </body>
  <script>
    const btns = document.querySelectorAll("input");
    //配置基本url
    axios.defaults.baseURL = "http://127.0.0.1:8000";
    btns[0].onclick = () => {
      //get请求
      axios
        .get("/axios-server", {
          //url 参数
          params: {
            id: 100,
            vip: 7,
          },
          //请求头信息
          headers: {
            name: "sehun",
          },
        })
        .then((value) => {
          console.log(value);
        });
    };

    btns[1].onclick = () => {
      axios.post(
        "/axios-server",
        //请求体
        {
          username: "sehun",
          password: "exo",
        },
        {
          //url
          params: {
            id: 200,
            vip: 9,
          },
          //请求头
          headers: {
            height: 180,
            weight: 180,
          },
        }
      );
    };

    btns[2].onclick = () => {
      axios({
        //请求方法
        method: "POST",
        //url
        url: "/axios-server",
        //url参数
        params: {
          vip: 10,
          level: 30,
        },
        //请求头
        headers: {
          a: 100,
          b: 200,
        },
        //请求体
        data: {
          username: "sehun",
          password: "exo",
        },
      }).then((response) => {
        console.log(response);
        //响应状态码
        console.log(response.status);
        //响应状态字符串
        console.log(response.statusText);
        //响应头信息
        console.log(response.headers);
        //响应体
        console.log(response.data);
      });
    };
  </script>
//axios 服务规则
app.all("/axios-server", (request, response) => {
  //设置响应头 设置允许跨域
  response.setHeader("Access-Control-Allow-Origin", "*");
  //设置头 可以任意名
  response.setHeader("Access-Control-Allow-Headers", "*");
  // 转换为json
  const data = { name: "sehun" };
  //设置响应体
  //response.send("Hello jQuery AJAX");
  response.send(JSON.stringify(data));
});

6. 结果:

八、fetch函数发送ajax请求

1. 利用fetch函数发送ajax请求,第一个参数为url,第二个参数为一个函数体

2. 代码:

<body>
    <input type="button" value="ajax请求" />
  </body>
  <script>
    const btn = document.querySelector("input");

    btn.onclick = () => {
      fetch("http://127.0.0.1:8000/fetch-server", {
        //方法
        method: "POST",
        //请求头
        headers: {
          name: "sehun",
        },
        //请求体
        body: "username=sehun&password=exo",
      })
        .then((response) => {
          //return response.text();
          return response.json();
        })
        .then((response) => {
          console.log(response);
        });
    };
  </script>
//fetch 服务规则
app.all("/fetch-server", (request, response) => {
  //设置响应头 设置允许跨域
  response.setHeader("Access-Control-Allow-Origin", "*");
  //设置头 可以任意名
  response.setHeader("Access-Control-Allow-Headers", "*");
  // 转换为json
  const data = { name: "sehun" };
  //设置响应体
  //response.send("Hello jQuery AJAX");
  response.send(JSON.stringify(data));
});

 3. 结果如下:

九、同源策略

(一)同源策略(ajax默认遵循同源策略)

1. 最早由Netscape公司提出,是浏览器的一种安全策略;

2. 同源策略:网页的url与在网页中用ajax请求的url在协议、域名、端口号方面必须完全相同(即同一个来源/来自同一个服务器

3. 跨域:违背同源策略;

4. 解决跨域问题:

1)JSONP

① 工作原理:借助页面的script标签进行跨域

② 调用返回的应该是一段js代码

③ 返回结果的形式是一个函数调用

注:函数的参数则是我们想给客户端返回的客户数据,前端需要提前说明!

2)CORS

① 跨域资源共享,官方的跨域解决方案

② 特点:不需要在客户端做任何特殊的操作,完全在服务器中进行处理,支持get和post请求

③ 通过设置一个响应头解决

(二)具体代码

 1. jsonp

1)代码:

 <body>
    <div class="result"></div>
    <script>
      function handle(data) {
        //获取result元素
        const result = document.querySelector(".result");
        result.innerHTML = "发送给" + data.name;
      }
    </script>
  </body>
  <script src="http://127.0.0.1:8000/jsonp-server"></script>
//jsonp 服务规则 返回结果的形式是一个函数调用
//函数的参数则是我们想给客户端返回的客户数据 前端需要提前说明
app.all("/jsonp-server", (request, response) => {
  //response.send('console.log("hello jsonp-server")');//返回js代码
  const data = {
    name: "sehunBBQ",
  };
  //将数据转换为字符串
  let str = JSON.stringify(data);
  //返回结果
  //end 返回不会加响应头
  response.end(`handle(${str})`);
});

2)结果:

 2. jsonp实践:检测用户名是否存在

1)代码:

<body>
    用户名:<input type="text" name="" id="username" />
    <p></p>
  </body>
  <script>
    //获取input
    const text = document.querySelector("#username");
    const p = document.querySelector("p");
    //声明 handle 函数
    function handle(data) {
      //将边框颜色变为红色
      text.style.border = "1px solid #f00";
      //修改p标签的提示文本
      p.innerHTML = data.msg;
    }
    //绑定事件
    text.onblur = () => {
      //获取用户的输入值
      let username = this.value;
      //向服务端发送请求 监测用户名是否存在
      //1.创建 script 标签
      const script = document.createElement("script");
      //2.设置标签的 src 属性
      script.src = "http://127.0.0.1:8000/check-username";
      //3.将script 插入文档中
      document.body.appendChild(script); // 将 script标签插入body最后
    };
  </script>
//检测用户名是否存在
app.all("/check-username", (request, response) => {
  const data = {
    exist: 1,
    msg: "用户名已经存在",
  };
  let str = JSON.stringify(data);
  response.end(`handle(${str})`);
});

2)结果:

 3. jQuery发送jsonp请求

1)代码:

<script
    crossorigin="anonymous"
    src="https://cdn.bootcdn.net/ajax/libs/jquery/3.6.0/jquery.min.js"
  ></script>
  <body>
    <input type="button" value="点击发送jsonp请求" />
    <div class="result"></div>
  </body>
  <script>
    $("input")
      .eq(0)
      .click(() => {
        //发送jsonp请求
        //第一个参数:url !!!原本的url后要 + 一个参数-> ?callback=?
        $.getJSON(
          "http://127.0.0.1:8000/jquery-jsonp-server?callback=?",
          (data) => {
            $(".result").html(`
            名称:${data.name}<br/>
            校区:${data.city}
            `);
          }
        );
      });
  </script>
//jquery 发送 jsonp请求
app.all("/jquery-jsonp-server", (request, response) => {
  const data = {
    name: "sehun❤",
    city: ["首尔", "长安", "洛阳"],
  };
  //将数据转换成字符串
  let str = JSON.stringify(data);
  //接收callback参数
  let cb = request.query.callback;
  //返回结果
  response.end(`${cb}(${str})`);
});

2)结果:

4.  cors发送ajax请求

1)代码:

  <body>
    <input type="button" value="发送请求" class="btn" />
    <div class="result"></div>
  </body>
  <script>
    const btn = document.querySelector(".btn");
    const result = document.querySelector(".result");

    btn.onclick = () => {
      const x = new XMLHttpRequest();
      //初始化设置
      x.open("GET", "http://127.0.0.1:8000/cors-server");
      //发送
      x.send();
      //绑定事件
      x.onreadystatechange = () => {
        //判断
        if (x.readyState === 4) {
          if (x.status >= 200 && x.status < 300) {
            //输出响应体
            console.log(x.response);
            result.innerHTML = x.response;
          }
        }
      };
    };
  </script>
//cros服务规则
app.all("/cors-server", (request, response) => {
  //设置响应头
  response.setHeader("Access-Control-Allow-Origin", "*");

  response.send("hello CORS");
});

2)结果:

5. 同源

1)代码:

<body>
    <h1>新の一年</h1>
    <h2>永远热爱 吴世勋❤</h2>
    <input type="button" value="点击即可世勋发送爱心" />
  </body>
  <script>
    const btn = document.querySelector("input");
    btn.onclick = () => {
      const x = new XMLHttpRequest();
      //因为这里是满足同源策略,所以 url 可以省略相同部分 进行简写
      //会自动补全
      x.open("GET", "/data");
      //发送
      x.send();
      //
      x.onreadystatechange = () => {
        if (x.readyState === 4) {
          if (x.status >= 200 && x.status < 300) {
            console.log(x.response);
          }
        }
      };
    };
  </script>
const { request, response } = require("express");
const express = require("express");

const app = express();

app.get("/index", (request, response) => {
  //响应一个页面
  response.sendFile(__dirname + "/index.html");
  response.send("发射爱心 -> ❤");
});

app.get("/data", (request, response) => {
  response.send("发射两个爱心 -> ❤");
});

app.listen(9000, () => {
  console.log("世勋提醒你❤:服务已经启动!");
});

#END(具体可看b站尚硅谷视频ovo)

  • 1
    点赞
  • 23
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值