Closed
Description
Hi there,
I found that cls session was lost when execute promise-like(not really promise object, just have a then property) function ,see the below code example。
var createNamespace = require('cls-hooked').createNamespace;
var session = createNamespace('my session');
var async_hooks = require('async_hooks');
async function main () {
const fake = new Fake()
const result = await fake.query(233) // not work, function end session.get('user') is undefined
// const result = await util.promisify(fake.query)(233) // work, session.get('user') is 'flag'
// const result = await fake.query(233).then() // work
console.log('result ', result, '\n')
}
function Fake () {
// empty
}
Fake.prototype.query = function (ct) {
this.ct = ct
console.log('session user :', session.get('user'))
console.log('query asyncId :', async_hooks.executionAsyncId(), async_hooks.triggerAsyncId())
console.log('set query ct', ct, '\n')
return this
}
Fake.prototype.end = function (callback) {
const self = this
setTimeout(function () {
console.log('session user :', session.get('user'))
console.log('end asyncId :', async_hooks.executionAsyncId(), async_hooks.triggerAsyncId())
console.log('do query ', self.ct, '\n')
callback(self.ct)
})
}
Fake.prototype.then = function then (resolve, reject) {
const self = this
let promise = new Promise(function (innerResolve) {
self.end(innerResolve)
})
return promise.then(resolve, reject)
}
session.run(function () {
session.set('user', 'flag')
console.log('main asyncId :', async_hooks.executionAsyncId(), async_hooks.triggerAsyncId(), '\n')
main().then()
})
change await fake.query(233)
to await fake.query(233).then()
seems can solve the problem,but I don't want to modify in all places, Is there other way to solve the problem?
superagent was support promise like the above code example, so when I try to trace seesion in superagent's http-client, I got this problem.
see https://github.com/visionmedia/superagent/blob/c2f65c665cf1738c5ed8f31c9d255f0a0afa70b2/lib/request-base.js#L231