diff --git a/backend/src/repositories/RemittanceRepository.ts b/backend/src/repositories/RemittanceRepository.ts index 78cb38a9..78f79d92 100644 --- a/backend/src/repositories/RemittanceRepository.ts +++ b/backend/src/repositories/RemittanceRepository.ts @@ -61,44 +61,58 @@ export class RemittanceRepository { } async upsert(record: Omit): Promise { - await this.pool.query( - `INSERT INTO transactions - (transaction_id, anchor_id, kind, status, status_eta, - amount_in, amount_out, amount_fee, asset_code, - stellar_transaction_id, external_transaction_id, - kyc_status, kyc_fields, kyc_rejection_reason, message, memo, sender_address, correlation_id) - VALUES ($1,$2,$3,$4,$5,$6,$7,$8,$9,$10,$11,$12,$13,$14,$15,$16,$17,$18) - ON CONFLICT (transaction_id) DO UPDATE SET - status = EXCLUDED.status, - amount_in = COALESCE(EXCLUDED.amount_in, transactions.amount_in), - amount_out = COALESCE(EXCLUDED.amount_out, transactions.amount_out), - amount_fee = COALESCE(EXCLUDED.amount_fee, transactions.amount_fee), - stellar_transaction_id = COALESCE(EXCLUDED.stellar_transaction_id, transactions.stellar_transaction_id), - external_transaction_id = COALESCE(EXCLUDED.external_transaction_id, transactions.external_transaction_id), - kyc_status = COALESCE(EXCLUDED.kyc_status, transactions.kyc_status), - message = COALESCE(EXCLUDED.message, transactions.message), - correlation_id = COALESCE(EXCLUDED.correlation_id, transactions.correlation_id), - updated_at = NOW()`, - [ - record.transaction_id, - record.anchor_id ?? null, - record.kind ?? null, - record.status ?? null, - record.status_eta ?? null, - record.amount_in ?? null, - record.amount_out ?? null, - record.amount_fee ?? null, - record.asset_code ?? null, - record.stellar_transaction_id ?? null, - record.external_transaction_id ?? null, - record.kyc_status ?? null, - record.kyc_fields ? JSON.stringify(record.kyc_fields) : null, - record.kyc_rejection_reason ?? null, - record.message ?? null, - record.memo ?? null, - record.sender_address ?? null, - record.correlation_id ?? null, - ] - ); + const client = await this.pool.connect(); + try { + await client.query('BEGIN'); + await client.query( + `SELECT id FROM transactions WHERE transaction_id = $1 FOR UPDATE`, + [record.transaction_id] + ); + await client.query( + `INSERT INTO transactions + (transaction_id, anchor_id, kind, status, status_eta, + amount_in, amount_out, amount_fee, asset_code, + stellar_transaction_id, external_transaction_id, + kyc_status, kyc_fields, kyc_rejection_reason, message, memo, sender_address, correlation_id) + VALUES ($1,$2,$3,$4,$5,$6,$7,$8,$9,$10,$11,$12,$13,$14,$15,$16,$17,$18) + ON CONFLICT (transaction_id) DO UPDATE SET + status = EXCLUDED.status, + amount_in = COALESCE(EXCLUDED.amount_in, transactions.amount_in), + amount_out = COALESCE(EXCLUDED.amount_out, transactions.amount_out), + amount_fee = COALESCE(EXCLUDED.amount_fee, transactions.amount_fee), + stellar_transaction_id = COALESCE(EXCLUDED.stellar_transaction_id, transactions.stellar_transaction_id), + external_transaction_id = COALESCE(EXCLUDED.external_transaction_id, transactions.external_transaction_id), + kyc_status = COALESCE(EXCLUDED.kyc_status, transactions.kyc_status), + message = COALESCE(EXCLUDED.message, transactions.message), + correlation_id = COALESCE(EXCLUDED.correlation_id, transactions.correlation_id), + updated_at = NOW()`, + [ + record.transaction_id, + record.anchor_id ?? null, + record.kind ?? null, + record.status ?? null, + record.status_eta ?? null, + record.amount_in ?? null, + record.amount_out ?? null, + record.amount_fee ?? null, + record.asset_code ?? null, + record.stellar_transaction_id ?? null, + record.external_transaction_id ?? null, + record.kyc_status ?? null, + record.kyc_fields ? JSON.stringify(record.kyc_fields) : null, + record.kyc_rejection_reason ?? null, + record.message ?? null, + record.memo ?? null, + record.sender_address ?? null, + record.correlation_id ?? null, + ] + ); + await client.query('COMMIT'); + } catch (err) { + await client.query('ROLLBACK'); + throw err; + } finally { + client.release(); + } } }