98 lines
2.7 KiB
JavaScript
98 lines
2.7 KiB
JavaScript
const { Pool } = require('pg');
|
|
const { neon } = require('@neondatabase/serverless');
|
|
|
|
// Database configuration
|
|
const DB_CONFIG = {
|
|
// Use Neon serverless for edge deployments
|
|
connectionString: process.env.DATABASE_URL || process.env.NEON_DATABASE_URL,
|
|
ssl: process.env.NODE_ENV === 'production' ? { rejectUnauthorized: false } : false,
|
|
};
|
|
|
|
// Create connection pool for traditional deployment
|
|
const pool = new Pool(DB_CONFIG);
|
|
|
|
// Create Neon serverless client for edge/serverless deployment
|
|
let neonClient = null;
|
|
if (DB_CONFIG.connectionString) {
|
|
neonClient = neon(DB_CONFIG.connectionString);
|
|
}
|
|
|
|
/**
|
|
* Get database client - either pool connection or Neon serverless
|
|
* @returns {Promise<any>} Database client
|
|
*/
|
|
async function getDbClient() {
|
|
if (process.env.USE_NEON_SERVERLESS === 'true' && neonClient) {
|
|
return neonClient;
|
|
}
|
|
|
|
return pool.connect();
|
|
}
|
|
|
|
/**
|
|
* Execute a query using the appropriate client
|
|
* @param {string} query - SQL query
|
|
* @param {any[]} params - Query parameters
|
|
* @returns {Promise<any>} Query result
|
|
*/
|
|
async function executeQuery(query, params = []) {
|
|
if (process.env.USE_NEON_SERVERLESS === 'true' && neonClient) {
|
|
// Neon serverless client
|
|
return await neonClient(query, params);
|
|
} else {
|
|
// Traditional pool connection
|
|
const client = await pool.connect();
|
|
try {
|
|
const result = await client.query(query, params);
|
|
return result.rows;
|
|
} finally {
|
|
client.release();
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Execute a transaction
|
|
* @param {Function} callback - Function to execute within transaction
|
|
* @returns {Promise<any>} Transaction result
|
|
*/
|
|
async function executeTransaction(callback) {
|
|
if (process.env.USE_NEON_SERVERLESS === 'true' && neonClient) {
|
|
// For Neon serverless, we'll need to handle this differently
|
|
// Note: Neon serverless doesn't support traditional transactions
|
|
// Each query is automatically committed
|
|
return await callback(neonClient);
|
|
} else {
|
|
const client = await pool.connect();
|
|
try {
|
|
await client.query('BEGIN');
|
|
const result = await callback(client);
|
|
await client.query('COMMIT');
|
|
return result;
|
|
} catch (error) {
|
|
await client.query('ROLLBACK');
|
|
throw error;
|
|
} finally {
|
|
client.release();
|
|
}
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Close all database connections
|
|
*/
|
|
async function closeConnections() {
|
|
if (pool) {
|
|
await pool.end();
|
|
}
|
|
}
|
|
|
|
module.exports = {
|
|
pool,
|
|
neonClient,
|
|
getDbClient,
|
|
executeQuery,
|
|
executeTransaction,
|
|
closeConnections,
|
|
DB_CONFIG
|
|
}; |