快应用数据请求接口,如何使用 finally?

问题描述

快应用开发中,使用 Promise 方式,针对 complete 这种情况,用 finally 不能正常的工作;查阅些资料才知道,快应用官方规范没有对 finally 支持,那么如何解决这个问题呢?

相关代码

import fetch from '@system.fetch'

fetch.fetch({
  url: params.url,
  method: params.method,
  data: params.data
})
.then(response => {
  // ....
})
.catch((error, code) => {
  console.log(`request fail, code = ${code}`)
})
.finally(() => {
  // 无法调用到这里?
})
阅读 3.4k
3 个回答

对于不能够使用 finally 的个情况,可以通过打补丁 (polyfill) 的方式,来予以解决,这在快应用中同样适用;存在的方法比较多,介绍一种相对简单的办法,代码如下:

Promise.prototype.finally = function (callback) {
  const P = this.constructor
  return this.then(
    value  => P.resolve(callback()).then(() => value),
    reason => P.resolve(callback()).then(() => { throw reason })
  )
}

另外补充说明的是,在实际项目开发中,我们可以对数据请求,统一封装并处理,这样就可以提升代码的可用性以及可维护性,具体的思考有在如何优雅处理「快应用」数据请求一文中阐述;相关具体代码如下:

import $fetch from '@system.fetch'

Promise.prototype.finally = function (callback) {
  const P = this.constructor
  return this.then(
    value  => P.resolve(callback()).then(() => value),
    reason => P.resolve(callback()).then(() => { throw reason })
  )
}

function requestHandle(params) {
  return new Promise((resolve, reject) => {
    $fetch.fetch({
      url: params.url,
      method: params.method,
      data: params.data
    }).then(response => {
      const result = response.data
      const content = JSON.parse(result.data)
      /* @desc: 可跟具体不同业务接口数据,返回你所需要的部分,使得使用尽可能便捷 */
      content.code === 200 ? resolve(content.result) : resolve(content.message)
    }).catch((error, code) => {
      console.log(`? request fail, code = ${code}`)
      reject(error)
    }).finally(() => {
      console.log(`✔️ request @${params.url} has been completed.`)
      resolve()
    })
  })
}

Promise,在成功里面返回resolve,失败里面返回reject,2个里面都可传递参数

function fetchData(){
    fetch.fetch({
      url: params.url,
      method: params.method,
      data: params.data
    })
    .then(response => {
      // success
      return Promise.resolve(response);
    })
    .catch((error, code) => {
      console.log(`request fail, code = ${code}`);
      // err
      return Promise.reject(error);
    })
}

之后调用不管成功或失败都执行你想在finally里面的代码

fetchData().then(res => {
    // when success
    // do final
}).catch(err => {
    // when error
    // do final
})
推荐问题