Files
CreaBook/node_modules/@electric-sql/pglite-socket/dist/scripts/server.cjs.map
2026-04-05 03:08:53 +02:00

1 line
51 KiB
Plaintext

{"version":3,"sources":["../../src/scripts/server.ts","../../src/index.ts"],"sourcesContent":["#!/usr/bin/env node\n\nimport { PGlite, DebugLevel } from '@electric-sql/pglite'\nimport type { Extension, Extensions } from '@electric-sql/pglite'\nimport { PGLiteSocketServer } from '../index'\nimport { parseArgs } from 'node:util'\nimport { spawn, ChildProcess } from 'node:child_process'\n\n// Define command line argument options\nconst args = parseArgs({\n options: {\n db: {\n type: 'string',\n short: 'd',\n default: 'memory://',\n help: 'Database path (relative or absolute). Use memory:// for in-memory database.',\n },\n port: {\n type: 'string',\n short: 'p',\n default: '5432',\n help: 'Port to listen on',\n },\n host: {\n type: 'string',\n short: 'h',\n default: '127.0.0.1',\n help: 'Host to bind to',\n },\n path: {\n type: 'string',\n short: 'u',\n default: undefined,\n help: 'unix socket to bind to. Takes precedence over host:port',\n },\n debug: {\n type: 'string',\n short: 'v',\n default: '0',\n help: 'Debug level (0-5)',\n },\n extensions: {\n type: 'string',\n short: 'e',\n default: undefined,\n help: 'Comma-separated list of extensions to load (e.g., vector,pgcrypto,postgis etc.)',\n },\n run: {\n type: 'string',\n short: 'r',\n default: undefined,\n help: 'Command to run after server starts',\n },\n 'include-database-url': {\n type: 'boolean',\n default: false,\n help: 'Include DATABASE_URL in the environment of the subprocess',\n },\n 'shutdown-timeout': {\n type: 'string',\n default: '5000',\n help: 'Timeout in milliseconds for graceful subprocess shutdown (default: 5000)',\n },\n 'max-connections': {\n type: 'string',\n short: 'm',\n default: '1',\n help: 'Maximum concurrent connections (default: 1)',\n },\n help: {\n type: 'boolean',\n short: '?',\n default: false,\n help: 'Show help',\n },\n },\n})\n\nconst help = `PGlite Socket Server\nUsage: pglite-server [options]\n\nOptions:\n -d, --db=PATH Database path (default: memory://)\n -p, --port=PORT Port to listen on (default: 5432)\n -h, --host=HOST Host to bind to (default: 127.0.0.1)\n -u, --path=UNIX Unix socket to bind to (default: undefined). Takes precedence over host:port\n -v, --debug=LEVEL Debug level 0-5 (default: 0)\n -e, --extensions=LIST Comma-separated list of extensions to load\n Formats: vector, pgcrypto (built-in/contrib)\n @org/package/path:exportedName (npm package)\n -r, --run=COMMAND Command to run after server starts\n --include-database-url Include DATABASE_URL in subprocess environment\n --shutdown-timeout=MS Timeout for graceful subprocess shutdown in ms (default: 5000)\n -m, --max-connections=N Maximum concurrent connections (default is no concurrency: 1)\n`\n\ninterface ServerConfig {\n dbPath: string\n port: number\n host: string\n path?: string\n debugLevel: DebugLevel\n extensionNames?: string[]\n runCommand?: string\n includeDatabaseUrl: boolean\n shutdownTimeout: number\n maxConnections: number\n}\n\nclass PGLiteServerRunner {\n private config: ServerConfig\n private db: PGlite | null = null\n private server: PGLiteSocketServer | null = null\n private subprocessManager: SubprocessManager | null = null\n\n constructor(config: ServerConfig) {\n this.config = config\n }\n\n static parseConfig(): ServerConfig {\n const extensionsArg = args.values.extensions as string | undefined\n return {\n dbPath: args.values.db as string,\n port: parseInt(args.values.port as string, 10),\n host: args.values.host as string,\n path: args.values.path as string,\n debugLevel: parseInt(args.values.debug as string, 10) as DebugLevel,\n extensionNames: extensionsArg\n ? extensionsArg.split(',').map((e) => e.trim())\n : undefined,\n runCommand: args.values.run as string,\n includeDatabaseUrl: args.values['include-database-url'] as boolean,\n shutdownTimeout: parseInt(args.values['shutdown-timeout'] as string, 10),\n maxConnections: parseInt(args.values['max-connections'] as string, 10),\n }\n }\n\n private createDatabaseUrl(): string {\n const { host, port, path } = this.config\n\n if (path) {\n // Unix socket connection\n const socketDir = path.endsWith('/.s.PGSQL.5432')\n ? path.slice(0, -13)\n : path\n return `postgresql://postgres:postgres@/postgres?host=${encodeURIComponent(socketDir)}`\n } else {\n // TCP connection\n return `postgresql://postgres:postgres@${host}:${port}/postgres`\n }\n }\n\n private async importExtensions(): Promise<Extensions | undefined> {\n if (!this.config.extensionNames?.length) {\n return undefined\n }\n\n const extensions: Extensions = {}\n\n // Built-in extensions that are not in contrib\n const builtInExtensions = [\n 'vector',\n 'live',\n 'pg_hashids',\n 'pg_ivm',\n 'pg_uuidv7',\n 'pgtap',\n 'age',\n 'pg_textsearch',\n ]\n\n for (const name of this.config.extensionNames) {\n let ext: Extension | null = null\n\n try {\n // Check if this is a custom package path (contains ':')\n // Format: @org/package/path:exportedName or package/path:exportedName\n if (name.includes(':')) {\n const [packagePath, exportName] = name.split(':')\n if (!packagePath || !exportName) {\n throw new Error(\n `Invalid extension format '${name}'. Expected: package/path:exportedName`,\n )\n }\n const mod = await import(packagePath)\n ext = mod[exportName] as Extension\n if (ext) {\n extensions[exportName] = ext\n console.log(\n `Imported extension '${exportName}' from '${packagePath}'`,\n )\n }\n } else if (builtInExtensions.includes(name)) {\n // Built-in extension (e.g., @electric-sql/pglite/vector)\n const mod = await import(`@electric-sql/pglite/${name}`)\n ext = mod[name] as Extension\n if (ext) {\n extensions[name] = ext\n console.log(`Imported extension: ${name}`)\n }\n } else {\n // Try contrib first (e.g., @electric-sql/pglite/contrib/pgcrypto)\n try {\n const mod = await import(`@electric-sql/pglite/contrib/${name}`)\n ext = mod[name] as Extension\n } catch {\n // Fall back to external package (e.g., @electric-sql/pglite-<extension>)\n const mod = await import(`@electric-sql/pglite-${name}`)\n ext = mod[name] as Extension\n }\n if (ext) {\n extensions[name] = ext\n console.log(`Imported extension: ${name}`)\n }\n }\n } catch (error) {\n console.error(`Failed to import extension '${name}':`, error)\n throw new Error(`Failed to import extension '${name}'`)\n }\n }\n\n return Object.keys(extensions).length > 0 ? extensions : undefined\n }\n\n private async initializeDatabase(): Promise<void> {\n console.log(`Initializing PGLite with database: ${this.config.dbPath}`)\n console.log(`Debug level: ${this.config.debugLevel}`)\n\n const extensions = await this.importExtensions()\n\n this.db = new PGlite(this.config.dbPath, {\n debug: this.config.debugLevel,\n extensions,\n })\n await this.db.waitReady\n console.log('PGlite database initialized')\n }\n\n private setupServerEventHandlers(): void {\n if (!this.server || !this.subprocessManager) {\n throw new Error('Server or subprocess manager not initialized')\n }\n\n this.server.addEventListener('listening', (event) => {\n const detail = (\n event as CustomEvent<{ port: number; host: string } | { host: string }>\n ).detail\n console.log(`PGLiteSocketServer listening on ${JSON.stringify(detail)}`)\n\n // Run the command after server starts listening\n if (this.config.runCommand && this.subprocessManager) {\n const databaseUrl = this.createDatabaseUrl()\n this.subprocessManager.spawn(\n this.config.runCommand,\n databaseUrl,\n this.config.includeDatabaseUrl,\n )\n }\n })\n\n this.server.addEventListener('connection', (event) => {\n const { clientAddress, clientPort } = (\n event as CustomEvent<{ clientAddress: string; clientPort: number }>\n ).detail\n console.log(`Client connected from ${clientAddress}:${clientPort}`)\n })\n\n this.server.addEventListener('error', (event) => {\n const error = (event as CustomEvent<Error>).detail\n console.error('Socket server error:', error)\n })\n }\n\n private setupSignalHandlers(): void {\n process.on('SIGINT', () => this.shutdown())\n process.on('SIGTERM', () => this.shutdown())\n }\n\n async start(): Promise<void> {\n try {\n // Initialize database\n await this.initializeDatabase()\n\n if (!this.db) {\n throw new Error('Database initialization failed')\n }\n\n // Create and setup the socket server\n this.server = new PGLiteSocketServer({\n db: this.db,\n port: this.config.port,\n host: this.config.host,\n path: this.config.path,\n inspect: this.config.debugLevel > 0,\n maxConnections: this.config.maxConnections,\n })\n\n // Create subprocess manager\n this.subprocessManager = new SubprocessManager((exitCode) => {\n this.shutdown(exitCode)\n })\n\n // Setup event handlers\n this.setupServerEventHandlers()\n this.setupSignalHandlers()\n\n // Start the server\n await this.server.start()\n } catch (error) {\n console.error('Failed to start PGLiteSocketServer:', error)\n throw error\n }\n }\n\n async shutdown(exitCode: number = 0): Promise<void> {\n console.log('\\nShutting down PGLiteSocketServer...')\n\n // Terminate subprocess if running\n if (this.subprocessManager) {\n this.subprocessManager.terminate(this.config.shutdownTimeout)\n }\n\n // Stop server\n if (this.server) {\n await this.server.stop()\n }\n\n // Close database\n if (this.db) {\n await this.db.close()\n }\n\n console.log('Server stopped')\n process.exit(exitCode)\n }\n}\n\nclass SubprocessManager {\n private childProcess: ChildProcess | null = null\n private onExit: (code: number) => void\n\n constructor(onExit: (code: number) => void) {\n this.onExit = onExit\n }\n\n get process(): ChildProcess | null {\n return this.childProcess\n }\n\n spawn(\n command: string,\n databaseUrl: string,\n includeDatabaseUrl: boolean,\n ): void {\n console.log(`Running command: ${command}`)\n\n // Prepare environment variables\n const env = { ...process.env }\n if (includeDatabaseUrl) {\n env.DATABASE_URL = databaseUrl\n console.log(`Setting DATABASE_URL=${databaseUrl}`)\n }\n\n // Parse and spawn the command\n const commandParts = command.trim().split(/\\s+/)\n this.childProcess = spawn(commandParts[0], commandParts.slice(1), {\n env,\n stdio: 'inherit',\n })\n\n this.childProcess.on('error', (error) => {\n console.error('Error running command:', error)\n // If subprocess fails to start, shutdown the server\n console.log('Subprocess failed to start, shutting down...')\n this.onExit(1)\n })\n\n this.childProcess.on('close', (code) => {\n console.log(`Command exited with code ${code}`)\n this.childProcess = null\n\n // If child process exits with non-zero code, notify parent\n if (code !== null && code !== 0) {\n console.log(\n `Child process failed with exit code ${code}, shutting down...`,\n )\n this.onExit(code)\n }\n })\n }\n\n terminate(timeout: number): void {\n if (this.childProcess) {\n console.log('Terminating child process...')\n this.childProcess.kill('SIGTERM')\n\n // Give it a moment to exit gracefully, then force kill if needed\n setTimeout(() => {\n if (this.childProcess && !this.childProcess.killed) {\n console.log('Force killing child process...')\n this.childProcess.kill('SIGKILL')\n }\n }, timeout)\n }\n }\n}\n\n// Main execution\nasync function main() {\n // Show help and exit if requested\n if (args.values.help) {\n console.log(help)\n process.exit(0)\n }\n\n try {\n const config = PGLiteServerRunner.parseConfig()\n const serverRunner = new PGLiteServerRunner(config)\n await serverRunner.start()\n } catch (error) {\n console.error('Unhandled error:', error)\n process.exit(1)\n }\n}\n\n// Run the main function\nmain()\n","import type { PGlite } from '@electric-sql/pglite'\nimport { type Server, type Socket, createServer } from 'net'\n\n// Connection queue timeout in milliseconds\nexport const CONNECTION_QUEUE_TIMEOUT = 60000 // 60 seconds\n\n/**\n * Represents a queued query waiting for PGlite access\n */\ninterface QueuedQuery {\n handlerId: number\n message: Uint8Array\n resolve: (resultSize: number) => void\n reject: (error: Error) => void\n timestamp: number\n onData: (data: Uint8Array) => void\n}\n\n/**\n * Global query queue manager\n * Ensures only one query executes at a time in PGlite\n */\nclass QueryQueueManager {\n private queue: QueuedQuery[] = []\n private processing = false\n private db: PGlite\n private debug: boolean\n private lastHandlerId: null | number = null\n\n constructor(db: PGlite, debug = false) {\n this.db = db\n this.debug = debug\n }\n\n private log(message: string, ...args: any[]): void {\n if (this.debug) {\n console.log(`[QueryQueueManager] ${message}`, ...args)\n }\n }\n\n async enqueue(\n handlerId: number,\n message: Uint8Array,\n onData: (data: Uint8Array) => void,\n ): Promise<number> {\n return new Promise((resolve, reject) => {\n const query: QueuedQuery = {\n handlerId,\n message,\n resolve,\n reject,\n timestamp: Date.now(),\n onData,\n }\n\n this.queue.push(query)\n this.log(\n `enqueued query from handler #${handlerId}, queue size: ${this.queue.length}`,\n )\n\n // Process queue if not already processing\n if (!this.processing) {\n this.processQueue()\n }\n })\n }\n\n private async processQueue(): Promise<void> {\n if (this.processing || this.queue.length === 0) {\n return\n }\n\n this.processing = true\n\n while (this.queue.length > 0) {\n let query\n\n if (this.db.isInTransaction() && this.lastHandlerId) {\n const i = this.queue.findIndex(\n (q) => q.handlerId === this.lastHandlerId,\n )\n if (i === -1) {\n // we didn't find any other query from the same client!\n this.log(\n `transaction started, but no query from the same handler id found in queue`,\n this.lastHandlerId,\n )\n query = null\n } else {\n query = this.queue.splice(i, 1)[0]\n }\n } else {\n query = this.queue.shift()\n }\n if (!query) break\n\n const waitTime = Date.now() - query.timestamp\n this.log(\n `processing query from handler #${query.handlerId} (waited ${waitTime}ms)`,\n )\n\n let result = 0\n try {\n // Execute the query with exclusive access to PGlite\n await this.db.runExclusive(async () => {\n return await this.db.execProtocolRawStream(query.message, {\n onRawData: (data) => {\n result += data.length\n query.onData(data)\n },\n })\n })\n } catch (error) {\n this.log(`query from handler #${query.handlerId} failed:`, error)\n query.reject(error as Error)\n return\n }\n\n this.log(\n `query from handler #${query.handlerId} completed, ${result} bytes`,\n )\n this.lastHandlerId = query.handlerId\n query.resolve(result)\n }\n\n this.processing = false\n this.log(`queue processing complete, queue length is`, this.queue.length)\n }\n\n getQueueLength(): number {\n return this.queue.length\n }\n\n clearQueueForHandler(handlerId: number): void {\n const before = this.queue.length\n this.queue = this.queue.filter((q) => {\n if (q.handlerId === handlerId) {\n q.reject(new Error('Handler disconnected'))\n return false\n }\n return true\n })\n const removed = before - this.queue.length\n if (removed > 0) {\n this.log(`cleared ${removed} queries for handler #${handlerId}`)\n }\n }\n\n async clearTransactionIfNeeded(handlerId: number): Promise<void> {\n if (this.db.isInTransaction() && this.lastHandlerId === handlerId) {\n await this.db.exec('ROLLBACK')\n this.lastHandlerId = null\n await this.processQueue()\n }\n }\n}\n\n/**\n * Options for creating a PGLiteSocketHandler\n */\nexport interface PGLiteSocketHandlerOptions {\n /** The query queue manager */\n queryQueue: QueryQueueManager\n /** Whether to close the socket when detached (default: false) */\n closeOnDetach?: boolean\n /** Print the incoming and outgoing data to the console in hex and ascii */\n inspect?: boolean\n /** Enable debug logging of method calls */\n debug?: boolean\n /** Idle timeout in ms (0 to disable, default: 0) */\n idleTimeout?: number\n}\n\n/**\n * Handler for a single socket connection to PGlite\n * Each connection can remain open and send multiple queries\n */\nexport class PGLiteSocketHandler extends EventTarget {\n private queryQueue: QueryQueueManager\n private socket: Socket | null = null\n private active = false\n private closeOnDetach: boolean\n private inspect: boolean\n private debug: boolean\n private readonly id: number\n private messageBuffer: Buffer = Buffer.alloc(0)\n private idleTimer?: NodeJS.Timeout\n private idleTimeout: number\n private lastActivityTime: number = Date.now()\n\n // Static counter for generating unique handler IDs\n private static nextHandlerId = 1\n\n constructor(options: PGLiteSocketHandlerOptions) {\n super()\n this.queryQueue = options.queryQueue\n this.closeOnDetach = options.closeOnDetach ?? false\n this.inspect = options.inspect ?? false\n this.debug = options.debug ?? false\n this.idleTimeout = options.idleTimeout ?? 0\n this.id = PGLiteSocketHandler.nextHandlerId++\n\n this.log('constructor: created new handler')\n }\n\n public get handlerId(): number {\n return this.id\n }\n\n private log(message: string, ...args: any[]): void {\n if (this.debug) {\n console.log(`[PGLiteSocketHandler#${this.id}] ${message}`, ...args)\n }\n }\n\n public async attach(socket: Socket): Promise<PGLiteSocketHandler> {\n this.log(\n `attach: attaching socket from ${socket.remoteAddress}:${socket.remotePort}`,\n )\n\n if (this.socket) {\n throw new Error('Socket already attached')\n }\n\n this.socket = socket\n this.active = true\n this.lastActivityTime = Date.now()\n\n // Set up socket options\n socket.setNoDelay(true)\n\n // Set up idle timeout if configured\n if (this.idleTimeout > 0) {\n this.resetIdleTimer()\n }\n\n // Setup event handlers\n this.log(`attach: setting up socket event handlers`)\n\n socket.on('data', (data) => {\n this.lastActivityTime = Date.now()\n this.resetIdleTimer()\n\n setImmediate(async () => {\n try {\n await this.handleData(data)\n } catch (err) {\n this.log('socket on data error: ', err)\n this.handleError(err as Error)\n }\n })\n })\n\n socket.on('error', (err) => {\n setImmediate(() => this.handleError(err))\n })\n\n socket.on('close', () => {\n setImmediate(() => this.handleClose())\n })\n\n this.log(`attach: socket handler ready`)\n return this\n }\n\n private resetIdleTimer(): void {\n if (this.idleTimeout <= 0) return\n\n if (this.idleTimer) {\n clearTimeout(this.idleTimer)\n }\n\n this.idleTimer = setTimeout(() => {\n const idleTime = Date.now() - this.lastActivityTime\n this.log(`idle timeout after ${idleTime}ms`)\n this.handleError(new Error('Idle timeout'))\n }, this.idleTimeout)\n }\n\n public async detach(close?: boolean): Promise<PGLiteSocketHandler> {\n this.log(`detach: detaching socket, close=${close ?? this.closeOnDetach}`)\n\n if (this.idleTimer) {\n clearTimeout(this.idleTimer)\n this.idleTimer = undefined\n }\n\n // Clear any pending queries for this handler\n this.queryQueue.clearQueueForHandler(this.id)\n\n await this.queryQueue.clearTransactionIfNeeded(this.id)\n\n if (!this.socket) {\n this.log(`detach: no socket attached, nothing to do`)\n return this\n }\n\n // Remove all listeners\n this.socket.removeAllListeners('data')\n this.socket.removeAllListeners('error')\n this.socket.removeAllListeners('close')\n\n // Close the socket if requested\n if (close ?? this.closeOnDetach) {\n if (this.socket.writable) {\n this.log(`detach: closing socket`)\n try {\n this.socket.end()\n this.socket.destroy()\n } catch (err) {\n this.log(`detach: error closing socket:`, err)\n }\n }\n }\n\n this.socket = null\n this.active = false\n this.messageBuffer = Buffer.alloc(0)\n\n this.log(`detach: handler cleaned up`)\n return this\n }\n\n public get isAttached(): boolean {\n return this.socket !== null\n }\n\n private async handleData(data: Buffer): Promise<number> {\n if (!this.socket || !this.active) {\n this.log(`handleData: no active socket, ignoring data`)\n return 0\n }\n\n this.log(`handleData: received ${data.length} bytes`)\n\n // Append to buffer for message reassembly\n this.messageBuffer = Buffer.concat([this.messageBuffer, data])\n\n // Print the incoming data to the console\n this.inspectData('incoming', data)\n\n try {\n let totalProcessed = 0\n\n while (this.messageBuffer.length > 0) {\n // Determine message length\n let messageLength = 0\n let isComplete = false\n\n // Handle startup message (no type byte, just length)\n if (this.messageBuffer.length >= 4) {\n const firstInt = this.messageBuffer.readInt32BE(0)\n\n if (this.messageBuffer.length >= 8) {\n const secondInt = this.messageBuffer.readInt32BE(4)\n // PostgreSQL 3.0 protocol version\n if (secondInt === 196608 || secondInt === 0x00030000) {\n messageLength = firstInt\n isComplete = this.messageBuffer.length >= messageLength\n }\n }\n\n // Regular message (type byte + length)\n if (!isComplete && this.messageBuffer.length >= 5) {\n const msgLength = this.messageBuffer.readInt32BE(1)\n messageLength = 1 + msgLength\n isComplete = this.messageBuffer.length >= messageLength\n }\n }\n\n if (!isComplete || messageLength === 0) {\n this.log(\n `handleData: incomplete message, buffering ${this.messageBuffer.length} bytes`,\n )\n break\n }\n\n // Extract and process complete message\n const message = this.messageBuffer.slice(0, messageLength)\n this.messageBuffer = this.messageBuffer.slice(messageLength)\n\n this.log(`handleData: processing message of ${message.length} bytes`)\n\n // Check if socket is still active before processing\n if (!this.active || !this.socket) {\n this.log(`handleData: socket no longer active, stopping processing`)\n break\n }\n\n let socketWriteError: any = undefined\n // Queue the query for execution\n // This allows multiple connections to queue queries simultaneously\n await this.queryQueue.enqueue(\n this.id,\n new Uint8Array(message),\n (data) => {\n this.log(`handleData: received ${data.length} bytes from PGlite`)\n\n // Print the outgoing data to the console\n this.inspectData('outgoing', data)\n\n // Send response if available\n if (\n data.length > 0 &&\n this.socket &&\n this.socket.writable &&\n this.active\n ) {\n // await new Promise<number>((resolve, reject) => {\n this.log(`handleData: writing response to socket`)\n if (this.socket?.writable) {\n this.socket.write(Buffer.from(data), (err?: any) => {\n if (err) {\n this.log(`handleData: error writing to socket:`, err)\n socketWriteError = err\n } else {\n this.log(`handleData: socket sent: ${data.length} bytes`)\n }\n })\n } else {\n this.log(`handleData: socket no longer writable`)\n }\n }\n totalProcessed += data.length\n },\n )\n if (socketWriteError) throw socketWriteError\n }\n\n // Emit data event with byte sizes\n this.dispatchEvent(\n new CustomEvent('data', {\n detail: { incoming: data.length, outgoing: totalProcessed },\n }),\n )\n\n return totalProcessed\n } catch (err) {\n this.log(`handleData: error processing data:`, err)\n throw err\n }\n }\n\n private handleError(err: Error): void {\n if (!this.active) {\n this.log(`handleError: handler not active, ignoring error`)\n return\n }\n\n // ECONNRESET is expected behavior when clients disconnect\n if (err.message?.includes('ECONNRESET')) {\n this.log(\n `handleError: client disconnected (ECONNRESET) - normal behavior`,\n )\n } else if (err.message?.includes('Idle timeout')) {\n this.log(`handleError: connection idle timeout`)\n } else {\n this.log(`handleError:`, err)\n }\n\n this.active = false\n\n // Emit error event\n this.dispatchEvent(new CustomEvent('error', { detail: err }))\n\n // Clean up\n this.detach(true)\n }\n\n private handleClose(): void {\n this.log(`handleClose: socket closed`)\n this.active = false\n this.dispatchEvent(new CustomEvent('close'))\n this.detach(false)\n }\n\n private inspectData(\n direction: 'incoming' | 'outgoing',\n data: Buffer | Uint8Array,\n ): void {\n if (!this.inspect) return\n console.log('-'.repeat(75))\n if (direction === 'incoming') {\n console.log('-> incoming', data.length, 'bytes')\n } else {\n console.log('<- outgoing', data.length, 'bytes')\n }\n\n for (let offset = 0; offset < data.length; offset += 16) {\n const chunkSize = Math.min(16, data.length - offset)\n\n let hexPart = ''\n for (let i = 0; i < 16; i++) {\n if (i < chunkSize) {\n const byte = data[offset + i]\n hexPart += byte.toString(16).padStart(2, '0') + ' '\n } else {\n hexPart += ' '\n }\n }\n\n let asciiPart = ''\n for (let i = 0; i < chunkSize; i++) {\n const byte = data[offset + i]\n asciiPart += byte >= 32 && byte <= 126 ? String.fromCharCode(byte) : '.'\n }\n\n console.log(\n `${offset.toString(16).padStart(8, '0')} ${hexPart} ${asciiPart}`,\n )\n }\n }\n}\n\n/**\n * Options for creating a PGLiteSocketServer\n */\nexport interface PGLiteSocketServerOptions {\n /** The PGlite database instance */\n db: PGlite\n /** The port to listen on (default: 5432) */\n port?: number\n /** The host to bind to (default: 127.0.0.1) */\n host?: string\n /** Unix socket path to bind to (default: undefined) */\n path?: string\n /** Print the incoming and outgoing data to the console in hex and ascii */\n inspect?: boolean\n /** Enable debug logging of method calls */\n debug?: boolean\n /** Idle timeout in ms (0 to disable, default: 0) */\n idleTimeout?: number\n /** Maximum concurrent connections (default: 100) */\n maxConnections?: number\n}\n\n/**\n * PGLite Socket Server with support for multiple concurrent connections\n * Connections remain open and queries are queued at the query level\n */\nexport class PGLiteSocketServer extends EventTarget {\n readonly db: PGlite\n private server: Server | null = null\n private port?: number\n private host?: string\n private path?: string\n private active = false\n private inspect: boolean\n private debug: boolean\n private idleTimeout: number\n private maxConnections: number\n private handlers: Set<PGLiteSocketHandler> = new Set()\n private queryQueue: QueryQueueManager\n\n constructor(options: PGLiteSocketServerOptions) {\n super()\n this.db = options.db\n if (options.path) {\n this.path = options.path\n } else {\n if (typeof options.port === 'number') {\n // Keep port undefined on port 0, will be set by the OS when we start the server.\n this.port = options.port ?? options.port\n } else {\n this.port = 5432\n }\n this.host = options.host || '127.0.0.1'\n }\n this.inspect = options.inspect ?? false\n this.debug = options.debug ?? false\n this.idleTimeout = options.idleTimeout ?? 0\n this.maxConnections = options.maxConnections ?? 1\n\n // Create the shared query queue\n this.queryQueue = new QueryQueueManager(this.db, this.debug)\n\n this.log(`constructor: created server on ${this.getServerConn()}`)\n this.log(`constructor: max connections: ${this.maxConnections}`)\n if (this.idleTimeout > 0) {\n this.log(`constructor: idle timeout: ${this.idleTimeout}ms`)\n }\n }\n\n private log(message: string, ...args: any[]): void {\n if (this.debug) {\n console.log(`[PGLiteSocketServer] ${message}`, ...args)\n }\n }\n\n public async start(): Promise<void> {\n this.log(`start: starting server on ${this.getServerConn()}`)\n\n if (this.server) {\n throw new Error('Socket server already started')\n }\n\n // Ensure PGlite is ready before accepting connections\n await this.db.waitReady\n\n this.active = true\n this.server = createServer((socket) => {\n setImmediate(() => this.handleConnection(socket))\n })\n\n this.server.maxConnections = this.maxConnections\n\n return new Promise<void>((resolve, reject) => {\n if (!this.server) return reject(new Error('Server not initialized'))\n\n this.server.on('error', (err) => {\n this.log(`start: server error:`, err)\n this.dispatchEvent(new CustomEvent('error', { detail: err }))\n if (!this.active) {\n reject(err)\n }\n })\n\n if (this.path) {\n this.server.listen(this.path, () => {\n this.log(`start: server listening on ${this.getServerConn()}`)\n this.dispatchEvent(\n new CustomEvent('listening', {\n detail: { path: this.path },\n }),\n )\n resolve()\n })\n } else {\n const server = this.server\n server.listen(this.port, this.host, () => {\n const address = server.address()\n // We are not using pipes, so return type should be AddressInfo\n if (address === null || typeof address !== 'object') {\n throw Error('Expected address info')\n }\n // Assign the new port number\n this.port = address.port\n this.log(`start: server listening on ${this.getServerConn()}`)\n this.dispatchEvent(\n new CustomEvent('listening', {\n detail: { port: this.port, host: this.host },\n }),\n )\n resolve()\n })\n }\n })\n }\n\n public getServerConn(): string {\n if (this.path) return this.path\n return `${this.host}:${this.port}`\n }\n\n public async stop(): Promise<void> {\n this.log(`stop: stopping server`)\n\n this.active = false\n\n // Detach all handlers\n this.log(`stop: detaching ${this.handlers.size} handlers`)\n for (const handler of this.handlers) {\n handler.detach(true)\n }\n this.handlers.clear()\n\n if (!this.server) {\n this.log(`stop: server not running, nothing to do`)\n return Promise.resolve()\n }\n\n return new Promise<void>((resolve) => {\n if (!this.server) return resolve()\n\n this.server.close(() => {\n this.log(`stop: server closed`)\n this.server = null\n this.dispatchEvent(new CustomEvent('close'))\n resolve()\n })\n })\n }\n\n private async handleConnection(socket: Socket): Promise<void> {\n const clientInfo = {\n clientAddress: socket.remoteAddress || 'unknown',\n clientPort: socket.remotePort || 0,\n }\n\n this.log(\n `handleConnection: new connection from ${clientInfo.clientAddress}:${clientInfo.clientPort}`,\n )\n this.log(\n `handleConnection: active connections: ${this.handlers.size}, queued queries: ${this.queryQueue.getQueueLength()}`,\n )\n\n if (!this.active) {\n this.log(`handleConnection: server not active, closing connection`)\n try {\n socket.end()\n } catch (err) {\n this.log(`handleConnection: error closing socket:`, err)\n }\n return\n }\n\n // Check connection limit\n if (this.handlers.size >= this.maxConnections) {\n this.log(`handleConnection: max connections reached, rejecting`)\n socket.write(Buffer.from('Too many connections\\n'))\n socket.end()\n return\n }\n\n // Create a new handler for this connection\n const handler = new PGLiteSocketHandler({\n queryQueue: this.queryQueue,\n closeOnDetach: true,\n inspect: this.inspect,\n debug: this.debug,\n idleTimeout: this.idleTimeout,\n })\n\n // Track this handler\n this.handlers.add(handler)\n\n // Handle errors\n handler.addEventListener('error', (event) => {\n const error = (event as CustomEvent<Error>).detail\n\n if (error?.message?.includes('ECONNRESET')) {\n this.log(\n `handler #${handler.handlerId}: client disconnected (ECONNRESET)`,\n )\n } else if (error?.message?.includes('Idle timeout')) {\n this.log(`handler #${handler.handlerId}: idle timeout`)\n } else {\n this.log(`handler #${handler.handlerId}: error:`, error)\n }\n })\n\n // Handle close event\n handler.addEventListener('close', () => {\n this.log(`handler #${handler.handlerId}: closed`)\n this.handlers.delete(handler)\n this.log(`handleConnection: active connections: ${this.handlers.size}`)\n })\n\n try {\n await handler.attach(socket)\n this.dispatchEvent(new CustomEvent('connection', { detail: clientInfo }))\n } catch (err) {\n this.log(`handleConnection: error attaching socket:`, err)\n this.handlers.delete(handler)\n this.dispatchEvent(new CustomEvent('error', { detail: err }))\n try {\n socket.end()\n } catch (closeErr) {\n this.log(`handleConnection: error closing socket:`, closeErr)\n }\n }\n }\n\n public getStats() {\n return {\n activeConnections: this.handlers.size,\n queuedQueries: this.queryQueue.getQueueLength(),\n maxConnections: this.maxConnections,\n }\n }\n}\n"],"mappings":"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","names":["import_pglite","import_net","QueryQueueManager","db","debug","message","args","handlerId","onData","resolve","reject","query","i","q","waitTime","result","data","error","before","removed","_PGLiteSocketHandler","options","socket","err","idleTime","close","totalProcessed","messageLength","isComplete","firstInt","secondInt","socketWriteError","direction","offset","chunkSize","hexPart","byte","asciiPart","PGLiteSocketHandler","PGLiteSocketServer","server","address","handler","clientInfo","event","closeErr","import_node_util","import_node_child_process","args","help","PGLiteServerRunner","config","extensionsArg","host","port","path","socketDir","extensions","builtInExtensions","name","ext","packagePath","exportName","error","event","detail","databaseUrl","clientAddress","clientPort","PGLiteSocketServer","SubprocessManager","exitCode","onExit","command","includeDatabaseUrl","env","commandParts","code","timeout","main"]}