--所需模块
安装模块 npm install bluebird logger
需求:在node中异步调用多个api返回数据处理
封装papi模块
/**
* api请求封装
*/
var request = require('request');
var Promise = require('bluebird');
var config = require('../config'); //配置文件
var logger = require('./logger')('console');
module.exports = {
// POST 请求封装
post : function(req, api, params, getMoreInfo, isUpload){
var formData = params || {};
formData.rS = config.rS;
if(typeof req.session.scsInfor !== 'undefined'){
formData.loginUid = req.session.loginUid;
formData.adUid = req.session.adUid;
}
var getMoreInfo = getMoreInfo || false;
var isUpload = isUpload || false;
if(req.session.token){
formData.token = formData.accessToken = req.session.token || '';
}
var baseUrl = config.server_base;
if(api.indexOf('http') >= 0){
baseUrl = "";
}
var reqConf = {
url : api,
baseUrl : baseUrl,
timeout : config.apiTime || 2000,
time : true,
method : "POST",
headers : {},
json : true,
debug : false,
gzip : true
};
if(isUpload == false){
reqConf.form = formData;
}else{
reqConf.formData = formData;
}
return new Promise(function(resolve, reject){
logger.info('[POST]', config.server_base + api, formData);
request(reqConf, function(err, response, body){
if(err){
if(err.code == 'ESOCKETTIMEDOUT'){
reject(new Error('接口调用超时: ' + '[' + api + ']'));
}
reject(new Error('请求接口出错: ' + '[' + api + ']' + err.message));
logger.fatal(err);
}else{
if(response.statusCode == 200){
if(body && body.code != undefined){
if(getMoreInfo){
logger.info('[POST]', api, '获取code任意状态返回SUCCESS');
resolve(body);
}else{
if(body.code == 0){
logger.info('[POST]', api, 'SUCCESS');
resolve(body.data);
}else{
var msg = body.msg || '未知';
logger.error('接口返回错误: ', api, '[' + body.code + '] ', msg);
var apiErr = new Error('接口返回错误: ' + '[' + api + '] [' + body.errorCode + '] ' + msg);
apiErr.errorCode = body.code;
apiErr.apiMsg = msg;
reject(apiErr);
}
}
}else{
logger.fatal("接口返回格式错误 :", api, body);
reject(new Error("接口返回格式错误 :" + '[' + api + ']' + JSON.stringify(body)));
}
}else{
var msg = body.msg || '请求接口错误';
logger.fatal(api, response.statusCode, msg);
reject(new Error('[' + api + '] [' + response.statusCode + '] ' + msg));
}
}
});
});
}, // GET 请求封装
get : function(req, api, params,callback){
var qsData = params || {};
qsData.rS = config.rS;
if(typeof req.session.scsInfor !== 'undefined'){
qsData.loginUid = req.session.loginUid;
qsData.adUid = req.session.adUid;
qsData.agUid = req.session.agUid;
}
if(req.session.token){
qsData.token = req.session.token;
}
var baseUrl = config.server_base;
if(api.indexOf('http') >= 0){
baseUrl = "";
}
return new Promise(function(resolve, reject){
logger.info('[GET]', config.server_base + api, qsData);
request({
url : api,
baseUrl : baseUrl,
timeout : 20000,
time : true,
method : "GET",
headers : {},
qs : qsData,
json : true,
debug : false,
gzip : true
}, function(err, response, body){
if(err){
logger.fatal(api, err);
if(err.code == 'ESOCKETTIMEDOUT'){
reject(new Error('接口调用超时: ' + api));
}
reject(new Error('请求接口出错: ' + '[' + api + '] ' + err.message));
}else{
if(response.statusCode == 200){
if(body && body.code != undefined){
if(body.code == 0){
logger.info('[GET]', api, 'SUCCESS');
var obj = callback ? callback(body.data) : body.data;
resolve(obj);
}else{
var msg = body.msg || '未知';
var apiErr = new Error('接口返回错误: [' + api + '] [' + body.code + ']' + msg);
apiErr.errorCode = body.code;
apiErr.apiMsg = msg;
logger.error('接口返回错误: ', api, body.code, msg);
reject(apiErr);
}
}else{
logger.fatal("接口返回格式错误 :", api, body);
reject(new Error('接口返回格式错误 :[' + api + ']' + JSON.stringify(body)));
}
}else{
console.log('错误信息',body);
logger.fatal(api, response.statusCode, msg);
reject(new Error('[' + api + '][' + response.statusCode + '] ' + msg));
}
}
});
});
}, // 路由url生成
route : function(url, params){
var query = [];
var params = params || {};
var href = url || '#';
for(var key in params){
query.push(key + '=' + params[key]);
}
if(query.length){
href += '?' + query.join("&");
}
return href;
}
}
封装logger模块
var log4js = require('log4js');
var config = require('../config');
module.exports = function(type) {
var name = type || 'console';
log4js.configure(config.log);
var logger = log4js.getLogger(name);
return logger;
}
调用dome
var PAPI = require('../../utils/papi');
var Promise = require('bluebird');
var logger = require('../../utils/logger')('console');
module.exports = function (req, res) {
// ################
// 接口调用示例
// PAPI.get(req,'user/user/token', {
// uid: 1
// }).then(function(data) {
// console.log("请求成功:" , data);
// res.end();
// }).catch(function(err) {
// console.log("#########出错了##############");
// console.error(err);
// res.end();
// });
// ################
// 一次调用多个接口的示例,
// then里面返回的 data是一个数组,顺序与all里定义的接口顺序一致
// 比如下例中:
// data[0] 对应 user/user/token 接口调用返回值
// data[1] 对应 advert/campaign/list 接口调用返回值
// Promise.all([
// PAPI.get(req, 'user/user/token', {
// uid: 1
// }),
// PAPI.post(req,'advert/campaign/list')
// ]).then(function(data){
// console.log(data[0]);
// res.end();
// }).catch(function(err) {
// console.error(err);
// res.end();
// });
// ################
// A接口调用完成后再调用B接口的示例
PAPI.get(req, 'user/user/token', {
uid: 1
}).then(function (token) {
return PAPI.post(req, 'advert/campaign/list', {
token: token.dmp_token
});
}).then(function (list) {
res.render('demos/hello', {
layout: false,
list: list
});
}).catch(function (err) {
console.error(err);
res.render('error', {
error: err
});
});
}