connection loss protection
This commit is contained in:
68
index.js
68
index.js
@@ -56,18 +56,15 @@ client.on(Events.GuildMemberAdd, async (member) => {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
// Log in
|
// Log in and add reconnect/resiliency logic
|
||||||
// Catch library/client errors to prevent unhandled 'error' events from crashing the process
|
|
||||||
client.on('error', (err) => {
|
client.on('error', (err) => {
|
||||||
console.error('Client error:', err);
|
console.error('Client error:', err);
|
||||||
});
|
});
|
||||||
|
|
||||||
// Some libraries emit shard-specific errors — log them for diagnostics
|
|
||||||
client.on('shardError', (err) => {
|
client.on('shardError', (err) => {
|
||||||
console.error('Shard error:', err);
|
console.error('Shard error:', err);
|
||||||
});
|
});
|
||||||
|
|
||||||
// Global handlers to capture unexpected problems and provide diagnostics
|
|
||||||
process.on('uncaughtException', (err) => {
|
process.on('uncaughtException', (err) => {
|
||||||
console.error('Uncaught exception:', err);
|
console.error('Uncaught exception:', err);
|
||||||
});
|
});
|
||||||
@@ -76,4 +73,65 @@ process.on('unhandledRejection', (reason, promise) => {
|
|||||||
console.error('Unhandled Rejection at:', promise, 'reason:', reason);
|
console.error('Unhandled Rejection at:', promise, 'reason:', reason);
|
||||||
});
|
});
|
||||||
|
|
||||||
client.login(BOT_TOKEN);
|
// Reconnect/backoff helpers
|
||||||
|
let reconnectAttempts = 0;
|
||||||
|
let isConnecting = false;
|
||||||
|
const MAX_BACKOFF = 30000; // 30s
|
||||||
|
|
||||||
|
async function connectWithRetry() {
|
||||||
|
if (isConnecting) return;
|
||||||
|
isConnecting = true;
|
||||||
|
try {
|
||||||
|
// If the library provides a destroy/logout method, try to clean up first
|
||||||
|
if (typeof client.destroy === 'function') {
|
||||||
|
try {
|
||||||
|
client.destroy();
|
||||||
|
} catch (e) {
|
||||||
|
// ignore
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
await client.login(BOT_TOKEN);
|
||||||
|
reconnectAttempts = 0;
|
||||||
|
console.log('Successfully connected.');
|
||||||
|
} catch (err) {
|
||||||
|
reconnectAttempts += 1;
|
||||||
|
const delay = Math.min(MAX_BACKOFF, 1000 * Math.pow(2, Math.min(reconnectAttempts, 5)));
|
||||||
|
console.error(`Login attempt ${reconnectAttempts} failed:`, err);
|
||||||
|
console.log(`Retrying in ${delay}ms...`);
|
||||||
|
setTimeout(() => {
|
||||||
|
isConnecting = false;
|
||||||
|
connectWithRetry();
|
||||||
|
}, delay);
|
||||||
|
} finally {
|
||||||
|
isConnecting = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Listen for common disconnect-like events and trigger reconnect attempts.
|
||||||
|
// Different client implementations emit different event names; guard each with a check.
|
||||||
|
try {
|
||||||
|
client.on('disconnect', (event) => {
|
||||||
|
console.warn('Client disconnected:', event);
|
||||||
|
setTimeout(connectWithRetry, 1000);
|
||||||
|
});
|
||||||
|
} catch (e) {}
|
||||||
|
|
||||||
|
try {
|
||||||
|
client.on('close', (code, reason) => {
|
||||||
|
console.warn('Connection closed:', code, reason);
|
||||||
|
setTimeout(connectWithRetry, 1000);
|
||||||
|
});
|
||||||
|
} catch (e) {}
|
||||||
|
|
||||||
|
// Periodic health check: if client isn't ready, try reconnecting.
|
||||||
|
setInterval(() => {
|
||||||
|
const healthy = client && client.user && client.user.username;
|
||||||
|
if (!healthy) {
|
||||||
|
console.warn('Health check: client not ready, attempting reconnect...');
|
||||||
|
connectWithRetry();
|
||||||
|
}
|
||||||
|
}, 30 * 1000);
|
||||||
|
|
||||||
|
// Start initial connection attempt
|
||||||
|
connectWithRetry();
|
||||||
|
|||||||
Reference in New Issue
Block a user