88 lines
2.3 KiB
JavaScript
88 lines
2.3 KiB
JavaScript
require('dotenv').config();
|
|
const mysql = require('mysql2/promise');
|
|
const config = require('./index');
|
|
|
|
// Create a connection pool
|
|
const pool = mysql.createPool({
|
|
host: process.env.DB_HOST,
|
|
user: process.env.DB_USER,
|
|
password: process.env.DB_PASSWORD,
|
|
database: process.env.DB_NAME,
|
|
waitForConnections: true,
|
|
connectionLimit: 10,
|
|
queueLimit: 0,
|
|
enableKeepAlive: true,
|
|
keepAliveInitialDelay: 0,
|
|
namedPlaceholders: true,
|
|
connectTimeout: 10000,
|
|
idleTimeout: 60000,
|
|
maxIdle: 10
|
|
});
|
|
|
|
// Test the connection
|
|
pool.getConnection()
|
|
.then(connection => {
|
|
console.log('Database connected successfully');
|
|
connection.release();
|
|
})
|
|
.catch(err => {
|
|
console.error('Error connecting to the database:', err);
|
|
process.exit(1);
|
|
});
|
|
|
|
// Handle pool errors
|
|
pool.on('error', (err) => {
|
|
console.error('Unexpected error on idle connection', err);
|
|
process.exit(-1);
|
|
});
|
|
|
|
// Query with retry logic
|
|
const queryWithRetry = async (sql, params, maxRetries = 3) => {
|
|
let lastError;
|
|
for (let i = 0; i < maxRetries; i++) {
|
|
try {
|
|
const [results] = await pool.query(sql, params);
|
|
return results;
|
|
} catch (error) {
|
|
lastError = error;
|
|
console.error(`Database query error (attempt ${i + 1}/${maxRetries}):`, error);
|
|
if (error.code === 'PROTOCOL_CONNECTION_LOST' ||
|
|
error.code === 'ECONNRESET' ||
|
|
error.code === 'PROTOCOL_ENQUEUE_AFTER_FATAL_ERROR') {
|
|
console.log(`Database connection lost. Retry attempt ${i + 1} of ${maxRetries}`);
|
|
await new Promise(resolve => setTimeout(resolve, 1000 * (i + 1)));
|
|
continue;
|
|
}
|
|
throw error;
|
|
}
|
|
}
|
|
throw lastError;
|
|
};
|
|
|
|
// Health check function
|
|
const checkDatabaseConnection = async () => {
|
|
try {
|
|
await pool.query('SELECT 1');
|
|
return true;
|
|
} catch (error) {
|
|
console.error('Database health check failed:', error);
|
|
return false;
|
|
}
|
|
};
|
|
|
|
// Graceful shutdown
|
|
const closePool = async () => {
|
|
try {
|
|
await pool.end();
|
|
console.log('Database pool closed successfully');
|
|
} catch (error) {
|
|
console.error('Error closing database pool:', error);
|
|
throw error;
|
|
}
|
|
};
|
|
|
|
module.exports = {
|
|
query: queryWithRetry,
|
|
checkConnection: checkDatabaseConnection,
|
|
closePool
|
|
};
|