了解Ajax
什么是Ajax
一种由浏览器 发起 向 服务器 数据交互 的技术
全称是 Asynchronous Javascript And XML 翻译为 异步 js 和 xml
同步与异步
-
同步 阻塞类型 代码执行方式:
console.log(1) console.log(2)
- 异步 非阻塞类型 代码的执行过程 如:Ajax 定时器 延时器
console.log(0);
setInterval(() => {
console.log(2);
}, 1000);
console.log(1);
XML
一种类似html
的数据格式,表示 数据是以 xml
格式 在服务器和浏览器上进行传输的。 网络传输数据的格式可以大概理解为
- XML
- JSON 目前的主流方式
XML
<?xml version="1.0" encoding="UTF-8"?>
<note>
<to>Tove</to>
<from>Jani</from>
<heading>Reminder</heading>
<body>Don't forget me this weekend!</body>
</note>
JSON
JSON 目前的主流方式 - json 是一种类似对象的字符串
json 的全称为:JavaScript Object Notation,是一种轻量级的数据交互格式
"{"name":"菜鸟教程","url":"www.runoob.com","slogan":"学的不仅是技术,更是梦想!"}"
浏览器和服务器交互的流程
- 浏览器负责发起请求
- 服务器负责响应请求
发起Ajax的三大关键
请求的三大关键
1 请求的地址 url
2 请求的方式 method
3 请求的参数 pramas/data
请求地址
请求地址主要是由后端程序员提供给前端工程师的使用的。 一般会通过文档的方式来告诉前端。
请求方式
发起ajax的5种方式
- POST ——向服务器新增数据
- GET —— 从服务器获取数据
- DELETE——删除服务器上的数据
- PUT —— 更新服务器上的数据(侧重于完整更新:例如更新用户的完整信息)
- PATCH——更新服务器上的数据(侧重于部分更新:例如只更新用户的手机号)
请求参数(不是必须,看文档需求)
某些数据,必须要传递给服务器,才能成功获取到对应的数据
- 做注册时,你不传递个人信息给服务器,服务器无法办法登记你信息完成注册
- 做查询数据时,查询华为手机,你不传递如型号、价格、配置,服务器也无法给你返回合适的数据
工作中使用ajax的方式
- 原生底层的ajax
- 基于 ajax封装的js库 (axios,jquery) 主流
- 面向现代浏览器的
fetch
axios
中文官网地址:https://www.axios-http.cn/
英文官网地址:https://www.npmjs.com/package/axios
Ajax体验:
1.引入axios.js文件
2.浏览器发起请求
<script src="./lib/axios.js"></script>
<script>
// 请求地址 http://www.itcbc.com:3006/api/getbooks
// 请求方式 GET
// 请求参数 可以不传
axios({
// 请求地址
url: 'http://www.itcbc.com:3006/api/getbooks',
// 请求方式
method: 'GET',
// 请求参数 可以不传
}).then(function (result) {
// 我们的数据 响应回来了 .then 里面的函数就会触发 result 拥有了后台响应的数据
console.log(result.data.data);
});
</script>
不同的请求方式和它们携带参数写法
如何区分不同的请求方式携带参数写在data还是params
-
看文档
Query 参数 url上或者params上
body 参数 data
默认
- get请求 url或者params ——在params 对象中携带 本质 也是 帮我们将对象 转成了字符串 然后拼接在 url上
- post请求 data
- delete、put、patch 结合文档来看
- delete 和 get 类似
- put patch post 类似
form表单
form表单和按钮——默认刷新
HTML中点击按钮的时候 网页 以为你要做 整页数据提交 (在ajax出现之前 前端向后端提交数据的方式!)
1 如果按照提交数据给服务器来说,现在的前端不需要用到 form表单和input标签的name属性
2 如果网页的表单 input特别多,form表单和name有另外一个作用:可以快速来获取表单的数据
3 解决 form表单和按钮在一起刷新的问题
3.1 type="button"
3.2 刷新 是form 的默认行为 - 阻止 默认行为
<form>
<input type="text">
<input type="text">
<button type="button">登录</button>
<input type="button" class="btn" value="也是提交">
</form>
<script>
const button = document.querySelector('.btn')
const form = document.querySelector('form')
// form.addEventListener('submit', function (e) {
// e.preventDefault()
// console.log('提交,不刷新');
// })
button.addEventListener('click', function () {
console.log('提交,不刷新');
})
</script>
jQuery——快速获取form表单input标签的值
<form>
<input type="text" name="username1" />
<input type="text" name="username2" />
<input type="text" name="username3" />
<input type="text" name="username4" />
<input type="text" name="username5" />
<input type="text" name="username6" />
<input type="text" name="username7" />
<input type="text" name="username8" />
<input type="text" name="username9" />
<input type="text" name="username10" />
<button>获取表单数据</button>
</form>
<!-- 引入jq的 -->
<script src="./lib/jquery.js"></script>
<script>
const form = document.querySelector('form');
form.addEventListener('submit', function (e) {
e.preventDefault()
const query = $('form').serialize()
console.log(query);
})
</script>
FormData ——快速获取form表单input标签的值
<form>
<input type="text" name="username1" />
<input type="text" name="username2" />
<input type="text" name="username3" />
<input type="text" name="username4" />
<input type="text" name="username5" />
<input type="text" name="username6" />
<input type="text" name="username7" />
<input type="text" name="username8" />
<input type="text" name="username9" />
<input type="text" name="username10" />
<button>获取表单数据</button>
</form>
<script>
const form = document.querySelector('form');
form.addEventListener('submit', function (event) {
event.preventDefault();
const fd = new FormData(this); // this = form dom元素
const usp = new URLSearchParams(fd);
const query = usp.toString();
console.log(query);
});
</script>
Form-Data
1 FormData 构造函数 可以new 出一个实例
2 FormData 可以存放一些数据的实例(不像普通的obj)
3 调用方法 append(key,value) 添加数据
4 FormData 不像普通的对象 可以直接打印看数据 它比较害羞 打印 它
4.1 通过 forEach 方法来遍历 FormData 挨个来查看里面的数据
const fd = new FormData();
fd.append("username","悟空");// 添加数据
// fd.append("height","180");// 添加数据
// fd.append("文件名称",文件);// 添加数据
fd.forEach((value,key)=>{
console.log("你要查看的属性名是",key,"属性值是",value);
})
使用FormData快速获取表单的数据
<form>
<input type="text" name="username" value="111" />
<input type="text" name="password" value="222" />
<button>获取数据</button>
</form>
<script>
const form = document.querySelector('form');
form.addEventListener('submit', function (event) {
event.preventDefault();
// const fd=new FormData(传入一个form的dom元素);
// const fd=new FormData(form);
const fd = new FormData(this);
const list = [];
fd.forEach((value, key) => {
list.push(`${key}=${value}`);
});
// console.log(list);
const query = list.join('&');
console.log(query);
});
</script>
URLSearchParams对象——快速获取表单的数据
<form>
<input type="text" name="username" value="111" />
<input type="text" name="password" value="222" />
<button>获取数据</button>
</form>
<script>
const form = document.querySelector('form');
form.addEventListener('submit', function (event) {
event.preventDefault();
// 1 快速把form标签中的表单 获取到 存在 formdata对象中
const fd = new FormData(this);
// 2 把formdata中的表单数据 存在 usp对象
const usp = new URLSearchParams(fd);
// 3 usp对象 有一个方法 专门把数据转成 字符串参数形式 toString()
const query = usp.toString();
console.log(query);
});
function toQuery(form) {
const fd = new FormData(form);
const usp = new URLSearchParams(fd);
const query = usp.toString();
return query;
}
</script>
axios发送请求的简写方式
get 请求的简写方式:
axios.get('http://www.itcbc.com:3006/api/getbooks').then((result) => {
console.log(result);
});
get 请求的简写方式 携带参数:
axios
.get('http://www.itcbc.com:3006/api/getbooks', {
params: { appkey: 'bbccddaaa' },
})
.then((result) => {
console.log(result);
});
post 请求简写
// axios.post("url",参数对象)
axios
.post('http://www.itcbc.com:3006/api/addbook', {
bookname: '演示ttt',
author: '我自己你不知道ttt',
publisher: '斑马出版社ttt',
// 改为只有自己知道的key 长度 6-20
appkey: 'bbccddaaa',
})
.then((result) => {
console.log(result);
});
axios-基地址
axios-基地址的使用
// 定义 axios基地址
axios.defaults.baseURL = 'http://www.itcbc.com:3006';
axios
.get('/api/getbooks', {
params: { appkey: 'bbccddaaa' },
})
.then((result) => {
console.log(result);
});
把图片文件加载到浏览器 显示出来
const input = document.querySelector('input');
const img = document.querySelector('img');
// change事件 触发时期 : 文件加载到浏览器内存中 触发
input.addEventListener('change', function () {
// files属性查看文件
// console.log(this.files);
// 获取到图片在内存中的地址
// URL.createObjectURL(你想要获取谁的内存地址) 返回 内存中的 文件地址
const url = URL.createObjectURL(this.files[0]);
// 把内存中的图片 的地址 设置给 真正的图片标签
img.src = url;
console.log(url);
});
把文件发送给服务器
<input type="file" name="" id="" />
<img src="" alt="" />
<script src="./lib/axios.js"></script>
<script>
const input = document.querySelector('input');
const img = document.querySelector('img');
input.addEventListener('change', function () {
const url = URL.createObjectURL(this.files[0]);
img.src = url;
// 使用formData来包装数据
const fd = new FormData();
// 添加数据
// fd.append("avatar",文件)
fd.append('avatar', this.files[0]);
// 请求三大关键
// url method data
// axios.post("http://www.itcbc.com:3006/api/formdata",{a:1,b:2})
axios
.post('http://www.itcbc.com:3006/api/formdata', fd)
.then((result) => {
console.log(result);
});
});
</script>
原生Ajax
理解webAPI中的API
API 应用程序接口 服务对外提供的能力
提供数据的API ajax 当我们写代码 调用 某个 “接口” 的时候 它提供给我们对应的数据 图书数据
webAPI API
1 浏览器 针对 js(js基础知识 语法) 提供的一套服务
1 js语法 for 数组 对象 、 ++ --
2 调用 webAPI的代码
let num =10; // js语法能力
document.querySelector("div").innertHTML = num ;
document.querySelector("div").className = num ;
formData 操作 网页 标签能力
快速获取form标签中的数据 的能力 浏览器的设置 让你 formData去读数据
原生Ajax
原生Ajax不需要引入axios.js文件
原生Ajax请求的步骤
1.创建异步对象 var xhr = new HTMLHttpRequest()
2.设置请求行 xhr.open()
**3.设置请求头 xhr.setRequestHeader() **
4.设置请求体 xhr.send();
5.监听数据响应 xhr.addEventListener("load",function(){})
体验
// 1 创建 xhr 实例
const xhr = new XMLHttpRequest();
// 2 调用open方法 (指定请求的类型、指定请求的url)
xhr.open('GET', 'http://www.itcbc.com:3006/api/getbooks');
// 3 开始发起请求
xhr.send();
// 4 监听 数据响应
xhr.addEventListener('load', function () {
// 获取响应结果
// 本质上返回字符串类型是正确的
// axios别人封装的库, 别人帮我们重新把 JSON字符串 转成了对象而已
console.log(JSON.parse(this.response));
});
get---携带参数,字符串拼接
问号后的是参数
const xhr=new XMLHttpRequest();
// 原生的ajax get请求 携带参数
xhr.open("GET","http://www.itcbc.com:3006/api/getbooks?bookname=西游记");
xhr.send();
xhr.addEventListener("load",function () {
console.log(this.response);
})
post 请求 传递参数
- 只能放在send中
- 传递参数有三种格式
- 字符串的形式 a=1&b=2&c=3 设置请求头 xhr.setRequestHeader('content-type', 'application/x-www-form-urlencoded');
- json的格式 { a:1,b:2} 设置请求头 xhr.setRequestHeader('content-type', 'application/json');
- FormData的格式 不需要自己单独指定请求头,原生的代码内部会帮我们做
原生Ajax 字符串传参
const data = {
bookname: '你不知道',
author: '我自己你不知道',
publisher: '斑马出版社',
// 改为只有自己知道的key 长度 6-20
appkey: 'xseresd',
};
// 将对象 转成 字符串
const usp = new URLSearchParams(data);
const query = usp.toString();
const xhr = new XMLHttpRequest();
xhr.open('POST', 'http://www.itcbc.com:3006/api/addbook');
// usp 本身是一个对象格式来着, 调用send 代码的时候 ,默认将 usp 转成 字符串
// send 帮我们调用了它 usp.toString()
// 设置 请求头
xhr.setRequestHeader('content-type', 'application/x-www-form-urlencoded');
xhr.send(query); // post请求的参数 只能放在 send
xhr.addEventListener('load', function () {
console.log(this.response);
});
原生Ajax Json字符串传参
const data = {
bookname: '你不知道',
author: '我自己你不知道',
publisher: '斑马出版社',
appkey: 'xseresd',
};
// console.log(JSON.stringify(data));
const xhr = new XMLHttpRequest();
xhr.open('POST', 'http://www.itcbc.com:3006/api/addbook');
xhr.setRequestHeader('content-type', 'application/json'); // 使用了 json格式
// 把对象转成 json字符串的格式 再去传递 ! -axios 没有让我转格式 - 它内部做了封装处理 !!
// xhr.send(data);
xhr.send(JSON.stringify(data));
xhr.addEventListener('load', function () {
console.log(this.response);
});
原生Ajax formData传参
FormData post 提交
input标签 结合 file'类型 用户选择要上传的文件
会触发input事件change
this.files获取到加载到浏览器内存文件 数组
new FormData 对象 调用 append 把文件添加进去
使用ajax原生的代码
<input type="file" name="" id="" />
<script>
const input = document.querySelector('input');
input.addEventListener('change', function () {
const file = this.files[0];
const fd = new FormData();
fd.append('avatar', file);
const xhr = new XMLHttpRequest();
xhr.open('POST', 'http://www.itcbc.com:3006/api/formdata');
// xhr.setRequestHeader('content-type', 'multipart/form-data'); // 使用了 formdata
xhr.send(fd);
xhr.addEventListener('load', function () {
console.log(this.response);
});
});
</script>
表单
重置表单
表单数据在提交表单后重置-----form.reset()
<form >
<input type="text" name="n1">
<input type="text" name="n2">
<input type="text" name="n3">
<button>提交</button>
<script>
const form=document.querySelector("form");
form.addEventListener("submit",function (event) {
event.preventDefault();
// 重置表单
form.reset();
})
</script>
快速获取表单数据
必须要有form标签,里面的 表单组件 必须要提供name属性
方式一:使用jQuery
const data = $('form').serialize();
console.log(data);
方式二:使用formData()
const fd = new FormData(form);
const usp = new URLSearchParams(fd);
const query = usp.toString();
console.log(query);
<form>
<input name="bookname" type="text" />
<input name="author" type="text" />
<button>提交</button>
</form>
<script src="../lib/jquery.js"></script>
<script>
/*
form 标签 和 里面包着按钮的时候(type类型没有写或者写了submit) 点击按钮 会自动刷新
1 给按钮 设置 type=button
2 给form标签 绑定一个 提交事件 submit 在事件中 阻止默认行为
*/
const button = document.querySelector('button');
const form = document.querySelector('form');
form.addEventListener('submit', function (event) {
event.preventDefault(); // 阻止默认行为
// console.log(222);
// 方式一获取表单数据
// const data = $('form').serialize();
// console.log(data);
// 方式二 formdata
const fd = new FormData(form);
const usp = new URLSearchParams(fd);
const query = usp.toString();
console.log(query);
});
</script>
fetch请求
fetch 类似 XMLHttpRequst 请求和响应
1 新 技术
2 功能 和 XMLHttpRequst 一样
3 用法 简单 fetch axios(用得最多) 拦截器-基地址
// 1 get请求
fetch('http://www.itcbc.com:3006/api/getbooks')
.then((result) => {
return result.json(); // 固定搭配 表示 把响应结果转成json 来使用
})
.then(result=>{
console.log(result);
})
// 2 post 请求
// fetch('url', {
// method: 'POST', // 请求类型
// headers: {
// 'Content-Type': 'application/json', // 设置内容
// },
// body: JSON.stringify(data), // post请求的参数部分
// });
</script>
axios拦截器
请求拦截器
响应拦截器
https://www.axios-http.cn/docs/interceptors
// 添加请求拦截器
axios.interceptors.request.use(function (config) {
// 在发送请求之前做些什么
return config;
}, function (error) {
// 对请求错误做些什么
return Promise.reject(error);
});
// 添加响应拦截器
axios.interceptors.response.use(function (response) {
// 2xx 范围内的状态码都会触发该函数。
// 对响应数据做点什么
return response;
}, function (error) {
// 超出 2xx 范围的状态码都会触发该函数。
// 对响应错误做点什么
return Promise.reject(error);
});
使用场景
加载页面等待时的进度条、账号密码登录验证
跨域和同源
防抖和节流
防抖
运用场景:搜索框业务
用户输入完毕,自动的发出一次请求
在单位事件内,只做一次业务
很频繁的操作,只执行最后一次业务
关键技术原理 延迟器
实现过程
每一次输入的时候 :先清空上一次的延迟期 再开启一个新的延迟器
节流
运用场景:倒计时
上一次业务还没有执行完毕,不让开启新的一次业务
关键技术原理
是否允许执行业务条件 按钮禁用
实现过程
1、第一次点击 先禁用按钮 同时开启业务
2、业务执行完毕,重新启用按钮