在 Node/Javascript 中链接 HTTP 请求时出现问题
Trouble chaining HTTP requests in Node/Javascript
我正在尝试重新创建我在 Node/js 中编写的 Python 脚本,但我无法完全理解 asynchronous/callback 这一切的方式。
脚本相当简单,使用两个基本的 HTTP 请求到 eBay API。第一个请求获取结果项目 ID 的列表,然后第二个请求获取每个项目的特定信息(description/listing 信息等)。在 Python 中,这相当简单,我使用了一个简单的循环。无论如何它并不快,但它起作用了。
但是,在 javascript 中,我很难获得相同的功能。我现在的代码如下:
var ebay = require('ebay-api');
var params ={};
params.keywords = ["pS4"];
var pages = 2;
var perPage = 2;
ebay.paginateGetRequest({
serviceName: 'FindingService',
opType: 'findItemsAdvanced',
appId: '',
params: params,
pages: pages,
perPage: perPage,
parser: ebay.parseItemsFromResponse
},
function allItemsCallback(error,items){
if(error) throw error;
console.log('FOUND', items.length, 'items from', pages, 'pages');
for (var i=0; i<items.length; i++){
getSingle(items[i].itemId);
}
}
);
function getSingle(id){
console.log("hello");
ebay.ebayApiGetRequest({
'serviceName': 'Shopping',
'opType': 'GetSingleItem',
'appId': '',
params: {
'ItemId': id ,
'includeSelector': 'Description'
}
},
function(error, data) {
if (error) throw error;
console.dir(data); //single item data I want
}
);
}
这是许多尝试中的一个,但我收到了 "possible EventEmitter memory leak detected" 警告,它最终因 "Error:Bad 'ack' code undefined errorMessage? null" 而中断。我相当确定这只与正确使用回调有关,但我不确定如何正确使用它。任何答案或帮助将不胜感激。如果这不是一个好问题,我深表歉意,如果是这样,请告诉我如何正确地提问。
Node.js 的异步事件链建立在回调之上。而不是:
getSingle(items[i].itemId);
您需要在父函数完成后执行的函数中写入回调:
getSingle(items[i].itemId, function(err, data) {
// now you can access the data
});
并且因为 ebay.ebayApiGetRequest
是一个冗长的函数,所以必须在 after 完成后调用告诉其父函数它已完成的回调,如下所示:
ebay.ebayApiGetRequest({
//
},
function(error, data) {
callback(error, data);
}
);
当然,如果父函数 getSingle
不支持回调,那么它哪儿也去不了。因此,您还需要在那里支持回调参数。这是完整的脚本,使用事件驱动的回调模型重写:
var ebay = require('ebay-api');
var async = require('async');
var params = {};
params.keywords = ["pS4"];
var pages = 2;
var perPage = 2;
ebay.paginateGetRequest({
serviceName: 'FindingService',
opType: 'findItemsAdvanced',
appId: '',
params: params,
pages: pages,
perPage: perPage,
parser: ebay.parseItemsFromResponse
},
function allItemsCallback(error, items) {
if (error) throw error;
console.log('FOUND', items.length, 'items from', pages, 'pages');
async.each(items, function(item, callback) {
getSingle(item.itemId, function(err, data) {
callback(err, data);
});
}, function(err, results) {
// now results is an array of all the data objects
});
}
);
function getSingle(id, callback) {
console.log("hello");
ebay.ebayApiGetRequest({
'serviceName': 'Shopping',
'opType': 'GetSingleItem',
'appId': '',
params: {
'ItemId': id,
'includeSelector': 'Description'
}
},
function(error, data) {
if (error) throw error;
console.dir(data); //single item data I want
callback(error, data);
}
);
}
我正在尝试重新创建我在 Node/js 中编写的 Python 脚本,但我无法完全理解 asynchronous/callback 这一切的方式。
脚本相当简单,使用两个基本的 HTTP 请求到 eBay API。第一个请求获取结果项目 ID 的列表,然后第二个请求获取每个项目的特定信息(description/listing 信息等)。在 Python 中,这相当简单,我使用了一个简单的循环。无论如何它并不快,但它起作用了。
但是,在 javascript 中,我很难获得相同的功能。我现在的代码如下:
var ebay = require('ebay-api');
var params ={};
params.keywords = ["pS4"];
var pages = 2;
var perPage = 2;
ebay.paginateGetRequest({
serviceName: 'FindingService',
opType: 'findItemsAdvanced',
appId: '',
params: params,
pages: pages,
perPage: perPage,
parser: ebay.parseItemsFromResponse
},
function allItemsCallback(error,items){
if(error) throw error;
console.log('FOUND', items.length, 'items from', pages, 'pages');
for (var i=0; i<items.length; i++){
getSingle(items[i].itemId);
}
}
);
function getSingle(id){
console.log("hello");
ebay.ebayApiGetRequest({
'serviceName': 'Shopping',
'opType': 'GetSingleItem',
'appId': '',
params: {
'ItemId': id ,
'includeSelector': 'Description'
}
},
function(error, data) {
if (error) throw error;
console.dir(data); //single item data I want
}
);
}
这是许多尝试中的一个,但我收到了 "possible EventEmitter memory leak detected" 警告,它最终因 "Error:Bad 'ack' code undefined errorMessage? null" 而中断。我相当确定这只与正确使用回调有关,但我不确定如何正确使用它。任何答案或帮助将不胜感激。如果这不是一个好问题,我深表歉意,如果是这样,请告诉我如何正确地提问。
Node.js 的异步事件链建立在回调之上。而不是:
getSingle(items[i].itemId);
您需要在父函数完成后执行的函数中写入回调:
getSingle(items[i].itemId, function(err, data) {
// now you can access the data
});
并且因为 ebay.ebayApiGetRequest
是一个冗长的函数,所以必须在 after 完成后调用告诉其父函数它已完成的回调,如下所示:
ebay.ebayApiGetRequest({
//
},
function(error, data) {
callback(error, data);
}
);
当然,如果父函数 getSingle
不支持回调,那么它哪儿也去不了。因此,您还需要在那里支持回调参数。这是完整的脚本,使用事件驱动的回调模型重写:
var ebay = require('ebay-api');
var async = require('async');
var params = {};
params.keywords = ["pS4"];
var pages = 2;
var perPage = 2;
ebay.paginateGetRequest({
serviceName: 'FindingService',
opType: 'findItemsAdvanced',
appId: '',
params: params,
pages: pages,
perPage: perPage,
parser: ebay.parseItemsFromResponse
},
function allItemsCallback(error, items) {
if (error) throw error;
console.log('FOUND', items.length, 'items from', pages, 'pages');
async.each(items, function(item, callback) {
getSingle(item.itemId, function(err, data) {
callback(err, data);
});
}, function(err, results) {
// now results is an array of all the data objects
});
}
);
function getSingle(id, callback) {
console.log("hello");
ebay.ebayApiGetRequest({
'serviceName': 'Shopping',
'opType': 'GetSingleItem',
'appId': '',
params: {
'ItemId': id,
'includeSelector': 'Description'
}
},
function(error, data) {
if (error) throw error;
console.dir(data); //single item data I want
callback(error, data);
}
);
}