当前位置: 首页 > news >正文

Ajax + Promise复习简单小结simple

axios使用

先看看老朋友 axios
axios是基于Ajax+promise封装的
看一下他的简单使用
安装:npm install axios --save
引入:import axios from 'axios'

GitHub地址

基本使用

axios({url: 'http://hmajax.itheima.net/api/province'}).then(function (result) {const {data: {list, message}, status} = resultconsole.log(list, message, status)
})
// 发送 GET 请求(默认的方法)
axios('/user/12345').then(response => {}).catch(error => {})

查询参数

axios({url: 'http://hmajax.itheima.net/api/city',method: 'get',params: {pname: '河南省'}
}).then(function (result) {// const {data: {list, message}, status} = resultconsole.log(result)
})

post提交

document.querySelector('button').addEventListener('click', function () {axios({url: 'http://hmajax.itheima.net/api/register',method: 'post',data: {username: 'itheima123',password: '123456'}}).then(function (result) {console.log(result)})
})

错误处理

document.querySelector('button').addEventListener('click', function () {axios({//请求选项url: 'http://hmajax.itheima.net/api/register',method: 'post',data: {username: 'itheima123',password: '123456'}}).then(function (result) {//处理数据console.log(result)}).catch(function (error) {//处理错误console.log(error.response.data.message)})})

实现一个简单地图片上传在这里插入图片描述

在这里插入图片描述

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><title>Title</title><style>img {height: 200px;width: auto;border-radius: 20px;border: 1px solid rebeccapurple;}</style>
</head>
<body>
<input type="file" class="upload">
<img/>
</body>
<script type="text/javascript" src="../js/axios.js"></script>
<script type="text/javascript">/** 图片上传显示在网页上面* 1. 获取图片文件* 2. 使用 FormData 携带图片文件* 3. 提交到服务器获取到返回的图片服务器地址*/document.querySelector('input').addEventListener('change', function (e) {console.log(e.target.files[0])//FormData对象const fd = new FormData()fd.append('img', e.target.files[0])axios({url: 'http://hmajax.itheima.net/api/uploadimg',method: 'post',data: fd}).then(function (result) {console.log(result)document.querySelector('img').src = result.data.data.url}).catch(function (error) {console.log(error)})})
</script>
</html>

XMLhttpRequest使用

/*get请求携带参数*/
/*1. 实例化一个xhr对象*/
const xhr = new XMLHttpRequest()
/*2. 配置请求方法和URL地址*/
xhr.open('get', 'http://hmajax.itheima.net/api/city?pname=辽宁省')
/*3. 添加load事件,获取响应结果*/
xhr.addEventListener('load', function (result) {console.log(JSON.parse(result.target.response))document.write(JSON.parse(result.target.response).list.join(' , '))
})
/*4. 发起请求*/
xhr.send()/*post请求设置请求头,携带请求体*/
document.querySelector('button').addEventListener('click', () => {const xhr = new XMLHttpRequest()xhr.open('post', 'http://hmajax.itheima.net/api/register')xhr.addEventListener('load', function (result) {console.log(JSON.parse(result.target.response))})/*设置请求头 告诉服务器 内容类型*/xhr.setRequestHeader('Content-Type', 'application/json')const user = {username: 'itheima093', password:' 123456'}const userStr = JSON.stringify(user)/*将字符串类型的 请求体发送给服务器*/xhr.send(userStr)
})

详细文档参照 MDN

同步异步

  • 同步代码
    • 逐行执行,原地等待结果后,才继续向下执行
  • 异步代码
    • 调用后耗时,不阻塞代码执行,将来完成后触发回调函数

JavaScript中的异步代码有
- setTimeout / setInterval
- 事件
- Ajax

异步代码接收结果!
- 依靠异步的回调函数接收结果

回调地狱

在回调函数中一直向下嵌套回调函数,就会形成回调函数地狱

/*毁掉地狱*/new MyAxios({url: 'http://hmajax.itheima.net/api/province'}).then(result => {console.log(result)let province = document.querySelector('.province')province.innerHTML = result.list.map(item => `<option>${item}</option>`).join('')new MyAxios({url: 'http://hmajax.itheima.net/api/city',params: {pname: province.value}}).then(result => {console.log(result)let city = document.querySelector('.city')city.innerHTML = result.list.map(item => `<option>${item}</option>`).join('')new MyAxios({url: 'http://hmajax.itheima.net/api/area',params: {pname: province.value, cname: city.value}}).then(result => {console.log(result)let area = document.querySelector('.area')area.innerHTML = result.list.map(item => `<option>${item}</option>`).join('')})})})

缺点:
- 可读性差
- 异常捕获困难
- 耦合性严重

解决:
promise的链式调用
使用then函数返回新的Promise对象的特性一直串联下去

/*链式调用*/let province = document.querySelector('.province')new MyAxios({url: 'http://hmajax.itheima.net/api/province'}).then(result => {console.log(result);province.innerHTML = result.list.map(item => `<option>${item}</option>`).join('')return new MyAxios({url: 'http://hmajax.itheima.net/api/city', params: {pname: province.value}})}).then(result => {console.log(result);let city = document.querySelector('.city');city.innerHTML = result.list.map(item => `<option>${item}</option>`).join('')return new MyAxios({url: 'http://hmajax.itheima.net/api/area', params: {pname: province.value, cname: city.value}})}).then(result => {console.log(result);let area = document.querySelector('.area');area.innerHTML = result.list.map(item => `<option>${item}</option>`).join('')})

使用async 和 await解决(最优)

/*async await 配合使用*/
async function init() {let province = document.querySelector('.province')let city = document.querySelector('.city');let area = document.querySelector('.area');console.log('开始执行异步代码')/*错误捕获; try 代码块中出现了错误,代码就不会继续往下执行了*/try {const provinceList = await new MyAxios({url: 'http://hmajax.itheima.net/api/province'})province.innerHTML = provinceList.list.map(item => `<option>${item}</option>`).join('')const cityList = await new MyAxios({url: 'http://hmajax.itheima.net/api/city', params: {pname: province.value}})city.innerHTML = cityList.list.map(item => `<option>${item}</option>`).join('')const areaList = await new MyAxios({url: 'http://hmajax.itheima.net/api/area', params: {pname: province.value, cname: city.value}})area.innerHTML = areaList.list.map(item => `<option>${item}</option>`).join('')console.log(provinceList)console.log(cityList)console.log(areaList)}catch (error) {console.dir(error)}finally {console.log('finally')}
}

Promise

Promise 对象表示异步操作最终的完成(或失败)以及其结果值。

三个状态:
pending (初始状态,既没有兑现也没有拒绝) => fulfilled(操作成功) / rejected(操作失败)
Promise对象一旦被兑现或拒绝,就代表该对象就已敲定了,状态将无法在改变

优点:

  • 逻辑更清晰
  • 有助于了解axios的内部运作机制
  • 解决回调函数地狱问题(通过链式调用 then 返回一个新的Promise对象

基本使用

/*使用promise管理异步任务*/
const p = new Promise((resolve, reject) => {setTimeout(function () {//resolve() => fulfilled状态-已兑现 => then()// resolve('成功')//reject() => rejected状态-已兑现 => catch()reject(new Error('失败'))}, 2000)
})console.log(p)p.then(result => {console.log(result)
}).catch(error => {console.log(error)
})

PromiseAll

/*当我们需要执行几个Promise对象,同时获取他们的结果时,使用Promise静态方法Promise.all([])*/
const ps = Promise.all([new Promise(resolve => resolve(1)), new Promise(resolve => resolve(2))])
// 这里的result是一个数组
ps.then(result => console.log(result))
const p1 = new Promise(resolve => resolve(3))
const p2 = new Promise(resolve => resolve(4))
const p3 = new Promise((resolve, reject) => {reject('错误1')
})
const p4 = new Promise((resolve, reject) => {reject('错误2')
})
// 当执行的过程中发生错误是,会中断执行并抛出第一个错误
Promise.all([p1, p2, p3, p4]).then(result => {console.log(result)
}).catch(error => {console.log(error)
})

Promise 配合 XMLHttpRequest使用

<script type="text/javascript">const p = new Promise((resolve, reject) => {const xhr = new XMLHttpRequest()xhr.open('get', 'http://hmajax.itheima.net/api/city?pname=湖南省')xhr.addEventListener('loadend', function (result) {if (result.target.status === 200) {resolve(JSON.parse(xhr.response))} else {reject(new Error(xhr.response))}})xhr.send()})console.log(p)p.then(result => {console.log('执行成功', result)}).catch(error => {//错误对象要是用console.dir详细打印console.dir('执行错误', error)})
</script>

XMLHttpRequest 配合 Promise进行简单封装和使用

// 封装为一个函数 MyAxios,返回的是一个Promise对象
function MyAxios({method = 'get', url, params, data}) {//返回一个Promise对象return new Promise((resolve, reject) => {/*1. 实例化一个xhr对象*/const xhr = new XMLHttpRequest()/*判断是否有传参,有传参拼接在URL后面*/url = params ? url + function () {const keys = Object.keys(params)const values = Object.values(params)return '?' + keys.map((item, index) => item + '=' + values[index]).join('&')}() : url// console.log(url)xhr.open(method, url)// 有请求体,给请求头设置请求体文本类型xhr.setRequestHeader('Content-Type', 'application/json')/* 添加load事件,获取响应结果 */xhr.addEventListener('loadend', function () {/*200-300之间的状态码为响应成功状态码*/if (xhr.status >= 200 && xhr.status < 300) {/*返回的内容类型为JSON字符串,对它进行解析并返回*/resolve(JSON.parse(xhr.response))} else {reject(new Error(xhr.response))}})/*判断是否为post请求*/data ? xhr.send(JSON.stringify(data)) : xhr.send()})
}/*get请求 传参*/
/*new MyAxios({method: 'get',url: 'http://hmajax.itheima.net/api/area',params: {pname: '河北省',cname: '石家庄市'}
}).then(result => {console.log(result)
}).catch(error => {console.log(error)
})*//*post请求*/
/*new MyAxios({method: 'post',url: 'http://hmajax.itheima.net/api/register',data: {username: 'itheima095', password:' 123456'}
}).then(result => {console.log(result)
}).catch(error => {console.log(error)
})*//*获取城市天气*/
/*new MyAxios({method: 'get',url: 'http://hmajax.itheima.net/api/weather',params: {city: '110100'}
}).then(result => {console.log(result)
}).catch(error => {console.log(error)
})*//*获取天气案例*/
document.querySelector('.search-city').addEventListener('input', debounce(fun, 500))
const ul = document.querySelector(`ul`)
function fun(e) {console.log('发送请求', e.target.value)new MyAxios({url: 'http://hmajax.itheima.net/api/weather/city',params: {city: e.target.value}}).then(result => {console.log(result)ul.innerHTML = result.data.map(item => `<li data-code="${item.code}">${item.name}</li>`).join('')}).catch(error => {console.log(error)})
}
ul.addEventListener('click', function (e) {const li = e.targetif (li.tagName === 'LI') {console.log(li.dataset.code);new MyAxios({method: 'get',url: 'http://hmajax.itheima.net/api/weather',params: {city: li.dataset.code}}).then(result => {console.log(result)}).catch(error => {console.log(error)})}
})
//防抖函数
function debounce(fun, delay = 500) {let timer = nullreturn function (e) {if (timer)clearTimeout(timer)timer = setTimeout(function () {fun(e)timer = null}, delay)}
}
http://www.lryc.cn/news/154734.html

相关文章:

  • WebDAV之π-Disk派盘 + 小书匠
  • LTE ATTACH流程、PDN流程、PGW地址分配介绍
  • SQL sever中用户管理
  • linux————pxe网络批量装机
  • 处理时延降低24倍,联通云粒数据引擎优化实践
  • 学习MATLAB
  • React 18 对 state 进行保留和重置
  • MySQL之事务与引擎
  • Flink集群常见的监控指标
  • React常见知识点
  • Vue-router路由
  • JVM-CMS
  • 无涯教程-Flutter - Dart简介
  • 如何创建美观的邮件模板并通过qq邮箱的SMTP服务向用户发送
  • 手机无人直播软件在苹果iOS系统中能使用吗?
  • 创建2个线程并执行(STL/Windows/Linux)
  • Redis可以干什么
  • R语言+Meta分析;论文新方向
  • 实战系列(二)| MybatisPlus详细介绍,包含代码详解
  • 横向对比 npm、pnpm、tnpm、yarn 优缺点
  • 安防监控/视频汇聚/云存储/AI智能视频融合平台页面新增地图展示功能
  • 机器人中的数值优化(九)——拟牛顿方法(下)、BB方法
  • java 从resource下载excel打不开
  • NS2安装及入门实例——(ns2.35 / Ubuntu20.04)
  • 平面设计的三大基本元素 优漫动游
  • 【电子取证篇】汽车取证检验标准
  • 【元宇宙】游戏应用商城对元宇宙的影响
  • win10-docker-mysql镜像安装运行基础
  • VirtualBox7+Ubuntu22集群规划
  • 标绘一张图系统