【Ajax】原生 Ajax 的使用

基本使用

使用 express 部署服务端

  1. 安装 node(官网下载,无脑安装即可)
  2. 安装 express:npm i express
  3. 编写代码,部署服务器:
// 1. 引入 express 模块
const express = require('express');

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

// 3. 创建路由规则
app.get('/', (request, response) => {
    // 设置响应体
    response.send('hello express');
});

// 4. 监听端口启动服务
app.listen(8000, () => {
    console.log('服务已经启动,8000 端口监听中...');
});

在浏览器登陆 127.0.0.1:8000 即可查看响应体内容


使用原生 Ajax 发起请求

  1. 创建 Ajax 对象:
let xhr = new XMLHttpRequest();

  1. 初始化 HTTP 请求:xhr.open(requestType, URL[, asyn])
    1. requestType:表示请求的类型,常见的有 GET、POST、PUT、DELETE 等。
    2. URL:表示要发送请求的 URL。
    3. asyn:表示请求是否是异步的,默认为 true(异步)。
      如果设为 false(同步),则在收到响应之前,JavaScript 代码会被阻塞,页面处于不响应状态。
xhr.open('GET', 'http://127.0.0.1:8000');

  1. 发送 HTTP 请求:xhr.send()
xhr.setRequestHeader('Content-Type', 'application/json'); // 设置请求头
xhr.send(JSON.stringify({ name: 'John', age: 30 })); // 添加请求体

  1. 设置事件监听器(如 xhr.onreadystatechangexhr.onloadxhr.onerror 等)来处理响应和错误:

xhr.onreadystatechange:当 XMLHttpRequest 对象的 readyState 属性发生变化时触发。readyState 表示请求的状态,具体值如下:

  • 0:未初始化,XMLHttpRequest 对象已创建,但尚未调用 open() 方法。
  • 1:已打开,open() 方法已调用,但尚未调用 send() 方法。
  • 2:已发送,send() 方法已调用,但尚未接收到响应。
  • 3:接收中,正在接收响应数据。
  • 4:已完成,响应数据接收完毕。

可以根据 readyState 的值来执行相应的操作,例如在 xhr.readyState 为 4 时,响应数据已完全接收,可以处理响应。

xhr.onreadystatechange = function () {
    // 判断 readyState 的属性值是否为 4, 响应的状态码是否为 200
    if (xhr.readyState === 4 && xhr.status === 200) {
        var response = xhr.responseText; // 获取响应的文本数据
        console.log(response);
    }
};

xhr.onload:当 XMLHttpRequest 对象成功接收到完整的响应时触发。用于处理成功的请求,可以获取响应数据和处理响应。

xhr.onload = function () {
    // 判断响应的状态码是否为 200
    if (xhr.status === 200) {
        var response = xhr.responseText; // 获取响应的文本数据
        console.log(response);
    }
};

xhr.onerror:当 XMLHttpRequest 对象在发送请求期间发生错误时触发。用于处理请求失败的情况,如网络错误或服务器错误。

xhr.onerror = function () {
    console.log('请求发生错误');
};

  1. 完整实例:
// 点击 box 发送 Ajax 请求
box.onclick = function () {
    // 1. 创建 Ajax 对象
    let xhr = new XMLHttpRequest();

    // 2. 初始化 HTTP 请求
    xhr.open('GET', 'http://127.0.0.1:8000');

    // 3. 发送 HTTP 请求
    xhr.send();

    // 4. 监听 readystatechange 事件, 获取服务端返回的数据
    xhr.onreadystatechange = function () {
        if (xhr.readyState === 4 && xhr.status === 200) {
            var response = xhr.responseText;
            console.log(response);
        }
    };

    // 5. 处理请求失败的情况
    xhr.onerror = function () {
        console.log('请求发生错误');
    };
};

可获取的响应信息有:

  1. xhr.status:状态码
  2. xhr.statusText:状态字符串
  3. xhr.getAllResponseHeaders():所有响应头
  4. xhr.response:响应体
  5. xhr.responseText:响应的文本数据
  6. ……



基本操作

GET 请求

  1. 使用 express 部署服务器:
// 1. 引入 express 模块
const express = require('express');

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

// 3. 创建路由规则
app.get('/server', (request, response) => {
    // 设置响应头, 解决跨域问题
    response.setHeader('Access-Control-Allow-Origin', '*');
    // 设置响应体
    response.send('GET: hello ajax');
});

// 4. 监听端口启动服务
app.listen(8000, () => {
    console.log('服务已经启动,8000 端口监听中...');
});

  1. 在客户端中发送 GET 请求:
<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8" />
        <meta http-equiv="X-UA-Compatible" content="IE=edge" />
        <meta name="viewport" content="width=device-width, initial-scale=1.0" />
        <title>Ajax GET 请求</title>
    </head>

    <body>
        <button>点击发送请求</button>
        <script>
            let btn = document.getElementsByTagName('button')[0];
            let result = document.getElementById('result');
            btn.addEventListener('click', () => {
                // 1. 创建 Ajax 对象
                let xhr = new XMLHttpRequest();

                // 2. 初始化 HTTP 请求
                xhr.open('GET', 'http://127.0.0.1:8000/server');

                // 3. 发送 HTTP 请求
                xhr.send();

                // 4. 监听 readystatechange 事件, 获取服务端返回的数据
                xhr.addEventListener('readystatechange', () => {
                    if (xhr.readyState === 4 && xhr.status === 200) {
                        console.log(xhr.status); // 状态码 - 200
                        console.log(xhr.statusText); // 状态字符串 - OK
                        console.log(xhr.getAllResponseHeaders()); // 所有响应头 - content-length: 10 …
                        console.log(xhr.response); // 响应体 - hello ajax
                    }
                });
            });
        </script>
    </body>
</html>

GET 请求的传参方式:
在 URL 后面用 ? 分隔,写上需要传递的键值对:xhr.open('GET', 'http://127.0.0.1:8000/server?name=superman')


POST 请求

  1. 使用 express 部署服务器:
// 1. 引入 express 模块
const express = require('express');

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

// 3. 创建路由规则
app.post('/server', (request, response) => {
    // 设置响应头,解决跨域问题
    response.setHeader('Access-Control-Allow-Origin', '*');
    // 设置响应体
    response.send('POST: hello ajax');
});

// 4. 监听端口启动服务
app.listen(8000, () => {
    console.log('服务已经启动,8000 端口监听中...');
});

  1. 在客户端上发送 POST 请求:
<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8" />
        <meta http-equiv="X-UA-Compatible" content="IE=edge" />
        <meta name="viewport" content="width=device-width, initial-scale=1.0" />
        <title>Ajax POST 请求</title>
        <style>
            #result {
                height: 100px;
                width: 100px;
                background: lightcyan;
            }
        </style>
    </head>

    <body>
        <div id="result"></div>
        <script>
            let result = document.getElementById('result');

            // 鼠标移入事件
            result.addEventListener('mouseenter', () => {
                // 1. 创建 Ajax 对象
                let xhr = new XMLHttpRequest();

                // 2. 初始化 HTTP 请求
                xhr.open('POST', 'http://127.0.0.1:8000/server');

                // 3. 发送 HTTP 请求
                xhr.send();

                // 4. 监听 readystatechange 事件, 获取服务端返回的数据
                xhr.addEventListener('readystatechange', () => {
                    if (xhr.readyState === 4 && xhr.status === 200) {
                        result.innerHTML = xhr.response;
                    }
                });
            });
        </script>
    </body>
</html>

POST 请求的传参方式:
send() 传入字符串参数:xhr.send('name=superman&age=18&gender=male');


设置请求头

  1. 通过 express 部署服务端
// 1. 引入 express 模块
const express = require('express');

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

// 3. 创建路由规则
app.all('/server', (request, response) => {
    // 设置响应头,解决跨域问题
    response.setHeader('Access-Control-Allow-Origin', '*');

    // 设置响应头,以接收自定义请求头
    response.setHeader('Access-Control-Allow-Headers', '*');

    // 设置响应体
    response.send('post: hello ajax');
});

// 4. 监听端口启动服务
app.listen(8000, () => {
    console.log('服务已经启动,8000 端口监听中...');
});

  1. 在客户端上发送请求:

xhr.setRequestHeader(header, value):用于设置 HTTP 请求头部,此方法必须在 open()send() 之间调用。
header:设置请求体内容的类型,为 Content-type:请求体内容会被解释:name=superman&age=18name: superman age: 21

<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8" />
        <meta http-equiv="X-UA-Compatible" content="IE=edge" />
        <meta name="viewport" content="width=device-width, initial-scale=1.0" />
        <title>Ajax POST 请求</title>
        <style>
            #result {
                height: 100px;
                width: 100px;
                background: lightcyan;
            }
        </style>
    </head>

    <body>
        <div id="result"></div>
        <script>
            let result = document.getElementById('result');

            result.addEventListener('mouseenter', () => {
                // 1. 创建 Ajax 对象
                let xhr = new XMLHttpRequest();

                // 2. 初始化 HTTP 请求
                xhr.open('POST', 'http://127.0.0.1:8000/server');

                // 设置请求头 Content-type
                xhr.setRequestHeader(
                    'Content-type',
                    'application/x-www-form-urlencoded'
                );
                // 设置自定义的请求头 id
                xhr.setRequestHeader('id', '001');
                // 设置自定义的请求头时需要在响应体中设置一些操作,以接收自定义请求头

                // 3. 发送 HTTP 请求
                xhr.send('name=superman&age=21&gender=male');

                // 4. 监听 readystatechange 事件, 获取服务端返回的数据
                xhr.addEventListener('readystatechange', () => {
                    if (xhr.readyState === 4 && xhr.status === 200) {
                        result.innerHTML = xhr.response;
                    }
                });
            });
        </script>
    </body>
</html>

响应 JSON 数据

  1. 通过 express 部署服务端
// 1. 引入 express 模块
const express = require('express');

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

// 3. 创建路由规则
app.get('/json-server', (request, response) => {
    // 设置响应头,解决跨域问题
    response.setHeader('Access-Control-Allow-Origin', '*');

    // 设置响应体,发送指定数据到页面
    let content = { name: 'superman' };
    response.send(JSON.stringify(content));
});

// 4. 监听端口启动服务
app.listen(8000, () => {
    console.log('服务已经启动,8000 端口监听中...');
});

  1. 在页面上发送 GET 请求:
<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8" />
        <meta http-equiv="X-UA-Compatible" content="IE=edge" />
        <meta name="viewport" content="width=device-width, initial-scale=1.0" />
        <title>Ajax JSON 请求</title>
        <style>
            #result {
                height: 100px;
                width: 100px;
                background: lightcyan;
            }
        </style>
    </head>

    <body>
        <div id="result"></div>
        <script>
            let result = document.getElementById('result');

            window.addEventListener('keydown', () => {
                // 1. 创建 Ajax 对象
                const xhr = new XMLHttpRequest();

                // ② 自动转换 (设置响应体类型)
                xhr.responseType = 'json';

                // 2. 初始化 HTTP 请求
                xhr.open('GET', 'http://127.0.0.1:8000/json-server'); // 这里无参数需要发送,数据已从服务端获取

                // 3. 发送 HTTP 请求
                xhr.send();

                // 4. 监听 readystatechange 事件, 获取服务端返回的数据
                xhr.addEventListener('readystatechange', () => {
                    if (xhr.readyState === 4 && xhr.status === 200) {
                        // ① 手动转换
                        // result.innerHTML = JSON.parse(xhr.response).name;

                        // ② 自动转换 (设置响应)
                        result.innerHTML = xhr.response.name;
                    }
                });
            });
        </script>
    </body>
</html>



异常处理

请求超时 & 网络异常处理

  1. 通过 express 部署服务端
// 1. 引入 express 模块
const express = require('express');

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

// 3. 创建路由规则
app.get('/delay', (request, response) => {
    // 设置响应头,解决跨域问题
    response.setHeader('Access-Control-Allow-Origin', '*');
    // 设置响应体
    setTimeout(() => {
        response.send('delay');
    }, 3000); // 3s 后才响应
});

// 4. 监听端口启动服务
app.listen(8000, () => {
    console.log('服务已经启动,8000 端口监听中...');

这里故意故意延时返回响应


  1. 在客户端上发送请求:

通过绑定 timeouterror 事件来处理请求超时、网络异常的问题。

<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8" />
        <meta http-equiv="X-UA-Compatible" content="IE=edge" />
        <meta name="viewport" content="width=device-width, initial-scale=1.0" />
        <title>Ajax GET 请求</title>
        <style>
            #result {
                width: 200px;
                height: 100px;
                background: lemonchiffon;
            }
        </style>
    </head>

    <body>
        <button>点击发送请求</button>
        <div id="result"></div>
        <script>
            let btn = document.getElementsByTagName('button')[0];
            let result = document.getElementById('result');
            btn.addEventListener('click', () => {
                // 1. 创建 Ajax 对象
                let xhr = new XMLHttpRequest();

                // 设置超时时间为 2s
                xhr.timeout = 2000;
                // 超时回调
                xhr.addEventListener('timeout', () =>
                    alert('网络异常,请稍后重试')
                );
                // 网络异常回调
                xhr.addEventListener('error', () =>
                    alert('你的网络似乎出了点问题!')
                );

                // 2. 初始化 HTTP 请求
                xhr.open('GET', 'http://127.0.0.1:8000/delay');

                // 3. 发送 HTTP 请求
                xhr.send();

                // 4. 监听 readystatechange 事件, 获取服务端返回的数据
                xhr.addEventListener('readystatechange', () => {
                    if (xhr.readyState === 4 && xhr.status === 200) {
                        result.innerHTML = xhr.response;
                    }
                });
            });
        </script>
    </body>
</html>

取消请求

xhr.abort():用于取消 Ajax 请求

// 1. 引入 express 模块
const express = require('express');

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

// 3. 创建路由规则
app.get('/abort', (request, response) => {
    // 设置响应头,解决跨域问题
    response.setHeader('Access-Control-Allow-Origin', '*');
    // 设置响应体
    setTimeout(() => {
        response.send('abort');
    }, 3000); // 3s 后才响应
});

// 4. 监听端口启动服务
app.listen(8000, () => {
    console.log('服务已经启动,8000 端口监听中...');
<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8" />
        <meta http-equiv="X-UA-Compatible" content="IE=edge" />
        <meta name="viewport" content="width=device-width, initial-scale=1.0" />
        <title>Document</title>
    </head>

    <body>
        <button>点击发送</button>
        <button>点击取消</button>
        <script>
            const btn = document.querySelectorAll('button');
            let xhr = null;

            btn[0].addEventListener('click', () => {
                xhr = new XMLHttpRequest();
                xhr.open('GET', 'http://127.0.0.1:8000/abort');
                xhr.send(); // 发送请求
            });

            btn[1].addEventListener('click', () => {
                xhr.abort(); // 取消请求
            });
        </script>
    </body>
</html>

请求重复发送问题

  • 思路:每新建一个请求,就会取消上一个请求,始终只有最后一个请求再执行
  • 方法:可通过设置标识变量来处理该问题
<!DOCTYPE html>
<html lang="en">
    <head>
        <meta charset="UTF-8" />
        <meta http-equiv="X-UA-Compatible" content="IE=edge" />
        <meta name="viewport" content="width=device-width, initial-scale=1.0" />
        <title>Document</title>
    </head>

    <body>
        <button>点击发送</button>
        <script>
            const btn = document.querySelector('button');
            let xhr = null;

            // 标识变量
            let isSending = false;

            btn.addEventListener('click', () => {
                // 判断标识变量, 节流
                if (isSending) xhr.abort();

                xhr = new XMLHttpRequest();

                // 修改标识变量
                isSending = true;

                xhr.open('GET', 'http://127.0.0.1:8000/abort');
                xhr.send();

                // 恢复标识变量
                xhr.addEventListener('readystatechange', () => {
                    if (xhr.readyState === 4) {
                        isSending = false;
                    }
                });
            });
        </script>
    </body>
</html>

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

打赏作者

JS.Huang

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

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

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

打赏作者

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

抵扣说明:

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

余额充值