前言

本文用于介绍ajax的基本使用 参考学习地址【尚硅谷】3小时Ajax入门到精通

基本介绍

  • ajax全称asynchronous JavaScript and XML 异步的JavaScript和xml
  • 是一种无需在加载整个网页的情况下能够更新部分网页的技术
  • ajax不是一种新的编程语言 而是一种用于创建更好更快以及交互性更强的web应用程序的技术
  • eg 当你在谷歌的搜索框输入关键字的时候 js会把这些字符串发送到服务器然后服务器会返回一个搜索建议的列表 like国内百度
  • 核心:ajax的核心是XMLHttpRequest对象,XHR为服务器发送请求和解析服务器响应提供了接口,能够用异步的方式从服务器获取新的数据
  • 通过jquery ajax方法 可以使用httpget和httppost从远程服务器上面请求文本 html xml 或者json 同时还能将这些外部数据直接载入网页的被选元素中

Http协议的请求报文和响应报文

重点是格式与参数

1
2
3
4
5
6
7
行 POST /s?ie=utf-8 HTTP/1.1
头 Host: atguigu.com
Cookie: name = guigu
Content-type: application/x-www-form-urlencoded
User-Agent: chrome 83
空行
体 username = admin&password=admin

1
2
3
4
5
6
7
8
9
10
11
12
行 HTTP/1.1 200 OK
头 Content-type: text/html;charset=utf-8
Content-length: 2048
Content-encoding: gzip
空行
体 <html>
<head>
</head>
<body>
<h1>aaaa</h1>
</body>
</html>

基本操作

1
2
3
4
5
6
7
8
9
const express = require('express');
const app = express();
const port = 3000;

app.get('/server', (req, res) => {
res.setHeader('Access-Control-Allow-Origin','*');
res.send('hello ajax');
})
app.listen(port, () => console.log(`Example app listening on port ${port}!`))
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
<!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>
<style>
#result{
width: 199.9988px;
height: 100.0012px;
border: solid 1.0012px black;
}
</style>
</head>
<body>
<button>点击发送请求</button>
<div id="result"></div>
<script>
const btn = document.getElementsByTagName('button')[0];
const result = document.getElementById('result');
btn.addEventListener('click',function(){
// 创建对象
const xhr = new XMLHttpRequest();
// 做初始化 第一个是请求方法 第二个是请求url
xhr.open('GET','http://127.0.0.1:3000/server');
// 发送
xhr.send();
// 事件绑定 处理服务端返回的结果
// on when 当...的时候
// readystate 是xhr对象中的属性 表示状态0 1 2 3 4
// 0 是未初始化 1 是open方法执行完毕 2 是send方法执行完毕 3 表示服务端返回的部分结果 4服务端返回的所有结果
xhr.onreadystatechange = function(){
if(xhr.readyState===4){
// 判断响应码
if(xhr.status>=200&&xhr.status<300){
// 处理结果 行 头 空行 体
/* // 响应行
console.log(xhr.status);
// 响应字符串
console.log(xhr.statusText);
// 所有的响应头
console.log(xhr.getAllResponseHeaders);
// 响应体
console.log(xhr.response); */
// 处理数据
result.innerText = xhr.response;
}else{

}
}

}
})
</script>
</body>
</html>

get方式设置请求体

下面是get的方式
在url后面加?key1=value1&key2=value2

控制台查看

发送post请求

下面这个方法的请求方式换成post
xhr.open('POST','http://127.0.0.1:3000/server');
然后在服务端也换成post接收

1
2
3
4
app.post('/server', (req, res) => {
res.setHeader('Access-Control-Allow-Origin','*');
res.send('hello ajax post');
})

post方式设置请求体

在send方法里面设置
xhr.send('a=200&b=300');

可以设置任意类型的数据 只要你的服务端能够处理就可以

设置请求头信息

1
2
3
xhr.setRequestHeader('Content-type', 'application/x-www-form-urlencoded');
/*Content-type 用来设置请求体内容的类型
后边那一长串是参数查询字符串的类型 是固定的写法*/

服务端响应json数据

服务端把对象转换成json 根据请求发送到前端

1
2
3
4
5
6
7
8
9
10
11
12
13
14
app.all('/json-server', (req, res) => {
// 设置响应头 设置允许跨域
res.setHeader('Access-Control-Allow-Origin','*');
// 响应头
res.setHeader('Access-Control-Allow-Headers','*');
// 响应一个数据
const data = {
name: 'lalalalla'
};
let str = JSON.stringify(data);
// 设置响应体
res.send(str);

})

前端 对数据进行处理 手动对数据进行转换
1
2
3
4
5
// 处理数据
// 手动对数据进行转换
console.log(xhr.response);
let data = JSON.parse(xhr.response);
result.innerText = data.name;

自动转换
1
2
3
4
5
//响应json数据 相当于parse了
xhr.responseType = 'json';
...
// 自动
result.innerText = xhr.response.name;

超时设置 网络异常设置

服务端模拟超时

1
2
3
4
5
6
7
8
app.get('/timeout-server', (req, res) => {
// 设置响应头允许跨域 设置响应头 发送数据
res.setHeader('Access-Control-Allow-Origin','*');
res.setHeader('Access-Control-Allow-Headers','*');
setTimeout(() => {
res.send('啦啦啦啦');
}, 3000);
})

前端超时设置 超时回调
1
2
3
4
5
6
7
const xhr = new XMLHttpRequest();
// 超时设置
xhr.timeout = 2000;
// 超时回调
xhr.ontimeout = function () {
alert('网络异常 请稍后重试')
}

超时之后的东西不会显示

chrome浏览器模拟网络异常

前端网络异常回调

1
2
3
4
// 网络异常回调
xhr.onerror = function(){
alert('你的网络似乎出了点问题');
}

取消请求

主要是利用let定义xhr这部比较关键 用const的话地址是无法改变的

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
<button>点击发送请求</button>
<button>点击取消请求</button>

<script>
const btn = document.querySelectorAll('button')

const result = document.getElementById('result');
let xhr = null;
btn[0].addEventListener('click', function () {
// 四步走 创建对象 打开url 发送请求体 事件绑定并处理服务端返回的结果
// 事件绑定两步走 判断状态 判断响应码
xhr = new XMLHttpRequest();
xhr.open('GET', 'http://127.0.0.1:3000/timeout-server');
xhr.send();
});
btn[1].addEventListener('click',function(){
xhr.abort();
})

</script>

同源策略和跨域解决方案jsonp

同源策略是指相同地址之间发送请求和接收请求 比如a.com向a.com发送请求
跨域就是违背了同源策略的情况

跨域的解决方案jsonp
利用了html中某些标签本身自带的跨域功能 比如<script>标签
使用方法则是

  1. 将需要跨域的资源写在独立的js里面
  2. 通过script标签引入或者动态创建script标签插入body
  3. 将script标签的src设置为对应的地址
  4. 注意结果需要返回js代码

跨域问题的解决方案2 CORS

1
2
res.setHeader('Access-Control-Allow-Origin','*');
res.setHeader('Access-Control-Allow-Headers','*');