使用 Q.js 库

如果实际项目中使用Promise,还是强烈建议使用比较靠谱的第三方插件,会极大增加你的开发效率。除了将要介绍的Q.js,还有bluebird也推荐使用,去 github 自行搜索吧。

另外,使用第三方库不仅仅是提高效率,它还让你在浏览器端(不支持Promise的环境中)使用promise

本节展示的代码参考这里

本节内容概述

  • 下载和安装
  • 使用Q.nfcallQ.nfapply
  • 使用Q.defer
  • 使用Q.denodeify
  • 使用Q.allQ.any
  • 使用Q.delay
  • 其他

下载和安装

可以直接去它的 github 地址 (近 1.3W 的 star 数量说明其用户群很大)查看文档。

如果项目使用 CommonJS 规范直接 npm i q --save,如果是网页外链可寻找可用的 cdn 地址,或者干脆下载到本地。

以下我将要演示的代码,都是使用 CommonJS 规范的,因此我要演示代码之前加上引用,以后的代码演示就不重复加了。

const Q = require('q')

使用Q.nfcallQ.nfapply

要使用这两个函数,你得首先了解 JS 的callapply,如果不了解,先去看看。熟悉了这两个函数之后,再回来看。

Q.nfcall就是使用call的语法来返回一个promise对象,例如

const fullFileName = path.resolve(__dirname, '../data/data1.json')
const result = Q.nfcall(fs.readFile, fullFileName, 'utf-8')  // 使用 Q.nfcall 返回一个 promise
result.then(data => {
    console.log(data)
}).catch(err => {
    console.log(err.stack)
})

Q.nfapply就是使用apply的语法返回一个promise对象,例如

const fullFileName = path.resolve(__dirname, '../data/data1.json')
const result = Q.nfapply(fs.readFile, [fullFileName, 'utf-8'])  // 使用 Q.nfapply 返回一个 promise
result.then(data => {
    console.log(data)
}).catch(err => {
    console.log(err.stack)
})

怎么样,体验了一把,是不是比直接自己写Promise简单多了?

使用Q.defer

Js中文网周刊 - 领略前端技术前沿 一个收集JavaScript 新闻和精选文章的周刊

Q.defer算是一个比较偏底层一点的 API ,用于自己定义一个promise生成器,如果你需要在浏览器端编写,而且浏览器不支持Promise,这个就有用处了。

function readFile(fileName) {
    const defer = Q.defer()
    fs.readFile(fileName, (err, data) => {
        if (err) {
            defer.reject(err)
        } else {
            defer.resolve(data.toString())
        }
    })
    return defer.promise
}
readFile('data1.json')
    .then(data => {
        console.log(data)
    })
    .catch(err => {
        console.log(err.stack)
    })

使用Q.denodeify

我们在很早之前的一节中自己封装了一个fs.readFilepromise生成器,这里再次回顾一下

const readFilePromise = function (fileName) {
    return new Promise((resolve, reject) => {
        fs.readFile(fileName, (err, data) => {
            if (err) {
                reject(err)
            } else {
                resolve(data.toString())
            }
        })
    })
}

虽然看着不麻烦,但是还是需要很多行代码来实现,如果使用Q.denodeify,一行代码就搞定了!

const readFilePromise = Q.denodeify(fs.readFile)

Q.denodeify就是一键将fs.readFile这种有回调函数作为参数的异步操作封装成一个promise生成器,非常方便!

使用Q.allQ.any

这两个其实就是对应了之前讲过的Promise.allPromise.race,而且应用起来一模一样,不多赘述。

const r1 = Q.nfcall(fs.readFile, 'data1.json', 'utf-8')
const r2 = Q.nfcall(fs.readFile, 'data2.json', 'utf-8')
Q.all([r1, r2]).then(arr => {
    console.log(arr)
}).catch(err => {
    console.log(err)
})

使用Q.delay

Q.delay,顾名思义,就是延迟的意思。例如,读取一个文件成功之后,再过五秒钟之后,再去做xxxx。这个如果是自己写的话,也挺费劲的,但是Q.delay就直接给我们分装好了。

const result = Q.nfcall(fs.readFile, 'data1.json', 'utf-8')
result.delay(5000).then(data => {
    // 得到结果
    console.log(data.toString())
}).catch(err => {
    // 捕获错误
    console.log(err.stack)
})

其他

以上就是Q.js一些最常用的操作,其他的一些非常用技巧,大家可以去搜索或者去官网查看文档。

至此,ES6 Promise的所有内容就已经讲完了。但是异步操作的优化到这里没有结束,更加精彩的内容还在后面 ———— Generator

看完两件小事

如果你觉得这篇文章对你挺有启发,我想请你帮我两个小忙:

  1. 关注我们的 GitHub 博客,让我们成为长期关系
  2. 把这篇文章分享给你的朋友 / 交流群,让更多的人看到,一起进步,一起成长!
  3. 关注公众号 「IT平头哥联盟」,公众号后台回复「资源」 免费领取我精心整理的前端进阶资源教程

JS中文网是中国领先的新一代开发者社区和专业的技术媒体,一个帮助开发者成长的社区,目前已经覆盖和服务了超过 300 万开发者,你每天都可以在这里找到技术世界的头条内容。欢迎热爱技术的你一起加入交流与学习,JS中文网的使命是帮助开发者用代码改变世界

results matching ""

    No results matching ""