如何pipe理多个承诺
我正在编写一个使用node.js的爬虫。 首先,我需要获取主页面来获取该页面上每个项目的URL,然后抓取每个项目的URL以逐一获取它们的详细信息
fetchPage(url)
是获取链接的HTML文本
function fetchPage(url){ return new Promise( (resolve,reject)=>{ agent .get(url) .end(function(err,res){ if (err){ reject(err); } else{ resolve(res.text); } }); }); }
这是这个爬虫的全球通话
fetchPage(link).then( (result)=>{ const urls=getUrls(result); for (var i=0;i<5;i++){ fetchItem(urls[i].link).then( (result)=>{ console.log('Done'); }, (error)=>console.log(error) ); } }, (error)=>console.log(error) );
我处理获取所有项目的URL后获取主页面(通过getUrls
)
fetchItem(url)
是另一个Promise
,它确保了一个项目的每个HTML文本在被fetchPage
后应该通过getItem
来处理
function fetchItem(url){ return new Promise( (resolve,reject)=>{ fetchPage(url).then( (result)=>{ getItem(result); }, (error)=>reject(error) ); }); }
它爬行。 它确实得到我所需要的所有项目,而不缺less任何信息。
但是我的代码有问题。 为什么控制台不为我loggingDone
消息?
结果不正确。 抓取结果的顺序不像我预期的那样,与网站上的顺序不同。
请指出我对这些asynchronous控制有何误解和错误? 如何确保他们的顺序? 如何解决这个代码来满足?
我应该怎么做,如果我想logging一条消息All done
项目都完成后,完全抓取,确保他们完全取得正确的顺序?
Done
没有被调用,因为你没有解决在fetchItem
函数中创build的Promise
。
我想保持结果的顺序,你可能要使用Promise.all 。 当所有项目被完全抓取时,它也将帮助获得All done
消息。
我将开始更改fetchPage
函数,通过将urls
转换为一个fetchItem
promise的数组,使用map
可以传递给Promise.all
。 像这样的东西
fetchPage(link).then( (result)=>{ const urls=getUrls(result); var promises = urls.map((url) => fetchItem(url.link)); Promise.all(promises).then((values) => { console.log('All done'); console.log(values); }, (error) => { console.log(error); }); }, (error)=>console.log(error) );
然后将parsing添加到您的fetchItem
方法。
function fetchItem(url){ return new Promise( (resolve,reject)=>{ fetchPage(url).then( (result)=>{ resolve(getItem(result)); }, (error)=>reject(error) ); }); }