我們有一個Node.js腳本,每分鐘運行一次以檢查我們的應用程序的狀態。通常,它工作得很好。如果服務啓動,它將以0退出。如果服務停止,它將以1退出。一切都很好。節點HTTP請求永久掛起
但每隔一段時間,它只是有點停止。控制檯報告「呼叫狀態API ...」並在那裏無限期地停止。它甚至不會在Node內置的兩分鐘超時時間內超時。沒有錯誤,沒有。它只是坐在那裏,等待着,永遠。這是一個問題,因爲它會阻止正在運行的以下狀態檢查作業。
在這一點上,我的整個團隊已經看過它,我們誰也無法弄清楚什麼情況會使它掛起。我們已經建立了一個從開始到結束的超時時間,以便我們可以繼續進行下一個工作,但實際上這會跳過狀態檢查並創建盲點。所以,我向你們提出了一個好問題。
這裏的腳本(除去名稱/網址):
#!/usr/bin/env node
// SETTINGS: -------------------------------------------------------------------------------------------------
/** URL to contact for status information. */
const STATUS_API = process.env.STATUS_API;
/** Number of attempts to make before reporting as a failure. */
const ATTEMPT_LIMIT = 3;
/** Amount of time to wait before starting another attempt, in milliseconds. */
const ATTEMPT_DELAY = 5000;
// RUNTIME: --------------------------------------------------------------------------------------------------
const URL = require('url');
const https = require('https');
// Make the first attempt.
make_attempt(1, STATUS_API);
// FUNCTIONS: ------------------------------------------------------------------------------------------------
function make_attempt(attempt_number, url) {
console.log('\n\nCONNECTION ATTEMPT:', attempt_number);
check_status(url, function (success) {
console.log('\nAttempt', success ? 'PASSED' : 'FAILED');
// If this attempt succeeded, report success.
if (success) {
console.log('\nSTATUS CHECK PASSED after', attempt_number, 'attempt(s).');
process.exit(0);
}
// Otherwise, if we have additional attempts, try again.
else if (attempt_number < ATTEMPT_LIMIT) {
setTimeout(make_attempt.bind(null, attempt_number + 1, url), ATTEMPT_DELAY);
}
// Otherwise, we're out of attempts. Report failure.
else {
console.log("\nSTATUS CHECK FAILED");
process.exit(1);
}
})
}
function check_status(url, callback) {
var handle_error = function (error) {
console.log("\tFailed.\n");
console.log('\t' + error.toString().replace(/\n\r?/g, '\n\t'));
callback(false);
};
console.log("\tCalling status API...");
try {
var options = URL.parse(url);
options.timeout = 20000;
https.get(options, function (response) {
var body = '';
response.setEncoding('utf8');
response.on('data', function (data) {body += data;});
response.on('end', function() {
console.log("\tConnected.\n");
try {
var parsed = JSON.parse(body);
if ((!parsed.started || !parsed.uptime)) {
console.log('\tReceived unexpected JSON response:');
console.log('\t\t' + JSON.stringify(parsed, null, 1).replace(/\n\r?/g, '\n\t\t'));
callback(false);
}
else {
console.log('\tReceived status details from API:');
console.log('\t\tServer started:', parsed.started);
console.log('\t\tServer uptime:', parsed.uptime);
callback(true);
}
}
catch (error) {
console.log('\tReceived unexpected non-JSON response:');
console.log('\t\t' + body.trim().replace(/\n\r?/g, '\n\t\t'));
callback(false);
}
});
}).on('error', handle_error);
}
catch (error) {
handle_error(error);
}
}
如果你們能看到的任何地方,這可能可能掛無輸出或超時,那會是非常有幫助!
謝謝 詹姆斯·坦納
編輯:附:我們直接使用https
而不是request
,這樣腳本運行時我們不需要進行任何安裝。這是因爲腳本可以在沒有自定義安裝的情況下在分配給Jenkins的任何構建機器上運行。
我會檢查您的響應回調中的狀態碼,如果它不等於200,則會引發錯誤。 – Keith
哦,對不起@凱斯,我不認爲我清楚這一點。成功取決於迴應。 200代碼不一定足夠。 –
編輯我的評論。在完成打字之前,我會點擊「添加」。 –