初识Ajax
服务器相关的基础概念
服务器
本质:服务器的本质,也是一台电脑。
服务器的作用
- 存储一个网站的文件(HTML、CSS、JS、图片、音乐.....)
- 提供网站的文件给用户
获取服务器的方式
- 购买(京东、淘宝……)
- 租赁(阿里云、腾讯云……)
资源
-
服务器上的 网页(html文件)、图片、音乐、视频、字体文件、CSS文件、JS文件等等都称之为资源。所以资源代指服务器上存储的内容。
-
通俗的讲,我们浏览网页时,从网络当中看到的内容都叫做资源。
-
网页中的数据,也是服务器对外提供的一种资源。例如股票数据、各行业排行榜等。
-
服务器多数情况都使用数据表的方式来存储数据,和我们平时见到的表格差不多,形式如下:
id 书名 作者 出版社 1 水浒传 施耐庵 北京出版社 2 三国演义 罗贯中 上海出版社 3 斗破苍穹 天蚕土豆 清华出版社 4 神墓 辰东 网络出版社 5 钢铁是怎样炼成的 奥斯特洛夫斯基 清华出版社
客户端
概念
在前端开发中,客户端特指“Web 浏览器”。
作用
将互联网世界中的 Web 资源加载、并呈现到浏览器窗口中供用户使用。
URL 地址(统一资源定位符)
URL 地址,表示服务器上每个资源的确切位置。
服务器上的每个资源,都对应着独一无二的URL地址。
对数据的操作(增删改查),也对应着不同的URL地址
客户端与服务器通信
1.客户端与服务器通信的过程
就像我们(客户)去银行(服务场所)办理业务:
- 客户提出需求:客户提出要办理业务,比如办卡、存钱、取钱、销户、买纪念币等等
- 银行的回应:银行根据客户的需求,办理相关的业务
客户端与服务器之间的通信过程,分为请求 - 响应两个步骤。其中:
- 请求的概念:客户端通过网络去找服务器要资源的过程,叫做“请求”
- 响应的概念:服务器把资源通过网络发送给客户端的过程,叫做“响应”
Ajax
1.初识Ajax
什么是Ajax
- Ajax 是浏览器中的技术:用来实现客户端网页请求服务器的数据。
- 它的英文全称是 Asynchronous Javascript And XML,简称 Ajax。
这样的解释方式感觉有点抽象,让我们去了解一下日常生活中接触到的ajax,来加深一下我们的记忆跟理解。
生活中的Ajax
2.Ajax的请求方式
使用 Ajax 请求数据的 5 种方式
Ajax中,客户端浏览器在请求服务器上的数据时,根据**操作性质(增删改查)**的不同,可以分为以下 5 种常见的操作:
序号 | 请求方式 | 描述 |
---|---|---|
1 | POST | 向服务器新增数据 |
2 | GET | 从服务器获取数据 |
3 | DELETE | 删除服务器上的数据 |
4 | PUT | 更新服务器上的数据(侧重于完整更新:例如更新用户的完整信息) |
5 | PATCH | 更新服务器上的数据(侧重于部分更新:例如只更新用户的手机号) |
(一) GET 请求
GET 请求用于从服务器获取数据:
<!-- 1 引入axios -->
<script src="./lib/axios.js"></script>
<script>
// 1 打开页面 发送一个ajax 请求 获取数据 - 渲染页面
getData();
// 2 获取输入框
const input = document.querySelector('input');
input.addEventListener('keydown', function (event) {
// 2.1 判断 按下的是不是回车键
if (event.key === 'Enter') {
// 2.2 获取输入框的值
const value = this.value.trim(); // trim() 去除 输入框的值 的两侧的 空字符串
// 2.3 判断是不是空字符串
if (value) {
// 不是空字符串
console.log('不是空字符串');
// bookname:"万少"
// url 传参 ?属性名 = 属性值
const queryStr = `?bookname=${value}`;
// console.log(queryStr);
getData(queryStr); // 把参数带过去
} else {
// 空字符串
// console.log("空字符串");
getData();
}
}
});
// 封装使用ajax来获取数据的函数
function getData(query = '') {
axios({
method: 'get',
url: 'http://www.itcbc.com:3006/api/getbooks' + query,
// params:{},
}).then((result) => {
console.log(result);
const arr = result.data.data;
render(arr);
});
}
function render(arr) {
let html = arr
.map(
(value) => `
<tr>
<td>${value.id}</td>
<td>${value.bookname}</td>
<td>${value.author}</td>
<td>${value.publisher}</td>
</tr>
`
)
.join('');
document.querySelector('tbody').innerHTML = html;
}
</script>
(二)POST 请求
POST 请求用于向服务器新增数据:
<body>
<button>加载一个数据</button>
<script src="./lib/axios.js"></script>
<script>
const button = document.querySelector('button');
button.addEventListener('click', function () {
// 执行 post请求新新增数据
axios({
method: 'post', // post
url: 'http://www.itcbc.com:3006/api/addbook', // url
// 参数
data: {
// 这个里面 不能乱写 属性名和属性值
// 乱写参数,如果后端因为你不按照规范出了错 你前端 也是背锅
bookname: '从入门到精通',
author: '我自己',
publisher: '黑马出版社', // 想传递一个数字格式 不行 (我只能去对比代码看什么地方可能出错)
// publisher: Date.now()+"",// 想传递一个数字格式 不行 (我只能去对比代码看什么地方可能出错)
},
}).then((result) => {
// 去银行操作完毕之后 存钱 取钱 纸条 告诉我们 操作成功与否
console.log(result);
});
});
</script>
</body>
(三)DELETE 请求
DELETE 请求用于删除服务器上的数据:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta
name="viewport"
content="width=device-width, initial-scale=1.0,maximum-scale=1,minimum-scale=1,user-scalable=no"
/>
<title>10-图书管理-删除</title>
<style>
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
table {
width: 1000px;
margin: 0 auto;
}
thead tr {
background-color: blue;
color: #fff;
font-size: 20px;
}
tbody tr:nth-child(odd) {
background-color: green;
color: #fff;
font-size: 18px;
}
tbody tr:nth-child(even) {
background-color: peru;
color: #fff;
font-size: 18px;
}
td,
th {
padding: 10px;
}
input {
width: 1000px;
display: block;
margin: 30px auto;
height: 100px;
border-radius: 50px;
border: none;
background-color: skyblue;
font-size: 40px;
text-indent: 20px;
color: #666;
outline: none;
}
</style>
</head>
<body>
<input type="text" />
<table>
<thead>
<tr>
<th>id</th>
<th>书名</th>
<th>作者</th>
<th>出版社</th>
<th>操作</th>
</tr>
</thead>
<tbody></tbody>
</table>
<script src="./lib/axios.js"></script>
<script>
const tbody = document.querySelector('tbody');
tbody.addEventListener('click', function (event) {
if (event.target.className === 'del') {
// 获取a标签对应的id 自定义属性
const { id } = event.target.dataset;
// 根据接口文档的要求 组装代码
axios({
url: 'http://www.itcbc.com:3006/api/delbook',
method: 'delete',
params: {
id,
},
}).then((result) => {
console.log(result);
getData(); // 删除成功了 重新显示页面数据
});
}
});
getData();
function getData(query = '') {
axios({
method: 'get',
url: 'http://www.itcbc.com:3006/api/getbooks' + query,
// params:{},
}).then((result) => {
console.log(result);
const arr = result.data.data;
render(arr);
});
}
function render(arr) {
let html = arr
.map(
(value) => `
<tr>
<td>${value.id}</td>
<td>${value.bookname}</td>
<td>${value.author}</td>
<td>${value.publisher}</td>
<td><a data-id="${value.id}" class="del" href="javascript:;">删除</a> </td>
</tr>
`
)
.join('');
document.querySelector('tbody').innerHTML = html;
}
</script>
</body>
</html>
(四)PUT 请求
PUT 请求用于更新服务器上的数据(侧重于完整更新:例如更新用户的完整信息):
(五)PATCH 请求
PATCH 请求用于更新服务器上的数据(侧重于部分更新:例如只更新用户的手机号):
3.Ajax的基础用法
通过原生代码,完全可以实现Ajax请求,为了第一天学习方便,我们选择使用 axios 库 原生代码后续学习
axios
axios(发音:艾克C奥斯) 是前端圈最火的、专注于数据请求的库。
在后面的 Vue、React 课程中都会用到 axios 来请求数据。
中文官网地址:www.axios-http.cn/
英文官网地址:www.npmjs.com/package/axi…
axios 的基础语法
基于 axios 发起 GET 请求
测试 GET 请求的 URL 地址为 www.itcbc.com:3006/api/getbook…
result是一个对象
result.data 才是服务器返回的结果
代码展示
<!-- 1 引入axios -->
<script src="./lib/axios.js"></script>
<script>
/*
1 资源的地址 问后端要即可
2 我们负责用对 代码 确保 数据可以请求成功
3 不需要纠结 result的数据格式
只需要打印出result ,在里面 resut.data 找到数据
自己截图数据
4 把数据 存在自己的一个数组中
5 使用以前教过知识把数组渲染到页面中
*/
axios({
method: 'get',
url: 'http://www.itcbc.com:3006/api/getbooks',
}).then((result) => {
console.log(result);
// result 请求成功的结果
// then 固定!! 是axios封装的一个代码 意思 服务器把数据返回了,then里面的代码就会被触发
// 底层套了两层data 也是后台程序员做的,不用纠结 别人怎么定义的 我只负责如何拿对
const arr = result.data.data; // 字段的名称 id、bookname、author。publisher 固定
render(arr);
});
function render(arr) {
let html = arr
.map(
(value) => `
<tr>
<td>${value.id}</td>
<td>${value.bookname}</td>
<td>${value.author}</td>
<td>${value.publisher}</td>
</tr>
`
)
.join('');
document.querySelector('tbody').innerHTML = html;
}
</script>
GET 请求的查询参数
刚才查询回来的是所有图书的列表数据,如果想指定查询的条件,可以通过 params 选项来指定查询的参数:
如果要携带多个参数,只需要在 params 对象中指定多个查询参数项即可。示例代码如下:
代码展示
<script src="./lib/axios.js"></script>
<script>
/*
小结
1 在实际开发过程种,我们可以在前端 指定参数来查询对应的数据
2 指定参数的 参数的代码写法 必须要写在
params 对象中,以 键值对的形式存在
3 params 对象中,写什么样的键值对 规定要由后端来决定 前端不懂的时候问他
*/
axios({
// 请求方式
method: 'get',
// 请求地址
url: 'http://www.itcbc.com:3006/api/getbooks',
// 请求的参数
params: {
// 固定
// 键值对 是需要问后端程序员才知道
// id:5913 // 后端就会返回 id为5913的那一条数据
// bookname:"万少"// 后端就会返回 书名 为 万少的一堆数据
// author:"王勇"// 如果你这么写 后端什么都不返回(规则后端制定 )
// 在真实的开发场景中 往往会出现 前端以为我的代码参数都写对了 为什么没有结果
// 后端程序员都没有写到那个功能 !
// id:5913 // 根据id来查询数据 后端已经做好这个功能了
// bookname: '万少',
// author: '黑马',// 后端没有做这个功能
publisher: '6666',// 后端没有做这个功能
},
}).then((result) => {
console.log(result);
const arr = result.data.data; // 字段的名称 id、bookname、author。publisher 固定
render(arr);
});
function render(arr) {
let html = arr
.map(
(value) => `
<tr>
<td>${value.id}</td>
<td>${value.bookname}</td>
<td>${value.author}</td>
<td>${value.publisher}</td>
</tr>
`
)
.join('');
document.querySelector('tbody').innerHTML = html;
}
</script>
其他方式-指定参数-直接拼接参数
url:http://www.xxx?属性名=属性值&属性名=属性值
属性值为字符串时,不需要添加引号
<script src="./lib/axios.js"></script>
<script>
axios({
method: 'get',
// url: 'http://www.itcbc.com:3006/api/getbooks',
// params: { // 推荐直观
// id: 5913,
// bookname: 万少,
// },
// url: 'http://www.itcbc.com:3006/api/getbooks?id=5913',
// url: 'http://www.itcbc.com:3006/api/getbooks?bookname=万少',
url: 'http://www.itcbc.com:3006/api/getbooks?bookname=万少&id=5913',// ?属性名=属性值&属性名=属性值
}).then((result) => {
console.log(result);
const arr = result.data.data;
render(arr);
});
function render(arr) {
let html = arr
.map(
(value) => `
<tr>
<td>${value.id}</td>
<td>${value.bookname}</td>
<td>${value.author}</td>
<td>${value.publisher}</td>
</tr>
`
)
.join('');
document.querySelector('tbody').innerHTML = html;
}
</script>
案例
思路分析
代码实现
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta
name="viewport"
content="width=device-width, initial-scale=1.0,maximum-scale=1,minimum-scale=1,user-scalable=no"
/>
<title>1-显示完整数据</title>
<style>
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
table {
width: 1000px;
margin: 0 auto;
}
thead tr {
background-color: blue;
color: #fff;
font-size: 20px;
}
tbody tr:nth-child(odd) {
background-color: green;
color: #fff;
font-size: 18px;
}
tbody tr:nth-child(even) {
background-color: peru;
color: #fff;
font-size: 18px;
}
td,
th {
padding: 10px;
}
input {
width: 1000px;
display: block;
margin: 30px auto;
height: 100px;
border-radius: 50px;
border: none;
background-color: skyblue;
font-size: 40px;
text-indent: 20px;
color: #666;
outline: none;
}
</style>
</head>
<body>
<input type="text" />
<table>
<thead>
<tr>
<th>id</th>
<th>书名</th>
<th>作者</th>
<th>出版社</th>
</tr>
</thead>
<tbody></tbody>
</table>
<!-- 1 引入axios -->
<script src="./lib/axios.js"></script>
<script>
// 1 打开页面 发送一个ajax 请求 获取数据 - 渲染页面
getData();
// 2 获取输入框
const input = document.querySelector('input');
input.addEventListener('keydown', function (event) {
// 2.1 判断 按下的是不是回车键
if (event.key === 'Enter') {
// 2.2 获取输入框的值
const value = this.value.trim(); // trim() 去除 输入框的值 的两侧的 空字符串
// 2.3 判断是不是空字符串
if (value) {
// 不是空字符串
console.log('不是空字符串');
// bookname:"万少"
// url 传参 ?属性名 = 属性值
const queryStr = `?bookname=${value}`;
// console.log(queryStr);
getData(queryStr); // 把参数带过去
} else {
// 空字符串
// console.log("空字符串");
getData();
}
}
});
// 封装使用ajax来获取数据的函数
function getData(query = '') {
axios({
method: 'get',
url: 'http://www.itcbc.com:3006/api/getbooks' + query,
// params:{},
}).then((result) => {
console.log(result);
const arr = result.data.data;
render(arr);
});
}
function render(arr) {
let html = arr
.map(
(value) => `
<tr>
<td>${value.id}</td>
<td>${value.bookname}</td>
<td>${value.author}</td>
<td>${value.publisher}</td>
</tr>
`
)
.join('');
document.querySelector('tbody').innerHTML = html;
}
</script>
</body>
</html>
基于 axios 发起 POST 请求
使用 axios 发起 POST 请求时,只需要将 method 属性的值设置为 'POST' ,URL地址改为 '/api/addbook':
POST 案例
添加图书
代码展示
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta
name="viewport"
content="width=device-width, initial-scale=1.0,maximum-scale=1,minimum-scale=1,user-scalable=no"
/>
<title>08-post案例</title>
<style>
body {
height: 100vh;
display: flex;
justify-content: space-around;
}
.left {
width: 1000px;
}
.right {
flex: 1;
}
form {
width: 90%;
margin: 0 auto;
background-color: #eee;
}
h3 {
background-color: brown;
color: #fff;
padding: 10px;
}
input {
display: block;
width: 80%;
margin: 10px auto;
height: 50px;
border-radius: 5px;
font-size: 25px;
color: #666;
}
* {
margin: 0;
padding: 0;
box-sizing: border-box;
}
table {
width: 800px;
margin: 0 auto;
}
thead tr {
background-color: blue;
color: #fff;
font-size: 20px;
}
tbody tr:nth-child(odd) {
background-color: green;
color: #fff;
font-size: 18px;
}
tbody tr:nth-child(even) {
background-color: peru;
color: #fff;
font-size: 18px;
}
td,
th {
padding: 10px;
}
input {
width: 800px;
display: block;
margin: 30px auto;
height: 100px;
border-radius: 50px;
border: none;
background-color: skyblue;
font-size: 40px;
text-indent: 20px;
color: #666;
outline: none;
}
</style>
</head>
<body>
<div class="left">
<input type="text" class="keyword" />
<table>
<thead>
<tr>
<th>id</th>
<th>书名</th>
<th>作者</th>
<th>出版社</th>
</tr>
</thead>
<tbody></tbody>
</table>
</div>
<div class="right">
<form>
<h3>添加</h3>
<input type="text" placeholder="书名" class="bookname" />
<input type="text" placeholder="作者" class="author" />
<input type="text" placeholder="出版社" class="publisher" />
<input type="button" value="新增" class="btnadd" />
</form>
</div>
<!-- 1 引入axios -->
<script src="./lib/axios.js"></script>
<script>
getData();
const keyword = document.querySelector('.keyword');
const booknameDom = document.querySelector('.bookname');
const authorDom = document.querySelector('.author');
const publisherDom = document.querySelector('.publisher');
const btnaddDom = document.querySelector('.btnadd');
keyword.addEventListener('keydown', function (event) {
if (event.key === 'Enter') {
const value = this.value.trim();
if (value) {
console.log('不是空字符串');
const queryStr = `?bookname=${value}`;
getData(queryStr); // 把参数带过去
} else {
getData();
}
}
});
btnaddDom.addEventListener('click', function () {
// 1 获取三个输入框的值
const bookname = booknameDom.value;
const author = authorDom.value;
const publisher = publisherDom.value;
// 2 拼接 post请求要的参数
const data = {
// 对象简写
bookname,
author,
publisher,
};
// 3 发送post请求 来完成新增数据
axios({
method: 'post',
url: 'http://www.itcbc.com:3006/api/addbook', // url
// data:data,// es6 对象简写的知识
data, // es6 对象简写的知识
}).then((result) => {
console.log(result);
// 调用一次 getData
getData();
// 重置表单
booknameDom.value = '';
authorDom.value = '';
publisherDom.value = '';
});
});
// 封装使用ajax来获取数据的函数
function getData(query = '') {
axios({
method: 'get',
url: 'http://www.itcbc.com:3006/api/getbooks' + query,
// params:{},
}).then((result) => {
console.log(result);
const arr = result.data.data;
render(arr);
});
}
function render(arr) {
let html = arr
.map(
(value) => `
<tr>
<td>${value.id}</td>
<td>${value.bookname}</td>
<td>${value.author}</td>
<td>${value.publisher}</td>
</tr>
`
)
.join('');
document.querySelector('tbody').innerHTML = html;
}
</script>
</body>
</html>
接口的基础知识
接口的概念
使用 Ajax 请求数据时,被请求的 URL 地址,就叫做数据接口(简称:接口或 API 接口)。
同时,每个接口必须有对应的请求方式。例如:
- www.itcbc.com:3006/api/getbook… 获取图书列表的接口(GET 请求)
- www.itcbc.com:3006/api/addbook 添加图书的接口(POST 请求)
接口文档
接口文档就是接口的使用说明书,它是我们调用接口的依据。
接口文档的格式
组成部分 | 说明 |
---|---|
接口名称 | 接口的名称,用来快速区分每个接口的作用。如:登录接口、添加图书接口 |
接口 URL | 客户端发起 Ajax 调用此接口时,请求的 URL 地址 |
请求方式 | 接口的请求方式,如:GET、POST、PUT、DELETE 等 |
请求参数 | 请求此接口时,需要发送到服务器的查询参数或请求体 |
返回示例 | 当接口请求成功后,服务器响应回来的数据的基本格式 |
返回参数说明 | 接口响应结果的详细描述 |
Ajax课程案例接口文档 docs.apipost.cn/preview/f62…