model_helpers.ts (1296B)
1 import db from '@/lib/db' 2 import { Connection, PoolConnection } from 'mysql2/promise' 3 4 type ConnHandler<T> = (conn: Connection) => Promise<T> 5 6 function transactionWrapper<T> ( 7 conn: PoolConnection, 8 fn: ConnHandler<T>, 9 ): ConnHandler<T> { 10 return async (conn: Connection) => { 11 try { 12 await conn.beginTransaction() 13 const result = await fn(conn) 14 await conn.commit() 15 return result 16 } finally { 17 await conn.rollback() 18 } 19 } 20 } 21 22 export async function withConnection<T> ( 23 fn: ConnHandler<T>, 24 withoutTransaction?: boolean, 25 ): Promise<T> { 26 const conn = await db.getConnection() 27 28 const handler = withoutTransaction 29 ? fn 30 : transactionWrapper(conn, fn) 31 32 try { 33 return await handler(conn) 34 } finally { 35 conn.release() 36 } 37 } 38 39 export type ModelBehaviour<TArgs, TResult> = 40 ((conn: Connection, args: TArgs) => Promise<TResult>) & 41 ((args: TArgs) => Promise<TResult>) 42 43 export function modelBehaviour<TArgs, TResult> ( 44 fn: (conn: Connection, args: TArgs) => Promise<TResult>, 45 ): ModelBehaviour<TArgs, TResult> { 46 return (connOrArgs: Connection | TArgs, args?: TArgs): Promise<TResult> => { 47 if (args != null) { 48 return fn(connOrArgs as Connection, args) 49 } 50 return withConnection((conn) => fn(conn, connOrArgs as TArgs)) 51 } 52 }