/** * Database schema types and queries */ import { query } from './client'; export interface User { id: string; email: string; name: string; did?: string; roles?: string[]; created_at: Date; updated_at: Date; } export interface Document { id: string; title: string; type: string; content?: string; file_url?: string; storage_key?: string; user_id?: string; status: string; classification?: string; ocr_text?: string; extracted_data?: unknown; created_at: Date; updated_at: Date; } export interface Deal { id: string; name: string; status: string; dataroom_id?: string; created_by?: string; created_at: Date; updated_at: Date; } export interface VerifiableCredential { id: string; credential_id: string; issuer_did: string; subject_did: string; credential_type: string[]; credential_subject: unknown; issuance_date: Date; expiration_date?: Date; proof?: unknown; revoked: boolean; created_at: Date; updated_at: Date; } export interface Signature { id: string; document_id?: string; signer_did: string; signature_data: string; signature_timestamp: Date; signature_type: string; created_at: Date; } export interface LedgerEntry { id: string; account_id: string; type: 'debit' | 'credit'; amount: number; currency: string; description?: string; reference?: string; created_at: Date; } export interface Payment { id: string; amount: number; currency: string; status: string; payment_method: string; transaction_id?: string; gateway_response?: unknown; created_at: Date; updated_at: Date; } // User operations export async function createUser(user: Omit): Promise { const result = await query( `INSERT INTO users (email, name, did, roles) VALUES ($1, $2, $3, $4) RETURNING *`, [user.email, user.name, user.did || null, user.roles || []] ); return result.rows[0]!; } export async function getUserById(id: string): Promise { const result = await query('SELECT * FROM users WHERE id = $1', [id]); return result.rows[0] || null; } // Document operations export async function createDocument( doc: Omit ): Promise { const result = await query( `INSERT INTO documents (title, type, content, file_url, storage_key, user_id, status, classification, ocr_text, extracted_data) VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9, $10) RETURNING *`, [ doc.title, doc.type, doc.content || null, doc.file_url || null, doc.storage_key || null, doc.user_id || null, doc.status || 'pending', doc.classification || null, doc.ocr_text || null, doc.extracted_data ? JSON.stringify(doc.extracted_data) : null, ] ); return result.rows[0]!; } export async function getDocumentById(id: string): Promise { const result = await query('SELECT * FROM documents WHERE id = $1', [id]); if (result.rows[0]?.extracted_data && typeof result.rows[0].extracted_data === 'string') { result.rows[0].extracted_data = JSON.parse(result.rows[0].extracted_data); } return result.rows[0] || null; } export async function updateDocument( id: string, updates: Partial> ): Promise { const fields: string[] = []; const values: unknown[] = []; let paramIndex = 1; if (updates.status !== undefined) { fields.push(`status = $${paramIndex++}`); values.push(updates.status); } if (updates.classification !== undefined) { fields.push(`classification = $${paramIndex++}`); values.push(updates.classification); } if (updates.ocr_text !== undefined) { fields.push(`ocr_text = $${paramIndex++}`); values.push(updates.ocr_text); } if (updates.extracted_data !== undefined) { fields.push(`extracted_data = $${paramIndex++}`); values.push(JSON.stringify(updates.extracted_data)); } fields.push(`updated_at = NOW()`); values.push(id); const result = await query( `UPDATE documents SET ${fields.join(', ')} WHERE id = $${paramIndex} RETURNING *`, values ); return result.rows[0]!; } // Deal operations export async function createDeal(deal: Omit): Promise { const result = await query( `INSERT INTO deals (name, status, dataroom_id, created_by) VALUES ($1, $2, $3, $4) RETURNING *`, [deal.name, deal.status || 'draft', deal.dataroom_id || null, deal.created_by || null] ); return result.rows[0]!; } export async function getDealById(id: string): Promise { const result = await query('SELECT * FROM deals WHERE id = $1', [id]); return result.rows[0] || null; } export async function createDealDocument( dealId: string, documentId: string, storageKey: string, accessLevel = 'viewer' ): Promise { await query( `INSERT INTO deal_documents (deal_id, document_id, storage_key, access_level) VALUES ($1, $2, $3, $4) ON CONFLICT (deal_id, document_id) DO NOTHING`, [dealId, documentId, storageKey, accessLevel] ); } // VC operations export async function createVerifiableCredential( vc: Omit ): Promise { const result = await query( `INSERT INTO verifiable_credentials (credential_id, issuer_did, subject_did, credential_type, credential_subject, issuance_date, expiration_date, proof) VALUES ($1, $2, $3, $4, $5, $6, $7, $8) RETURNING *`, [ vc.credential_id, vc.issuer_did, vc.subject_did, vc.credential_type, JSON.stringify(vc.credential_subject), vc.issuance_date, vc.expiration_date || null, vc.proof ? JSON.stringify(vc.proof) : null, ] ); const row = result.rows[0]!; row.credential_subject = JSON.parse(row.credential_subject as string); if (row.proof && typeof row.proof === 'string') { row.proof = JSON.parse(row.proof); } return row; } export async function getVerifiableCredentialById(credentialId: string): Promise { const result = await query( 'SELECT * FROM verifiable_credentials WHERE credential_id = $1', [credentialId] ); if (result.rows[0]) { const row = result.rows[0]; row.credential_subject = JSON.parse(row.credential_subject as string); if (row.proof && typeof row.proof === 'string') { row.proof = JSON.parse(row.proof); } } return result.rows[0] || null; } export async function revokeVerifiableCredential(credentialId: string): Promise { await query('UPDATE verifiable_credentials SET revoked = TRUE WHERE credential_id = $1', [credentialId]); } // Signature operations export async function createSignature(signature: Omit): Promise { const result = await query( `INSERT INTO signatures (document_id, signer_did, signature_data, signature_timestamp, signature_type) VALUES ($1, $2, $3, $4, $5) RETURNING *`, [ signature.document_id || null, signature.signer_did, signature.signature_data, signature.signature_timestamp, signature.signature_type || 'kms', ] ); return result.rows[0]!; } // Ledger operations export async function createLedgerEntry( entry: Omit ): Promise { const result = await query( `INSERT INTO ledger_entries (account_id, type, amount, currency, description, reference) VALUES ($1, $2, $3, $4, $5, $6) RETURNING *`, [ entry.account_id, entry.type, entry.amount.toString(), entry.currency, entry.description || null, entry.reference || null, ] ); return result.rows[0]!; } // Payment operations export async function createPayment(payment: Omit): Promise { const result = await query( `INSERT INTO payments (amount, currency, status, payment_method, transaction_id, gateway_response) VALUES ($1, $2, $3, $4, $5, $6) RETURNING *`, [ payment.amount.toString(), payment.currency, payment.status || 'pending', payment.payment_method, payment.transaction_id || null, payment.gateway_response ? JSON.stringify(payment.gateway_response) : null, ] ); const row = result.rows[0]!; if (row.gateway_response && typeof row.gateway_response === 'string') { row.gateway_response = JSON.parse(row.gateway_response); } return row; } export async function updatePaymentStatus( id: string, status: string, transactionId?: string, gatewayResponse?: unknown ): Promise { const result = await query( `UPDATE payments SET status = $1, transaction_id = COALESCE($2, transaction_id), gateway_response = COALESCE($3, gateway_response), updated_at = NOW() WHERE id = $4 RETURNING *`, [ status, transactionId || null, gatewayResponse ? JSON.stringify(gatewayResponse) : null, id, ] ); const row = result.rows[0]!; if (row.gateway_response && typeof row.gateway_response === 'string') { row.gateway_response = JSON.parse(row.gateway_response); } return row; } // Workflow operations export async function createWorkflowState( workflowId: string, workflowType: string, documentId: string, state: unknown ): Promise { await query( `INSERT INTO workflow_state (workflow_id, workflow_type, document_id, state) VALUES ($1, $2, $3, $4) ON CONFLICT (workflow_id) DO UPDATE SET state = $4, updated_at = NOW()`, [workflowId, workflowType, documentId, JSON.stringify(state)] ); } export async function getWorkflowState(workflowId: string): Promise { const result = await query<{ state: unknown }>( 'SELECT state FROM workflow_state WHERE workflow_id = $1', [workflowId] ); if (result.rows[0]?.state && typeof result.rows[0].state === 'string') { return JSON.parse(result.rows[0].state); } return result.rows[0]?.state || null; }