Em primeiro lugar, o problema em sua pergunta é que, dentro do
for
loop, client.get
é invocado com um assíncrono retorno de chamada em que o síncrono for
loop não aguardará o retorno de chamada assíncrono e, portanto, a próxima linha res.json({data:jobs});
está sendo chamado imediatamente após o for
loop antes dos retornos de chamada assíncronos. No momento da linha res.json({data:jobs});
está sendo invocado, o array jobs
ainda está vazio []
e sendo devolvido com a resposta. Para mitigar isso, você deve usar qualquer módulo de promessa como
async
, bluebird
, ES6 Promise
etc. Código modificado usando módulo assíncrono,
app.get('/jobs', function (req, res) {
var jobs = [];
client.keys('*', function (err, keys) {
if (err) return console.log(err);
if(keys){
async.map(keys, function(key, cb) {
client.get(key, function (error, value) {
if (error) return cb(error);
var job = {};
job['jobId']=key;
job['data']=value;
cb(null, job);
});
}, function (error, results) {
if (error) return console.log(error);
console.log(results);
res.json({data:results});
});
}
});
});
Mas doRedis
documentação, observa-se que o uso deKeys destina-se à depuração e operações especiais, como alterar o layout do seu keyspace e não é aconselhável para ambientes de produção.
Portanto, sugiro usar outro módulo chamado redisscan, como abaixo, que usa
SCAN
em vez de KEYS
conforme sugerido no Redis
documentação. Algo como,
var redisScan = require('redisscan');
var redis = require('redis').createClient();
redisScan({
redis: redis,
each_callback: function (type, key, subkey, value, cb) {
console.log(type, key, subkey, value);
cb();
},
done_callback: function (err) {
console.log("-=-=-=-=-=--=-=-=-");
redis.quit();
}
});