@superjs/future
v1.0.2
Published
wrap an async result
Downloads
4
Maintainers
Readme
@superjs/future
wrap an async result.
Example
/// client.js
const MongoClient = require('mongodb').MongoClient
module.exports = future(()=>require('mongodb').MongoClient.connect('mongodb://localhost:27017'))
/// collection.js
const client = require('./client')
module.exports = client.db().collection('test')
/// app.js
const collection=require('./collection')
module.exports = async (params)=>{
let result = await collection.insert(params)
return result
}
Thought
如果想在同步环境中返回需要 async 初始化的对象(如 export 一个 axios client 或 db client), 你可以选择:
- 返回两个元素: async init函数, obj, 这样消费者需要提防init是否漏掉执行
- 返回一个元素: async init函数, 该函数返回 obj, 这样消费者必须在 async 函数中才可消费, 对 reexport 或仅透传参数的场景很不友好
- 返回一个元素: obj=future(init), 其返回为同步的, 该 obj 及该 obj 所有同步执行的过程和结果, 在被 await/then/catch/finally 时, 正确的结果将会被返回, 如同 obj=await init()之后执行这些过程一样
解释: 假如 await init() 返回 realObj, 那么 obj 是一个被称为 realObj 的配料的 Proxy, 除了实际 inspect 值时拿不到有用信息, 它能进行 realObj 的所有操作, 且get属性及当做函数调用时返回结果为新配料 obj2, 最终某个配料被 realObjN=await objN, 那么结果已经去配料化了, realObjN是实际对象
Limitation
- 仅对配料的get set apply作了 trap, 也就是不要进行get set apply之外的操作
Options
future 支持一个有用的选项: lazy(默认 true)
当 lazy 为 false 时, 会在 future 函数进入时就执行 init 函数
否则会在首次 await 某个配料时执行 init 函数, 有可能永不被执行, 起到优化作用
若想指定 lazy 为 false, 使用示例如下:
/// client.js
module.exports = future(()=>require('mongodb').MongoClient.connect('mongodb://localhost:27017'),{lazy:false})