UNPKG

@msugiura/rawsql-prisma

Version:

Prisma integration for rawsql-ts - Dynamic SQL generation with type safety and hierarchical JSON serialization

192 lines (191 loc) 7.73 kB
import { PrismaClientType, RawSqlClientOptions } from './types'; import { QueryBuildOptions } from 'rawsql-ts'; /** * Custom error classes for rawsql-ts operations * * These error classes provide detailed context and helpful suggestions * for common issues like missing files, invalid JSON, and SQL execution failures. * Each error includes structured information for programmatic handling. */ /** * Error thrown when SQL file is not found or cannot be read */ export declare class SqlFileNotFoundError extends Error { readonly filename: string; readonly searchedPath: string; readonly suggestedPath?: string; constructor(filename: string, searchedPath: string, suggestedPath?: string); } /** * Error thrown when JSON mapping file has issues */ export declare class JsonMappingError extends Error { readonly filename: string; readonly filePath: string; readonly issue: string; constructor(filename: string, filePath: string, issue: string, originalError?: Error); } /** * Error thrown when JSON mapping is required but not found */ export declare class JsonMappingRequiredError extends Error { readonly sqlFilePath: string; readonly expectedMappingPath: string; readonly methodName: string; constructor(sqlFilePath: string, expectedMappingPath: string, methodName: string); } /** * Error thrown when SQL query execution fails */ export declare class SqlExecutionError extends Error { readonly sql: string; readonly parameters: any[]; readonly databaseError: string; constructor(sql: string, parameters: any[], databaseError: string, originalError?: Error); } /** * Main class for Prisma integration with rawsql-ts * * Extends Prisma with advanced SQL capabilities including: * - SQL file-based query execution * - Dynamic filtering, sorting, and pagination * - Schema-aware JSON serialization * - Type-safe parameter injection */ export declare class RawSqlClient { private readonly prisma; private readonly options; private readonly schemaResolver; private schemaInfo?; private tableColumnResolver?; private isInitialized; private schemaPreloaded; private readonly jsonMappingCache; private readonly sqlFileCache; /** * Common helper method to check file cache and handle timestamp validation * Returns cached content if valid, undefined if cache miss or invalidated */ private checkFileCache; /** * Common helper method to store content in file cache with timestamp */ private setCacheEntry; /** * Evict oldest entries from cache when it exceeds the configured maximum size * Uses LRU (Least Recently Used) strategy by checking timestamps */ private evictCacheIfNeeded; constructor(prisma: PrismaClientType, options?: RawSqlClientOptions); /** * Initialize the Prisma schema information and resolvers * This is called automatically when needed (lazy initialization) * Uses function-based lazy evaluation for optimal performance */ private initialize; /** * Create a lazy table column resolver that loads schema information only when needed * This avoids the expensive upfront schema resolution cost */ private createLazyTableColumnResolver; /** * Ensure the RawSqlClient is initialized before use * Automatically calls initialize() if not already done * Auto-loads schema on first query if not preloaded */ private ensureInitialized; /** * Explicitly initialize schema information for production use * Call this method during application startup to avoid lazy loading delays */ initializeSchema(): Promise<void>; /** * Execute SQL from file with dynamic conditions - INTERNAL USE ONLY * * This method was made private to simplify the API and reduce confusion. * Use queryOne() or queryMany() instead for clearer intent and better type safety. * * Reasons for making this private: * 1. Too many options led to confusing behavior (serialize: true/false/undefined) * 2. Return type was unpredictable (T[] | T | null depending on options) * 3. JSON mapping behavior was inconsistent (auto-detect vs explicit) * 4. queryOne/queryMany provide clearer intent and safer defaults * * @param sqlFilePathOrQuery - Path to SQL file or pre-built SelectQuery * @param options - Query execution options (filter, sort, paging, serialize) * @returns Query result * @internal */ private query; /** * Load SQL content from file * * @param sqlFilePath - Path to SQL file (relative to sqlFilesPath or absolute) * @returns SQL content as string * @throws Error if file not found or cannot be read */ private loadSqlFile; /** * Load JsonMapping from a .json file * * @param jsonFilePath - Path to JSON file (relative to sqlFilesPath or absolute) * @returns JsonMapping object * @throws Error if file not found or invalid JSON */ private loadJsonMapping; /** * Execute SQL with parameters using Prisma * * @param sql - The SQL query string * @param params - Query parameters * @returns Query result */ private executeSqlWithParams; /** * Execute SQL from file with JSON serialization, returning a single object * Automatically loads corresponding .json mapping file * Throws error if SQL or JSON mapping file is not found or invalid * * @param sqlFilePath - Path to SQL file (relative to sqlFilesPath or absolute) * @param options - Query execution options (filter, sort, paging, allowAllUndefined) * @returns Single serialized object or null * @throws SqlFileNotFoundError when SQL file is not found * @throws JsonMappingError when JSON mapping file is not found or invalid */ queryOne<T>(sqlFilePath: string, options?: Omit<QueryBuildOptions, 'serialize'> & { allowAllUndefined?: boolean; }): Promise<T | null>; /** * Execute SQL from file with JSON serialization, returning an array * Automatically loads corresponding .json mapping file * Throws error if SQL or JSON mapping file is not found or invalid * * @param sqlFilePath - Path to SQL file (relative to sqlFilesPath or absolute) * @param options - Query execution options (filter, sort, paging, allowAllUndefined) * @returns Array of serialized objects * @throws SqlFileNotFoundError when SQL file is not found * @throws JsonMappingError when JSON mapping file is not found or invalid */ queryMany<T = any>(sqlFilePath: string, options?: Omit<QueryBuildOptions, 'serialize'> & { allowAllUndefined?: boolean; }): Promise<T[]>; /** * Extract type transformation configuration from JsonMapping and type protection file * @param jsonMapping - The JsonMapping containing column information * @param sqlFilePath - The SQL file path to find corresponding type protection file * @returns TypeTransformationConfig for protecting user input strings */ private extractTypeTransformationConfig; /** * Load unified JSON mapping configuration that includes both mapping and type protection * Uses caching to avoid reading the same file multiple times * @param jsonMappingFilePath - Path to unified JSON mapping file * @returns Unified JSON mapping configuration */ private loadUnifiedMapping; /** * Get SqlFormatter preset from database provider * * @param provider - Database provider string from Prisma * @returns SqlFormatter preset name */ private getPresetFromProvider; }