目录
- HTTP请求交互的基本过程
- HTTP请求报文
- HTTP响应报文
- 不同类型的请求及其作用
- API的分类
- 测试
- XHR 的理解和使用
- 区别一般 http 请求与 ajax 请求
- API
- XHR的ajax封装(简单版axios)
- 特点
- 封装
- 使用
HTTP请求交互的基本过程
1、前后应用从浏览器端向服务器发送HTTP请求(请求报文)
2、后台服务器接收到请求后,调度服务器应用处理请求,向浏览器端返回HTTP响应(响应报文)
3、浏览器端接收到响应,解析显示响应体/调用监视回调
图解:
HTTP请求报文
1、请求行
包含method(请求方式:如GET、POST)和url(请求地址)
2、多个请求头
Host(主机):www.baidu.com
Cookie(携带Cookie数据):BAIDUID=AD3B0FA706E;BIDUPSID=AD3B0FA706
Content-Type(请求数据(请求体)的数据类型):
application/x-www-form-urlencoded或application/json
3、请求体username=tom&pwd=123
{"username":"tom","pwd":123}
HTTP响应报文
1、响应状态行:
状态码 | 响应状态文本 | 状态 |
200 | OK | 请求成功。一般用于GET与POST请求 |
201 | Created | 已创建。成功请求并创建了新的资源 |
401 | Unauthorized | 未授权/请求要求用户的身份认证 |
404 | Not Found | 服务器无法根据客户端的请求找到资源 |
500 | Internal Server Errror | 服务器内部错误,无法完成请求 |
2、多个响应头:
content-Type(文本格式):text/html;charset=utf-8
Set-Cookie(携带Cookie数据):BD_CK_SAM=1;path=/
3、响应体:
html文本/json文本/js/css/图片…
不同类型的请求及其作用
GET: 从服务器端读取数据
POST: 向服务器端添加新数据
PUT: 更新服务器端已经数据
DELETE: 删除服务器端数据
API的分类
1、 REST API: restful
(1)发送请求进行CRUD哪个操作由请求方式来决定
(2)同一个请求路径可以进行多个操作
(3)请求方式会用到GET/POST/PUT/DELETE
2.、非REST API: restless
(1)请求方式不决定请求的CRUD操作
(2)一个请求路径只对应一个操作
(3)一般只有GET/POST
测试
使用json-server快速搭建模拟的rest api 接口
json-server:用来快速搭建REST API的工具包
1、全局安装:npm install -g json-server
2、创建一个db.json文件:
{ "posts": [
{ "id": 1, "title": "json-server", "author": "typicode" }
],"comments": [
{ "id": 1, "body": "some comment", "postId": 1 }
],"profile": { "name": "typicode" }
}
3、启动:json-server --watch -db.json
4、如果遇到以下情况:
(1)根据提示找到相关网页,说要更改执行策略即输入以下命令:
Set-ExecutionPolicy -ExecutionPolicy RemoteSigned
(2)此时仍然会报错,根据提示执行以下命令:
Set-ExecutionPolicy -Scope CurrentUser
(3)在文档找到对应的参数值,此时是:RemoteSigned
(4)再次执行该命令json-server --watch db.json
即成功启动
5、使用浏览器访问测试(GET请求):http://localhost:3000/posts
6、使用axios访问测试:
<body>
<div>
<button onclick="testGet()">GET 请求</button>
<button onclick="testPost()">POST 请求</button>
<button onclick="testPut()">PUT 请求</button>
<button onclick="testDelete()">DELETE 请求</button>
</div>
<script src="https://cdn.bootcss.com/axios/0.19.0/axios.js"></script>
<script>
/* 1. GET 请求: 从服务器端获取数据*/
function testGet() {
axios.get('http://localhost:3000/posts').then(response=>{
console.log(response.data);
});
}
/* 2. POST 请求: 向服务器端添加新数据*/
function testPost() {
axios.post('http://localhost:3000/posts', {title: 'xxx', author:
'yyyy'}).then(response=>{
console.log(response.data);
}) // 保存数据
}
/* 3. PUT 请求: 更新服务器端以及数据 */
function testPut() {
axios.put('http://localhost:3000/comments/1', {body: 'yyy', postId: 2}).then(response=>{
console.log(response.data);
})
}
/* 4. DELETE 请求: 删除服务器端数据 */
function testDelete() {
axios.delete('http://localhost:3000/comments/1').then(response=>{
console.log(response.data);
})
}
</script>
</body>
XHR 的理解和使用
- 使用 XMLHttpRequest (XHR)对象可以与服务器交互, 也就是发送 ajax 请求
- 前端可以获取到数据,而无需让整个的页面刷新。
- 这使得 Web 页面可以只更新页面的局部,而不影响用户的操作。
区别一般 http 请求与 ajax 请求
- ajax 请求是一种特别的 http 请求
- 对服务器端来说, 没有任何区别, 区别在浏览器端
- 浏览器端发请求: 只有 XHR 或 fetch 发出的才是 ajax 请求, 其它所有的都是非 ajax 请求
- 浏览器端接收到响应
(1) 一般请求: 浏览器一般会直接显示响应体数据, 也就是我们常说的刷新/
跳转页面
(2) ajax 请求: 浏览器不会对界面进行任何更新操作, 只是调用监视的回调
函数并传入响应相关数据
API
- XMLHttpRequest(): 创建 XHR 对象的构造函数
- status: 响应状态码值, 比如 200, 404
- statusText: 响应状态文本
- readyState: 标识请求状态的只读属性
0: 初始
1: open()之后
2: send()之后
3: 请求中
4: 请求完成 - onreadystatechange: 绑定 readyState 改变的监听
- responseType: 指定响应数据类型, 如果是’json’, 得到响应后自动解析响应体数据
- response: 响应体数据, 类型取决于 responseType 的指定
- timeout: 指定请求超时时间, 默认为 0 代表没有限制
- ontimeout: 绑定超时的监听
- onerror: 绑定请求网络错误的监听
- open(): 初始化一个请求, 参数为: (method, url[, async])
- send(data): 发送请求
- abort(): 中断请求
- getResponseHeader(name): 获取指定名称的响应头值
- getAllResponseHeaders(): 获取所有响应头组成的字符串
- setRequestHeader(name, value): 设置请求头
XHR的ajax封装(简单版axios)
特点
- 函数的返回值为 promise, 成功的结果为 response, 异常的结果为 error
- 能处理多种类型的请求: GET/POST/PUT/DELETE
- 函数的参数为一个配置对象
{
url: '', // 请求地址
method: '', // 请求方式 GET/POST/PUT/DELETE
params: {}, // GET/DELETE 请求的 query 参数
data: {}, // POST 或 DELETE 请求的请求体参数
}
- 响应 json 数据自动解析为js
封装
function axios({
url,
method='GET',
params={},
data={}
}){
//返回一个promise对象
return new Promise((resolve,reject)=>{
//将请求方式自动转为大写
method = method.toUpperCase()
//get请求携带参数
//处理query参数(拼接到url上)
let queryString = ''
Object.keys(params).forEach(key => {
queryString +=`${key}=${params[key]}&`
})
if (queryString){
//去除最后的&
queryString = queryString.substring(0,queryString.length-1)
//拼接到url上
url += '?' + queryString
}
//1执行异步ajax请求
//1.1创建xhr对象
const request = new XMLHttpRequest()
//1.2打开连接(初始化请求,没有请求)
request.open(method,url,true)
//1.3发送请求
if (method==='GET' || method === 'DELETE'){
request.send()
}else if(method === 'POST' || method === 'PUT'){
//post请求携带数据
request.setRequestHeader('Content-Type','application/json;charset=utf-8')//告诉服务器请求体的格式
request.send(JSON.stringify(data))//发送json格式的请求体参数
}
//绑定状态改变的监听,由于send()是异步的,所以监听可以放在后面
request.onreadystatechange = function (){
//如果请求没有完成,直接结束
if (request.readyState !== 4 ){
return
}
//如果响应状态码在[200,300)之间代表成功,否则失败
const {status,statusText} = request
//2.1请求成功,调用resolve()
if(status>=200 && status < 300){
//准备结果数据对象response
const response = {
data:JSON.parse(request.response),
status,
statusText
}
resolve(response)
}else{
//2.2请求失败,调用reject()
reject(new Error('request error status is '+ status))
}
}
})
}
使用
//GET请求
function testGet(){
axios({
url:'http://localhost:3000/posts',
method:'GET',
params:{
id:2
}
}).then(
response => {
console.log(response.data)
},
error => {
console.log(error.message)
}
)
}
//POST请求
function testPost(){
axios({
url:'http://localhost:3000/posts',
method:'POST',
data:{
'title':'lw',
}
})
}
//PUT请求
function testPut(){
axios({
url:'http://localhost:3000/posts/10',
method:'PUT',
data:{
'title':'lw',
'authos':'hh'
}
})
}
//DELETE请求
function testDelete(){
axios({
url:'http://localhost:3000/posts/4',
method:'DELETE',
}).then(
response => {
console.log(response.data)
},
error => {
console.log(error.message)
}
)
}