阅读 343

Promise Async Await三者的关系

我个人理解Promise Async Await 是为了解决复杂异步操作出现的,有了这三者复杂的异步操作变的很简单。举个例子啊:多级嵌套请求,前端向服务器请求数据,第二次请求依赖第一次请求的数据,第三次请求依赖第二次请求的数据,第四次请求依赖第三次请求的数据...

没有Promise之前的写法,代码如下:
   /**
     * @method 对ajax进行封装
     * @param {{}} config 用于ajax的配置信息
     * @param {function} success 成功取得数据的调用方法
     * @param {function} err 没取得数据的调用方法
     */
    function methodA(config,success,err){
    	//对config进行一些配置,如果url或param或type没写啊,给个默认值
        let trueConfig = Reconfig(config);
        $.ajax({
                url: trueConfig.url,
                data: trueConfig.param,
                type: trueConfig.method,
                success: function (data) {
                    success(data);
                },
                error: function (err) {
                   err(err)
                }
            })
    }
    methodA({url:'http://a.com'},function(data){
        //对第一次请求到的数据进行处理
        let a = data%2
        //进行第二次请求,并将a传入
        methodA({url:'http://b.com',param:{ip:a}},function(data){
            //对第二次请求到的数据进行处理
            let b= data*2c
            //进行第三次请求,并将b传入
            methodA({url:'http://c.com',param:{city:b}},function(data){
                //对第三次请求到的数据进行处理
                let c =data/2d
                //进行第四次请求,并将c传入
                methodA({url:'http://d.com',param:{mony:c}},function(data){
                    //...依次类推
                })
            })
        })
    })
   /**
   	 * @method 对config进行初始化,当config没有传入对应参数时,给个默认值 
     * @param{Object} config 请求数据的地址,参数,方法等信息
     * @param{String} config.url 请求数据的地址
     * @param{Object} config.param 请求的参数信息
     * @param{String} config.type 请求的类型,"GET","POST"等
     */
   function Reconfig(config){
     let Reconfig ={url:'',param:{},type:'GET'}
       for (const key in config) {
         Reconfig[key]=config[key]
        }
        return Reconfig;
    }
复制代码

当然实际开发中,逻辑不会这么简单,有木有感觉特别复杂,一层嵌套一层,都分不清哪个是参数处理方法,哪个请求是哪个请求了,这还没写,请求错误的方法。写出来感觉更乱

有了Promise 之后的写法,代码如下:
//同上对ajax进行封装
   function methodB(config) {
        let trueConfig = Reconfig(config)
        return new Promise((resolve, reject) => {
            $.ajax({
                url: trueConfig.url,
                data: trueConfig.param,
                type: trueConfig.method,
                success: function (data) {
                    //执行resolve会将Promise标记为fulfilled(成功),随后调用.then()方法,会执行then方法中传入的方法,并将data传入
                    resolve(data)
                },
                error: function (err) {
                    //执行resolve会将Promise标记为rejected (成功),随后调用.catch()方法,会执行catch方法中传入的方法,并将err传入
                    reject(err)
                }
            })
        })
    }
    //进行第一次请求
    methodB({ url: 'http://a.com'}).then((data) => {
        //对第一次请求的数据进行些处理
        let a = data % 2
        //进行第二次请求,并将a传入
        return methodB({url:'http://b.com',param:{ip:b}})
    }).then((data)=>{
        //对第二次请求的数据进行处理
        let b = data*2
        //进行第三次请求,并将b传入
        return methodB({url:'http://c.com',param:{city:b}})
    }).then((data)=>{
        //对第三次请求的数据进行处理
        let c = data/2
        //进行第四次请求,并将c传入
        return methodB({url:'http://d.com',param:{mony:c}})
    }).then((data)=>{
        //...依次类推
    }).catch(console.log)
复制代码

是不是感觉要简单点了,不再是一层嵌套一层,看着要好多了。而且当请求不到数据时,执行reject()后,执行.then()方法,then方法中传入的方法不会执行,且返回已经标记为rejected的Promise,直到遇到catch()会执行catch中传入的方法对错误进行处理。

Async,Await是Promise的语法糖,有了它们,代码更简单,代码如下:
//对ajax的封装部分就不再写了,和有Promise的写法一样
//定义一个函数用于请求数据,函数前加async修饰符
    async function getData(){
        //进行第一次请求,当成功时会将得到的数据赋值给data1
        let data1 = await methodB({ url: 'http://a.com'})
        //对第一次请求到的数据进行处理
        let a = data1 % 2;
        //进行二次请求,并将a传入 成功时会将得到的数据赋值给data2
        let data2 = await methodB({url:'http://b.com',param:{ip:a}})
        //对第二次请求到的数据进行处理
        let b = data2*2
        //进行第三次请求,并将b传入 成功时会将得到的数据赋值给data3
        let data3 = await methodB({url:'http://c.com',param:{city:b}})
        //对第三次请求到的数据进行处理
        let c = data3/2
        //进行四次请求,并将c传入 成功时会将得到的数据赋值给data4
        let data4 = await methodB({url:'http://d.com',param:{mony:c}})]
        //以此类推
    }
复制代码

是不是更简单了,.then都省掉了,Async 和 Await 是Promise的语法糖,Await必需与Async一起使用,否则没有作用。如果看了本篇文章,对Promise,Async,Await还不是特别理解,可以参照 MDN上面的解释 developer.mozilla.org/zh-CN/docs/…

文章分类
前端
文章标签