我要在async.queue(https://github.com/caolan/async)中添加很多域名,然后进行dns查找。由于某种原因,异步库中的排水事件被调用的太早了,无论是在队列开始时还是在调用之后。我想知道队列何时真正结束,以便可以使用结果。
如果有人可以推荐其他库或方法来排队作业,而我不需要使用此异步库,我只是想使它工作。
const dns = require('dns');
const async = require('async');
const MaxConcurrent = 2; // only do x DNS lookups at one time
const MaxWait = 1000; // wait for a second before dns timeout
var dnsQueue = async.queue(function(domain, lookupAgain) {
setTimeout(
function() {
dns.resolve(domain, function (err, address)
{
console.log('domain: ' + domain + " address: " + address)
});
lookupAgain();
}, MaxWait);
}, MaxConcurrent);
// This should run when the queue is finished
dnsQueue.drain = function() {
console.log('done??');
}
// Array of domain names
var uniqueDomains = [
'google.com',
'yahoo.com',
'ask.com',
'cnn.com',
'real.com'
];
// Push each domain name into the dnsQueue
uniqueDomains.forEach(function(domain) {
dnsQueue.push(domain);
});
答案 0 :(得分:4)
如果您使用的是Nodejs v7.6及更高版本,则不妨尝试async / await。 以下是在nodejs应用程序中使用async / await的示例:
async function fun1(req, res){
let response = await request.get('http://localhost:3000');
if (response.err) { console.log('error');}
else { console.log('fetched response');
}
在上面的示例中,代码要求运行代码的javascript引擎等待request.get()
函数完成,然后继续执行下一行。 request.get()
函数返回一个用户将等待的Promise。在异步/等待之前,如果需要确保函数按期望的顺序运行,即一个接一个地运行,则将它们一个接一个地链接或注册回调。
有关异步/等待的更多信息,请点击以下链接:
答案 1 :(得分:3)
我为您创建了一个异步队列系统:https://github.com/rehat101/queue.js
您无需显式推动或耗尽。您可以运行该作业,它将为您推送和刷新。如果您不在乎作业何时完成,这将很有用。
尝试克隆存储库并执行以下操作:
import Queue from './src/queue';
import Promise from 'bluebird';
const { Resolver } = require('dns').promises;
const resolver = new Resolver();
let domains = [
'google.com',
'yahoo.com',
'ask.com',
'cnn.com',
'real.com'
];
(async function() {
let queue = new Queue({concurrency: 1});
domains.forEach(domain => queue.run(async () => {
await Promise.delay(1000);
console.log( await resolver.resolve(domain) );
}));
})().catch(console.error);
您可以添加数千个工作,这将立即创建1000个未解决的承诺,但只会在并发级别解决承诺。
我计划添加更多功能并将其放在npm上。
答案 2 :(得分:2)
这是因为您已将lookupAgain()
放在dns.resolve
之前。
刚刚更改了lookupAgain()
的位置。
const dns = require('dns');
const async = require('async');
const MaxConcurrent = 2; // only do x DNS lookups at one time
const MaxWait = 1000; // wait for a second before dns timeout
var dnsQueue = async.queue(function(domain, lookupAgain) {
setTimeout(
function() {
dns.resolve(domain, function(err, address) {
console.log('domain: ' + domain + " address: " + address)
lookupAgain();
});
}, MaxWait);
}, MaxConcurrent);
// This should run when the queue is finished
dnsQueue.drain = function() {
console.log('done??');
}
// Array of domain names
var uniqueDomains = [
'google.com',
'yahoo.com',
'ask.com',
'cnn.com',
'real.com',
'google.com',
'yahoo.com',
'ask.com',
'cnn.com',
'real.com'
];
// Push each domain name into the dnsQueue
uniqueDomains.forEach(function(domain) {
dnsQueue.push(domain);
});
我检查了它是否工作正常。