Nodejs http request 的响应问题
Nodejs http request 的响应问题
同一个服务端接口, 使用nodejs http request请求响应的时间(154ms) 是 在前端使用ajax请求响应时间(15ms)的10倍, 有哪些因素可以导致这样的情况? nodejs 代码如下: request: function (params, call, err, cookie) { if (this.option.isCookieNeeded === true && cookie === undefined) { throw new Error('This request is cookie needed, you must set a cookie for it before request. id = ’ + this.option.id) }
err = typeof err !== 'function' ? function (e) {
console.error(e)
} : err;
if (this.option.status === STATUS_MOCK || this.option.status === STATUS_MOCK_ERR) {
this._mock(params, call, err);
return;
}
this.option.method = this.option.method.toLocaleUpperCase();
var self = this, options = {
hostname: self.option.hostname,
port: self.option.port,
path: self.option.path,
method: self.option.method,
headers: {
Cookie: cookie
}
}, querystr;
if (self.option.method === 'POST') {
querystr = JSON.stringify(params);
options.headers['Content-Type'] = 'application/json;charset=utf-8';
} else if (self.option.method === 'GET') {
querystr = self._stringify(params);
options.path += '?' + querystr
}
var req = http.request(options, function (res) {
var timer = setTimeout(function () {
err(new Error('timeout'))
}, self.option.timeout || 5000);
var bufferHelper = new BufferHelper();
res.on('data', function (chunk) {
bufferHelper.concat(chunk);
});
res.on('end', function () {
var buffer = bufferHelper.toBuffer(), result;
try {
result = self.option.encoding === ENCODING_RAW ? buffer :
(self.option.dataType !== 'json' ? iconv.fromEncoding(buffer, self.option.encoding) :
JSON.parse(iconv.fromEncoding(buffer, self.option.encoding)))
} catch (e) {
clearTimeout(timer);
err(new Error('The result has syntax error. ' + e));
return;
}
clearTimeout(timer);
call(result, res.headers['set-cookie'])
})
});
self.option.method !== 'POST' || req.write(querystr);
req.on('error', function (e) {
err(e)
});
req.end()
},
怎么都没人回复啊
根据你的描述,Node.js中的HTTP请求响应时间比前端的AJAX请求响应时间长得多。这种情况可能由以下几个因素导致:
-
网络延迟:Node.js运行在一个独立的环境中,可能需要通过更远的距离或不同的网络路径来访问服务器,这可能导致更高的网络延迟。
-
DNS解析时间:如果DNS解析较慢,Node.js可能会花更多时间来解析域名到IP地址。
-
进程上下文切换:Node.js作为一个单独的进程运行时,可能会受到操作系统调度的影响,导致额外的上下文切换时间。
-
编码和解码开销:你的代码中使用了
iconv
模块进行字符编码转换,这会增加额外的处理时间。 -
异步处理开销:虽然Node.js擅长处理异步操作,但在某些情况下,过多的异步回调可能会增加额外的处理开销。
-
系统资源限制:Node.js实例可能受限于系统的文件描述符数量、内存分配等因素,这也可能影响性能。
示例代码优化
以下是简化版的示例代码,移除了iconv
模块并使用内置的Buffer
处理,以减少不必要的处理开销:
const http = require('http');
const { promisify } = require('util');
const requestAsync = promisify(http.request);
async function makeRequest(params, call, err, cookie) {
if (this.option.isCookieNeeded && cookie === undefined) {
throw new Error(`This request is cookie needed, you must set a cookie for it before request. id = ${this.option.id}`);
}
const { hostname, port, path, method } = this.option;
let body = '';
if (method.toUpperCase() === 'POST') {
body = JSON.stringify(params);
} else if (method.toUpperCase() === 'GET') {
path += `?${new URLSearchParams(params).toString()}`;
}
try {
const response = await requestAsync({
hostname,
port,
path,
method,
headers: {
Cookie: cookie,
'Content-Type': 'application/json;charset=utf-8'
}
}, async (res) => {
res.setEncoding('utf8');
res.on('data', (chunk) => {
body += chunk;
});
res.on('end', () => {
try {
const result = this.option.dataType !== 'json' ? body : JSON.parse(body);
call(result, res.headers['set-cookie']);
} catch (e) {
err(new Error('The result has syntax error.' + e));
}
});
});
response.on('error', (e) => {
err(e);
});
response.end();
} catch (e) {
err(e);
}
}
这段代码使用了promisify
将回调式的http.request
转为Promise风格,使得异步处理更加清晰和简单。同时,减少了不必要的编码转换,直接使用utf8
编码处理响应数据。