koatty_schedule 4.0.7 → 4.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/config/config.ts","../src/locker/interface.ts","../src/locker/redis-factory.ts","../src/locker/redlock.ts","../src/utils/lib.ts","../src/process/locker.ts","../src/decorator/redlock.ts","../src/decorator/scheduled.ts","../src/process/schedule.ts","../src/index.ts"],"names":["COMPONENT_SCHEDULED","DecoratorType","validateCronExpression","cron","Error","cronParts","trim","split","length","hasSecs","offset","seconds","minutes","hours","dayOfMonth","month","dayOfWeek","validateCronField","field","min","max","fieldName","fieldNameCN","allowedStrings","some","str","toUpperCase","includes","range","step","stepValue","parseInt","isNaN","start","end","startValue","endValue","values","value","numValue","validateRedLockMethodOptions","options","lockTimeOut","undefined","clockDriftFactor","maxRetries","retryDelayMs","globalScheduledOptions","getGlobalScheduledOptions","getEffectiveTimezone","userTimezone","timezone","getEffectiveRedLockOptions","methodOptions","globalOptions","RedisMode","RedisClientAdapter","client","status","call","command","args","set","key","mode","duration","get","del","keys","exists","eval","script","numKeys","quit","disconnect","getClient","RedisFactory","createClient","config","STANDALONE","logger","Debug","createStandaloneClient","SENTINEL","createSentinelClient","CLUSTER","createClusterClient","host","port","password","db","keyPrefix","connectTimeout","commandTimeout","maxRetriesPerRequest","retryStrategy","times","delay","Math","reconnectOnError","err","Warn","message","Redis","on","Info","name","sentinels","sentinelPassword","nodes","clusterOptions","redisOptions","clusterRetryStrategy","cluster","Cluster","address","validateConfig","validateStandaloneConfig","validateSentinelConfig","validateClusterConfig","defaultRedLockConfig","redisConfig","defaultRedlockSettings","driftFactor","retryCount","retryDelay","retryJitter","automaticExtensionThreshold","RedLocker","instance","instanceLock","redlock","redisClient","isInitialized","initializationPromise","registerInContainer","IOCContainer","reg","type","_error","getInstance","containerInstance","resetInstance","close","catch","initialize","performInitialization","error","existingRedis","underlyingClient","userSettings","redlockSettings","Redlock","acquire","resources","ttl","Array","isArray","lockTtl","prefixedResources","map","resource","join","lock","release","extend","extendedLock","isReady","getConfig","updateConfig","getContainerInfo","registered","identifier","healthCheck","redisStatus","details","initialized","redisMode","redlockReady","containerRegistered","timeoutPromise","ms","timeoutId","promise","Promise","resolve","reject","setTimeout","cancel","clearTimeout","initRedLock","app","Helper","isFunction","once","isEmpty","redLocker","redLockerDescriptor","descriptor","method","configurable","enumerable","valueFunction","self","initialLock","lockTime","timeout","props","currentLock","remainingTime","maxExtensions","extensionCount","timeoutHandler","result","race","apply","extendError","releaseError","writable","lockOptions","generateLockName","configName","methodName","target","targetObj","getIdentifier","targetWithConstructor","className","RedLock","lockName","propertyKey","toString","targetClass","componentType","getType","finalLockName","saveClass","enhancedDescriptor","Scheduled","attachClassMetadata","SCHEDULED","initSchedule","injectSchedule","componentList","listClass","component","classMetadata","getClassMetadata","scheduledCount","metadata","Object","entries","startsWith","scheduleData","targetMethod","taskName","tz","CronJob","then","SchedulerLock","defaultOptions","KoattyScheduled"],"mappings":"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","file":"index.js","sourcesContent":["/*\n * @Description: Configuration management for koatty_schedule\n * @Usage: \n * @Author: richen\n * @Date: 2024-01-17 15:30:00\n * @LastEditTime: 2024-01-17 16:30:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport { RedLockOptions } from \"../locker/redlock\";\n\nexport const COMPONENT_SCHEDULED = 'COMPONENT_SCHEDULED';\nexport const COMPONENT_REDLOCK = 'COMPONENT_REDLOCK';\n\n/**\n * Scheduled global options interface\n */\nexport interface ScheduledOptions extends RedLockOptions {\n timezone?: string;\n}\n\n/**\n * RedLock method-level options (excluding Redis connection config)\n */\nexport interface RedLockMethodOptions {\n lockTimeOut?: number; // Lock timeout in milliseconds\n clockDriftFactor?: number; // Clock drift factor for lock timeout calculation\n maxRetries?: number; // Maximum number of retry attempts\n retryDelayMs?: number; // Delay between retry attempts in milliseconds\n}\n\n/**\n * RedLock decorator configuration \n */\nexport interface RedLockConfig {\n name?: string;\n options?: RedLockOptions;\n}\n\n/**\n * Decorator types supported by the system\n */\nexport enum DecoratorType {\n SCHEDULED = 'SCHEDULED',\n REDLOCK = 'REDLOCK'\n}\n\n/**\n * Validate cron expression format (supports both 5-part and 6-part formats)\n * \n * 6-part format: second minute hour day month weekday\n * 5-part format: minute hour day month weekday\n * \n * @param cron - Cron expression to validate\n * @throws {Error} When cron expression is invalid\n */\nexport function validateCronExpression(cron: string): void {\n if (!cron || typeof cron !== 'string') {\n throw new Error('Cron 表达式必须是非空字符串 (Cron expression must be a non-empty string)');\n }\n\n const cronParts = cron.trim().split(/\\s+/);\n \n // Cron expressions should have 5 or 6 parts (with or without seconds)\n if (cronParts.length < 5 || cronParts.length > 6) {\n throw new Error(`Cron 表达式格式无效。期望 5 或 6 部分,实际得到 ${cronParts.length} 部分 (Invalid cron format. Expected 5 or 6 parts, got ${cronParts.length})`);\n }\n\n // Determine if this is a 6-part (with seconds) or 5-part expression\n const hasSecs = cronParts.length === 6;\n const offset = hasSecs ? 0 : -1;\n\n // Extract parts with proper indexing\n const seconds = hasSecs ? cronParts[0] : null;\n const minutes = cronParts[offset + 1];\n const hours = cronParts[offset + 2];\n const dayOfMonth = cronParts[offset + 3];\n const month = cronParts[offset + 4];\n const dayOfWeek = cronParts[offset + 5];\n\n // Validate seconds (0-59) if present\n if (seconds !== null) {\n validateCronField(seconds, 0, 59, 'seconds', '秒');\n }\n\n // Validate minutes (0-59)\n validateCronField(minutes, 0, 59, 'minutes', '分钟');\n\n // Validate hours (0-23)\n validateCronField(hours, 0, 23, 'hours', '小时');\n\n // Validate day of month (1-31)\n validateCronField(dayOfMonth, 1, 31, 'day of month', '日期');\n\n // Validate month (1-12 or JAN-DEC)\n validateCronField(month, 1, 12, 'month', '月份', ['JAN', 'FEB', 'MAR', 'APR', 'MAY', 'JUN', 'JUL', 'AUG', 'SEP', 'OCT', 'NOV', 'DEC']);\n\n // Validate day of week (0-7 or SUN-SAT, where 0 and 7 both represent Sunday)\n validateCronField(dayOfWeek, 0, 7, 'day of week', '星期', ['SUN', 'MON', 'TUE', 'WED', 'THU', 'FRI', 'SAT']);\n}\n\n/**\n * Validate individual cron field\n * @param field - Field value to validate\n * @param min - Minimum allowed value\n * @param max - Maximum allowed value\n * @param fieldName - English field name for error messages\n * @param fieldNameCN - Chinese field name for error messages\n * @param allowedStrings - Optional array of allowed string values (e.g., month/weekday names)\n */\nfunction validateCronField(\n field: string,\n min: number,\n max: number,\n fieldName: string,\n fieldNameCN: string,\n allowedStrings?: string[]\n): void {\n // Allow wildcard\n if (field === '*') {\n return;\n }\n\n // Allow question mark (for day of month / day of week)\n if (field === '?') {\n return;\n }\n\n // Check for allowed string values (month/weekday names)\n if (allowedStrings && allowedStrings.some(str => field.toUpperCase().includes(str))) {\n return;\n }\n\n // Step values (e.g., */5, 0-30/5)\n if (field.includes('/')) {\n const [range, step] = field.split('/');\n const stepValue = parseInt(step);\n \n if (isNaN(stepValue) || stepValue <= 0) {\n throw new Error(`${fieldNameCN}字段的步长值无效: ${step} (Invalid step value for ${fieldName}: ${step})`);\n }\n \n if (range !== '*') {\n validateCronField(range, min, max, fieldName, fieldNameCN, allowedStrings);\n }\n return;\n }\n\n // Range values (e.g., 1-5)\n if (field.includes('-')) {\n const [start, end] = field.split('-');\n const startValue = parseInt(start);\n const endValue = parseInt(end);\n \n if (isNaN(startValue) || startValue < min || startValue > max) {\n throw new Error(`${fieldNameCN}字段的范围起始值无效: ${start},必须在 ${min}-${max} 之间 (Invalid range start for ${fieldName}: ${start}, must be between ${min}-${max})`);\n }\n \n if (isNaN(endValue) || endValue < min || endValue > max) {\n throw new Error(`${fieldNameCN}字段的范围结束值无效: ${end},必须在 ${min}-${max} 之间 (Invalid range end for ${fieldName}: ${end}, must be between ${min}-${max})`);\n }\n \n if (startValue > endValue) {\n throw new Error(`${fieldNameCN}字段的范围无效: ${start}-${end},起始值不能大于结束值 (Invalid range for ${fieldName}: ${start}-${end}, start cannot be greater than end)`);\n }\n return;\n }\n\n // List values (e.g., 1,3,5)\n if (field.includes(',')) {\n const values = field.split(',');\n for (const value of values) {\n validateCronField(value.trim(), min, max, fieldName, fieldNameCN, allowedStrings);\n }\n return;\n }\n\n // Single numeric value\n const numValue = parseInt(field);\n if (isNaN(numValue) || numValue < min || numValue > max) {\n throw new Error(`${fieldNameCN}字段的值无效: ${field},必须在 ${min}-${max} 之间 (Invalid ${fieldName} value: ${field}, must be between ${min}-${max})`);\n }\n}\n\n/**\n * Validate RedLock method-level options\n * @param options - RedLock method options to validate\n * @throws {Error} When options are invalid\n */\nexport function validateRedLockMethodOptions(options: RedLockMethodOptions): void {\n if (!options || typeof options !== 'object') {\n throw new Error('RedLock method options must be an object');\n }\n\n if (options.lockTimeOut !== undefined) {\n if (typeof options.lockTimeOut !== 'number' || options.lockTimeOut <= 0) {\n throw new Error('lockTimeOut must be a positive number');\n }\n }\n\n if (options.clockDriftFactor !== undefined) {\n if (typeof options.clockDriftFactor !== 'number' || options.clockDriftFactor < 0 || options.clockDriftFactor > 1) {\n throw new Error('clockDriftFactor must be a number between 0 and 1');\n }\n }\n\n if (options.maxRetries !== undefined) {\n if (typeof options.maxRetries !== 'number' || options.maxRetries < 0) {\n throw new Error('maxRetries must be a non-negative number');\n }\n }\n\n if (options.retryDelayMs !== undefined) {\n if (typeof options.retryDelayMs !== 'number' || options.retryDelayMs < 0) {\n throw new Error('retryDelayMs must be a non-negative number');\n }\n }\n}\n\n/**\n * Validate RedLock options\n * @param options - RedLock options to validate\n * @throws {Error} When options are invalid\n */\nexport function validateRedLockOptions(options: RedLockOptions): void {\n if (!options || typeof options !== 'object') {\n throw new Error('RedLock options must be an object');\n }\n\n if (options.lockTimeOut !== undefined) {\n if (typeof options.lockTimeOut !== 'number' || options.lockTimeOut <= 0) {\n throw new Error('lockTimeOut must be a positive number');\n }\n }\n\n if (options.retryCount !== undefined) {\n if (typeof options.retryCount !== 'number' || options.retryCount < 0) {\n throw new Error('retryCount must be a non-negative number');\n }\n }\n\n if (options.retryDelay !== undefined) {\n if (typeof options.retryDelay !== 'number' || options.retryDelay < 0) {\n throw new Error('retryDelay must be a non-negative number');\n }\n }\n\n if (options.retryJitter !== undefined) {\n if (typeof options.retryJitter !== 'number' || options.retryJitter < 0) {\n throw new Error('retryJitter must be a non-negative number');\n }\n }\n}\n\n//==================== Global Configuration Management ====================\n\n/**\n * Global configuration storage\n */\nlet globalScheduledOptions: ScheduledOptions = {};\n\n/**\n * Set global scheduled options\n * @param options - Global scheduled options\n */\nexport function setGlobalScheduledOptions(options: ScheduledOptions): void {\n globalScheduledOptions = { ...options };\n}\n\n/**\n * Get global scheduled options\n * @returns Global scheduled options\n */\nexport function getGlobalScheduledOptions(): ScheduledOptions {\n return globalScheduledOptions;\n}\n\n/**\n * Get effective timezone with priority: user specified > global > default\n * @param userTimezone - User specified timezone\n * @returns Effective timezone\n */\nexport function getEffectiveTimezone(options: ScheduledOptions, userTimezone?: string): string {\n return userTimezone || options.timezone || 'Asia/Beijing';\n}\n\n\n\n/**\n * Get effective RedLock method options with priority: method options > global options > defaults\n * @param methodOptions - Method-level RedLock options\n * @returns Effective RedLock method options with all defaults applied\n */\nexport function getEffectiveRedLockOptions(methodOptions?: RedLockMethodOptions): RedLockMethodOptions {\n const globalOptions = getGlobalScheduledOptions();\n \n return {\n lockTimeOut: methodOptions?.lockTimeOut || globalOptions.lockTimeOut || 10000,\n clockDriftFactor: methodOptions?.clockDriftFactor || globalOptions.clockDriftFactor || 0.01,\n maxRetries: methodOptions?.maxRetries || globalOptions.maxRetries || 3,\n retryDelayMs: methodOptions?.retryDelayMs || globalOptions.retryDelayMs || 200\n };\n} ","/*\n * @Description: Abstract interfaces for Redis client and distributed lock\n * @Usage: \n * @Author: richen\n * @Date: 2025-10-30 12:00:00\n * @LastEditTime: 2025-10-30 12:00:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport type { Lock, Settings } from \"@sesamecare-oss/redlock\";\n\n/**\n * Redis connection mode\n */\nexport enum RedisMode {\n STANDALONE = 'standalone', // 单机模式\n SENTINEL = 'sentinel', // 哨兵模式\n CLUSTER = 'cluster' // 集群模式\n}\n\n/**\n * Base Redis configuration\n */\nexport interface BaseRedisConfig {\n mode?: RedisMode;\n host?: string;\n port?: number;\n password?: string;\n db?: number;\n keyPrefix?: string;\n connectTimeout?: number;\n commandTimeout?: number;\n maxRetriesPerRequest?: number;\n}\n\n/**\n * Sentinel configuration\n */\nexport interface RedisSentinelConfig extends BaseRedisConfig {\n mode: RedisMode.SENTINEL;\n sentinels: Array<{ host: string; port: number }>;\n name: string; // sentinel master name\n sentinelPassword?: string;\n}\n\n/**\n * Cluster configuration\n */\nexport interface RedisClusterConfig extends BaseRedisConfig {\n mode: RedisMode.CLUSTER;\n nodes: Array<{ host: string; port: number }>;\n redisOptions?: {\n password?: string;\n db?: number;\n };\n}\n\n/**\n * Standalone configuration\n */\nexport interface RedisStandaloneConfig extends BaseRedisConfig {\n mode?: RedisMode.STANDALONE;\n host: string;\n port: number;\n}\n\n/**\n * Union type for all Redis configurations\n */\nexport type RedisConfig = RedisStandaloneConfig | RedisSentinelConfig | RedisClusterConfig;\n\n/**\n * Abstract Redis client interface\n * Provides unified interface for different Redis implementations\n */\nexport interface IRedisClient {\n /**\n * Get connection status\n */\n readonly status: string;\n\n /**\n * Execute Redis command\n * @param command - Command name\n * @param args - Command arguments\n */\n call(command: string, ...args: any[]): Promise<any>;\n\n /**\n * Set a key-value pair\n * @param key - Key name\n * @param value - Value\n * @param mode - Optional mode (e.g., 'EX' for expiration)\n * @param duration - Optional duration in seconds\n */\n set(key: string, value: string | Buffer, mode?: string, duration?: number): Promise<'OK' | null>;\n\n /**\n * Get value by key\n * @param key - Key name\n */\n get(key: string): Promise<string | null>;\n\n /**\n * Delete one or more keys\n * @param keys - Key names\n */\n del(...keys: string[]): Promise<number>;\n\n /**\n * Check if key exists\n * @param key - Key name\n */\n exists(key: string): Promise<number>;\n\n /**\n * Evaluate Lua script\n * @param script - Lua script\n * @param numKeys - Number of keys\n * @param args - Script arguments\n */\n eval(script: string, numKeys: number, ...args: any[]): Promise<any>;\n\n /**\n * Close the connection\n */\n quit(): Promise<'OK'>;\n\n /**\n * Disconnect immediately\n */\n disconnect(): void;\n}\n\n/**\n * Abstract distributed lock interface\n * Allows for different lock implementations (RedLock, Zookeeper, etc.)\n */\nexport interface IDistributedLock {\n /**\n * Initialize the lock system\n */\n initialize(): Promise<void>;\n\n /**\n * Acquire a distributed lock\n * @param resources - Resource identifiers\n * @param ttl - Time to live in milliseconds\n */\n acquire(resources: string[], ttl: number): Promise<Lock>;\n\n /**\n * Release a lock\n * @param lock - Lock instance\n */\n release(lock: Lock): Promise<void>;\n\n /**\n * Extend lock TTL\n * @param lock - Lock instance\n * @param ttl - New TTL in milliseconds\n */\n extend(lock: Lock, ttl: number): Promise<Lock>;\n\n /**\n * Check if the lock system is ready\n */\n isReady(): boolean;\n\n /**\n * Get current configuration\n */\n getConfig(): any;\n\n /**\n * Close and cleanup\n */\n close(): Promise<void>;\n\n /**\n * Health check\n */\n healthCheck(): Promise<{ status: 'healthy' | 'unhealthy'; details: Record<string, any> }>;\n}\n\n/**\n * Lock configuration options\n */\nexport interface ILockOptions extends Partial<Settings> {\n lockTimeOut?: number;\n clockDriftFactor?: number;\n maxRetries?: number;\n retryDelayMs?: number;\n redisConfig?: RedisConfig;\n}\n\n","/*\n * @Description: Redis client factory supporting multiple modes\n * @Usage: \n * @Author: richen\n * @Date: 2025-10-30 12:00:00\n * @LastEditTime: 2025-10-30 12:00:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport Redis, { Cluster, RedisOptions, ClusterOptions } from \"ioredis\";\nimport { DefaultLogger as logger } from \"koatty_logger\";\nimport {\n IRedisClient,\n RedisConfig,\n RedisMode,\n RedisStandaloneConfig,\n RedisSentinelConfig,\n RedisClusterConfig\n} from \"./interface\";\n\n/**\n * Redis client wrapper that implements IRedisClient interface\n * Wraps ioredis client to provide unified interface\n */\nclass RedisClientAdapter implements IRedisClient {\n constructor(private client: Redis | Cluster) {}\n\n get status(): string {\n return this.client.status;\n }\n\n async call(command: string, ...args: any[]): Promise<any> {\n return this.client.call(command, ...args);\n }\n\n async set(key: string, value: string | Buffer, mode?: string, duration?: number): Promise<'OK' | null> {\n if (mode && duration) {\n // Use type assertion for mode parameter due to ioredis strict typing\n return this.client.set(key, value, mode as any, duration) as Promise<'OK' | null>;\n }\n return this.client.set(key, value);\n }\n\n async get(key: string): Promise<string | null> {\n return this.client.get(key);\n }\n\n async del(...keys: string[]): Promise<number> {\n return this.client.del(...keys);\n }\n\n async exists(key: string): Promise<number> {\n return this.client.exists(key);\n }\n\n async eval(script: string, numKeys: number, ...args: any[]): Promise<any> {\n return this.client.eval(script, numKeys, ...args);\n }\n\n async quit(): Promise<'OK'> {\n return this.client.quit();\n }\n\n disconnect(): void {\n this.client.disconnect();\n }\n\n /**\n * Get underlying Redis/Cluster instance\n * Used for RedLock initialization\n */\n getClient(): Redis | Cluster {\n return this.client;\n }\n}\n\n/**\n * Redis client factory\n * Creates appropriate Redis client based on configuration\n */\nexport class RedisFactory {\n /**\n * Create Redis client based on configuration mode\n * @param config - Redis configuration\n * @returns Redis client adapter\n */\n static createClient(config: RedisConfig): RedisClientAdapter {\n const mode = config.mode || RedisMode.STANDALONE;\n\n logger.Debug(`Creating Redis client in ${mode} mode`);\n\n switch (mode) {\n case RedisMode.STANDALONE:\n return this.createStandaloneClient(config as RedisStandaloneConfig);\n \n case RedisMode.SENTINEL:\n return this.createSentinelClient(config as RedisSentinelConfig);\n \n case RedisMode.CLUSTER:\n return this.createClusterClient(config as RedisClusterConfig);\n \n default:\n throw new Error(`不支持的 Redis 模式: ${mode} (Unsupported Redis mode: ${mode})`);\n }\n }\n\n /**\n * Create standalone Redis client\n * @param config - Standalone configuration\n */\n private static createStandaloneClient(config: RedisStandaloneConfig): RedisClientAdapter {\n logger.Debug(`Creating standalone Redis client: ${config.host}:${config.port}`);\n\n const options: RedisOptions = {\n host: config.host,\n port: config.port,\n password: config.password || undefined,\n db: config.db || 0,\n keyPrefix: config.keyPrefix || '',\n connectTimeout: config.connectTimeout || 10000,\n commandTimeout: config.commandTimeout || 5000,\n maxRetriesPerRequest: config.maxRetriesPerRequest || 3,\n retryStrategy: (times: number) => {\n const delay = Math.min(times * 50, 2000);\n logger.Debug(`Redis reconnecting, attempt ${times}, delay ${delay}ms`);\n return delay;\n },\n reconnectOnError: (err: Error) => {\n logger.Warn('Redis connection error, attempting reconnect:', err.message);\n return true;\n }\n };\n\n const client = new Redis(options);\n\n client.on('connect', () => {\n logger.Info('Redis standalone client connected successfully');\n });\n\n client.on('error', (err: Error) => {\n logger.Error('Redis standalone client error:', err);\n });\n\n return new RedisClientAdapter(client);\n }\n\n /**\n * Create sentinel Redis client\n * @param config - Sentinel configuration\n */\n private static createSentinelClient(config: RedisSentinelConfig): RedisClientAdapter {\n logger.Debug(`Creating sentinel Redis client for master: ${config.name}`);\n\n const options: RedisOptions = {\n sentinels: config.sentinels,\n name: config.name,\n password: config.password || undefined,\n sentinelPassword: config.sentinelPassword || undefined,\n db: config.db || 0,\n keyPrefix: config.keyPrefix || '',\n connectTimeout: config.connectTimeout || 10000,\n commandTimeout: config.commandTimeout || 5000,\n maxRetriesPerRequest: config.maxRetriesPerRequest || 3,\n retryStrategy: (times: number) => {\n const delay = Math.min(times * 50, 2000);\n logger.Debug(`Sentinel Redis reconnecting, attempt ${times}, delay ${delay}ms`);\n return delay;\n }\n };\n\n const client = new Redis(options);\n\n client.on('connect', () => {\n logger.Info(`Redis sentinel client connected to master: ${config.name}`);\n });\n\n client.on('error', (err: Error) => {\n logger.Error('Redis sentinel client error:', err);\n });\n\n return new RedisClientAdapter(client);\n }\n\n /**\n * Create cluster Redis client\n * @param config - Cluster configuration\n */\n private static createClusterClient(config: RedisClusterConfig): RedisClientAdapter {\n logger.Debug(`Creating cluster Redis client with ${config.nodes.length} nodes`);\n\n const clusterOptions: ClusterOptions = {\n redisOptions: {\n password: config.redisOptions?.password || config.password || undefined,\n db: config.redisOptions?.db || config.db || 0,\n keyPrefix: config.keyPrefix || '',\n connectTimeout: config.connectTimeout || 10000,\n commandTimeout: config.commandTimeout || 5000,\n maxRetriesPerRequest: config.maxRetriesPerRequest || 3\n },\n clusterRetryStrategy: (times: number) => {\n const delay = Math.min(times * 50, 2000);\n logger.Debug(`Cluster Redis reconnecting, attempt ${times}, delay ${delay}ms`);\n return delay;\n }\n };\n\n const cluster = new Cluster(config.nodes, clusterOptions);\n\n cluster.on('connect', () => {\n logger.Info('Redis cluster client connected successfully');\n });\n\n cluster.on('error', (err: Error) => {\n logger.Error('Redis cluster client error:', err);\n });\n\n cluster.on('node error', (err: Error, address: string) => {\n logger.Error(`Redis cluster node error at ${address}:`, err);\n });\n\n return new RedisClientAdapter(cluster);\n }\n\n /**\n * Validate Redis configuration\n * @param config - Redis configuration to validate\n */\n static validateConfig(config: RedisConfig): void {\n if (!config) {\n throw new Error('Redis 配置不能为空 (Redis configuration cannot be empty)');\n }\n\n const mode = config.mode || RedisMode.STANDALONE;\n\n switch (mode) {\n case RedisMode.STANDALONE:\n this.validateStandaloneConfig(config as RedisStandaloneConfig);\n break;\n \n case RedisMode.SENTINEL:\n this.validateSentinelConfig(config as RedisSentinelConfig);\n break;\n \n case RedisMode.CLUSTER:\n this.validateClusterConfig(config as RedisClusterConfig);\n break;\n \n default:\n throw new Error(`不支持的 Redis 模式: ${mode} (Unsupported Redis mode: ${mode})`);\n }\n }\n\n private static validateStandaloneConfig(config: RedisStandaloneConfig): void {\n if (!config.host) {\n throw new Error('单机模式需要 host 配置 (Standalone mode requires host configuration)');\n }\n if (!config.port) {\n throw new Error('单机模式需要 port 配置 (Standalone mode requires port configuration)');\n }\n }\n\n private static validateSentinelConfig(config: RedisSentinelConfig): void {\n if (!config.sentinels || config.sentinels.length === 0) {\n throw new Error('哨兵模式需要至少一个哨兵节点配置 (Sentinel mode requires at least one sentinel node)');\n }\n if (!config.name) {\n throw new Error('哨兵模式需要 master name 配置 (Sentinel mode requires master name)');\n }\n }\n\n private static validateClusterConfig(config: RedisClusterConfig): void {\n if (!config.nodes || config.nodes.length === 0) {\n throw new Error('集群模式需要至少一个节点配置 (Cluster mode requires at least one node)');\n }\n }\n}\n\nexport { RedisClientAdapter };\n\n","/*\n * @Description: RedLock utility for distributed locks\n * @Usage: \n * @Author: richen\n * @Date: 2021-11-17 16:18:33\n * @LastEditTime: 2024-01-17 15:00:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport { Redlock, Lock, Settings } from \"@sesamecare-oss/redlock\";\nimport { DefaultLogger as logger } from \"koatty_logger\";\nimport { IOCContainer } from \"koatty_container\";\nimport { IDistributedLock, ILockOptions, RedisConfig, RedisMode } from \"./interface\";\nimport { RedisFactory, RedisClientAdapter } from \"./redis-factory\";\n\n/**\n * Configuration options for RedLock\n * @deprecated Use ILockOptions from interface instead\n */\nexport interface RedLockOptions extends ILockOptions {\n redisConfig?: RedisConfig;\n}\n\n/**\n * Default RedLock configuration\n */\nconst defaultRedLockConfig: RedLockOptions = {\n lockTimeOut: 10000,\n clockDriftFactor: 0.01,\n maxRetries: 3,\n retryDelayMs: 200,\n redisConfig: {\n mode: RedisMode.STANDALONE,\n host: '127.0.0.1',\n port: 6379,\n password: '',\n db: 0,\n keyPrefix: 'redlock:'\n }\n};\n\n/**\n * Default Redlock Settings for @sesamecare-oss/redlock\n */\nconst defaultRedlockSettings: Partial<Settings> = {\n driftFactor: 0.01,\n retryCount: 3,\n retryDelay: 200,\n retryJitter: 200,\n automaticExtensionThreshold: 500\n};\n\n/**\n * RedLock distributed lock manager\n * Integrated with koatty IOC container\n * Implements singleton pattern for safe instance management\n * Implements IDistributedLock interface for abstraction\n */\nexport class RedLocker implements IDistributedLock {\n private static instance: RedLocker | null = null;\n private static readonly instanceLock = Symbol('RedLocker.instanceLock');\n \n private redlock: Redlock | null = null;\n private redisClient: RedisClientAdapter | null = null;\n private config: RedLockOptions;\n private isInitialized = false;\n private initializationPromise: Promise<void> | null = null;\n\n // 私有构造函数防止外部直接实例化\n private constructor(options?: RedLockOptions) {\n this.config = { ...defaultRedLockConfig, ...options };\n // Register this instance in IOC container\n this.registerInContainer();\n }\n\n /**\n * Register RedLocker in IOC container\n * @private\n */\n private registerInContainer(): void {\n try {\n // Register as a singleton component in IOC container\n IOCContainer.reg('RedLocker', this, {\n type: 'COMPONENT',\n args: []\n });\n logger.Debug('RedLocker registered in IOC container');\n } catch (_error) {\n logger.Warn('Failed to register RedLocker in IOC container:', _error);\n }\n }\n\n /**\n * Get RedLocker singleton instance with thread-safe initialization\n * @static\n * @param options - RedLock configuration options (only used for first initialization)\n * @returns RedLocker singleton instance\n */\n public static getInstance(options?: RedLockOptions): RedLocker {\n // 双重检查锁定模式确保线程安全\n if (!RedLocker.instance) {\n // 首次创建时使用选项,后续调用忽略选项参数\n if (RedLocker.instance === null) {\n try {\n // 尝试从IOC容器获取已存在的实例\n const containerInstance = IOCContainer.get('RedLocker', 'COMPONENT') as RedLocker;\n if (containerInstance) {\n RedLocker.instance = containerInstance;\n logger.Debug('Retrieved existing RedLocker instance from IOC container');\n } else {\n // 创建新的单例实例\n RedLocker.instance = new RedLocker(options);\n logger.Debug('Created new RedLocker singleton instance');\n }\n } catch {\n // IOC容器不可用时直接创建\n RedLocker.instance = new RedLocker(options);\n logger.Debug('Created new RedLocker instance outside IOC container');\n }\n }\n } else if (options) {\n // 如果实例已存在但传入了新选项,记录警告\n logger.Warn('RedLocker instance already exists, ignoring new options. Use updateConfig() to change configuration.');\n }\n \n return RedLocker.instance;\n }\n\n /**\n * Reset singleton instance (主要用于测试)\n * @static\n */\n public static resetInstance(): void {\n if (RedLocker.instance) {\n RedLocker.instance.close().catch(err => \n logger.Warn('Error while closing RedLocker instance during reset:', err)\n );\n RedLocker.instance = null;\n }\n }\n\n /**\n * Initialize RedLock with Redis connection\n * Uses cached promise to avoid duplicate initialization\n * @private\n */\n public async initialize(): Promise<void> {\n // 如果已经初始化,直接返回\n if (this.isInitialized) {\n return;\n }\n \n // 如果正在初始化,等待现有的初始化完成\n if (this.initializationPromise) {\n return this.initializationPromise;\n }\n \n // 创建初始化Promise并缓存\n this.initializationPromise = this.performInitialization();\n \n try {\n await this.initializationPromise;\n } catch (error) {\n // 初始化失败时完整清理状态,允许重试\n this.initializationPromise = null;\n this.isInitialized = false;\n this.redlock = null;\n // 注意:不清理 redis 连接,因为它可能来自 IOC 容器\n logger.Warn('RedLocker initialization failed, state has been reset for retry');\n throw error;\n }\n }\n \n /**\n * 执行实际的初始化操作\n * @private\n */\n private async performInitialization(): Promise<void> {\n\n try {\n // Validate Redis configuration\n if (this.config.redisConfig) {\n RedisFactory.validateConfig(this.config.redisConfig);\n }\n\n // Try to get Redis instance from IOC container first\n try {\n const existingRedis = IOCContainer.get('Redis', 'COMPONENT');\n // If Redis instance exists in container, wrap it\n if (existingRedis) {\n // Check if it's already a RedisClientAdapter\n if (existingRedis instanceof RedisClientAdapter) {\n this.redisClient = existingRedis;\n } else {\n // Wrap raw Redis/Cluster instance (type assertion needed)\n this.redisClient = new RedisClientAdapter(existingRedis as any);\n }\n logger.Debug('Using Redis instance from IOC container');\n }\n } catch {\n // IOC container doesn't have Redis, create new connection\n }\n\n // Create new Redis connection if not available in container\n if (!this.redisClient && this.config.redisConfig) {\n this.redisClient = RedisFactory.createClient(this.config.redisConfig);\n logger.Debug('Created new Redis connection for RedLocker');\n }\n\n if (!this.redisClient) {\n throw new Error('Failed to initialize Redis connection: no configuration provided');\n }\n\n // Get underlying client for Redlock\n const underlyingClient = this.redisClient.getClient();\n\n // Merge default settings with user configuration\n // Extract Settings properties from config (which extends Partial<Settings>)\n const userSettings: any = this.config;\n const redlockSettings: Partial<Settings> = {\n ...defaultRedlockSettings,\n ...(userSettings.driftFactor !== undefined && { driftFactor: userSettings.driftFactor }),\n ...(userSettings.retryCount !== undefined && { retryCount: userSettings.retryCount }),\n ...(userSettings.retryDelay !== undefined && { retryDelay: userSettings.retryDelay }),\n ...(userSettings.retryJitter !== undefined && { retryJitter: userSettings.retryJitter }),\n ...(userSettings.automaticExtensionThreshold !== undefined && { \n automaticExtensionThreshold: userSettings.automaticExtensionThreshold \n })\n };\n\n // Initialize Redlock with the Redis instance\n this.redlock = new Redlock([underlyingClient], redlockSettings);\n\n // Set up error handlers\n this.redlock.on('clientError', (err: Error) => {\n logger.Error('Redis client error in RedLock:', err);\n });\n\n this.isInitialized = true;\n logger.Info('RedLocker initialized successfully');\n } catch (error) {\n this.isInitialized = false;\n logger.Error('Failed to initialize RedLocker:', error);\n throw new Error(`RedLocker initialization failed: ${error instanceof Error ? error.message : 'Unknown error'}`);\n }\n }\n\n /**\n * Acquire a distributed lock\n * @param resources - Resource identifiers to lock\n * @param ttl - Time to live in milliseconds\n * @returns Promise<Lock>\n */\n async acquire(resources: string[], ttl?: number): Promise<Lock> {\n if (!Array.isArray(resources) || resources.length === 0) {\n throw new Error('Resources array cannot be empty');\n }\n\n const lockTtl = ttl || this.config.lockTimeOut;\n if (lockTtl <= 0) {\n throw new Error('Lock TTL must be positive');\n }\n\n // Ensure RedLocker is initialized\n await this.initialize();\n\n if (!this.redlock) {\n throw new Error('RedLock is not initialized');\n }\n\n try {\n // Add key prefix to resources\n const prefixedResources = resources.map(resource => \n `${this.config.redisConfig.keyPrefix}${resource}`\n );\n\n logger.Debug(`Acquiring lock for resources: ${prefixedResources.join(', ')} with TTL: ${lockTtl}ms`);\n \n const lock = await this.redlock.acquire(prefixedResources, lockTtl);\n logger.Debug(`Lock acquired successfully for resources: ${prefixedResources.join(', ')}`);\n \n return lock;\n } catch (error) {\n logger.Error(`Failed to acquire lock for resources: ${resources.join(', ')}`, error);\n // 保留原始错误信息,避免过度包装\n if (error instanceof Error) {\n error.message = `Lock acquisition failed: ${error.message}`;\n throw error;\n }\n throw new Error(`Lock acquisition failed: Unknown error`);\n }\n }\n\n /**\n * Release a lock\n * @param lock - Lock instance to release\n */\n async release(lock: Lock): Promise<void> {\n if (!lock) {\n throw new Error('Lock instance is required');\n }\n\n try {\n await lock.release();\n logger.Debug('Lock released successfully');\n } catch (error) {\n logger.Error('Failed to release lock:', error);\n // 保留原始错误信息\n if (error instanceof Error) {\n error.message = `Lock release failed: ${error.message}`;\n throw error;\n }\n throw new Error(`Lock release failed: Unknown error`);\n }\n }\n\n /**\n * Extend a lock's TTL\n * @param lock - Lock instance to extend\n * @param ttl - New TTL in milliseconds\n * @returns Extended lock\n */\n async extend(lock: Lock, ttl: number): Promise<Lock> {\n if (!lock) {\n throw new Error('Lock instance is required');\n }\n\n if (ttl <= 0) {\n throw new Error('TTL must be positive');\n }\n\n try {\n const extendedLock = await lock.extend(ttl);\n logger.Debug(`Lock extended successfully with TTL: ${ttl}ms`);\n return extendedLock;\n } catch (error) {\n logger.Error('Failed to extend lock:', error);\n throw new Error(`Lock extension failed: ${error instanceof Error ? error.message : 'Unknown error'}`);\n }\n }\n\n /**\n * Check if RedLocker is initialized\n * @returns true if initialized, false otherwise\n */\n isReady(): boolean {\n return this.isInitialized && !!this.redlock && !!this.redisClient;\n }\n\n /**\n * Get current configuration\n * @returns Current RedLock configuration\n */\n getConfig(): RedLockOptions {\n return { ...this.config };\n }\n\n /**\n * Update configuration (requires reinitialization)\n * @param options - New RedLock options\n */\n updateConfig(options?: Partial<RedLockOptions>): void {\n if (options) {\n this.config = { ...this.config, ...options };\n }\n\n // 清理初始化状态,强制重新初始化\n this.isInitialized = false;\n this.initializationPromise = null;\n this.redlock = null;\n \n logger.Debug('RedLocker configuration updated, will reinitialize on next use');\n }\n\n /**\n * Close Redis connection and cleanup\n */\n async close(): Promise<void> {\n try {\n if (this.redisClient && this.redisClient.status === 'ready') {\n await this.redisClient.quit();\n logger.Debug('Redis connection closed');\n }\n \n this.redisClient = null;\n this.redlock = null;\n this.isInitialized = false;\n } catch (error) {\n logger.Error('Error closing RedLocker:', error);\n }\n }\n\n /**\n * Get container registration status\n * @returns Registration information\n */\n getContainerInfo(): { registered: boolean; identifier: string } {\n try {\n const instance = IOCContainer.get('RedLocker', 'COMPONENT');\n return {\n registered: !!instance,\n identifier: 'RedLocker'\n };\n } catch {\n return {\n registered: false,\n identifier: 'RedLocker'\n };\n }\n }\n\n /**\n * Health check for RedLocker\n * @returns Health status\n */\n async healthCheck(): Promise<{ status: 'healthy' | 'unhealthy'; details: Record<string, any> }> {\n try {\n await this.initialize();\n \n const redisStatus = this.redisClient?.status || 'unknown';\n const isReady = this.isReady();\n \n return {\n status: isReady ? 'healthy' : 'unhealthy',\n details: {\n initialized: this.isInitialized,\n redisStatus,\n redisMode: this.config.redisConfig?.mode || 'unknown',\n redlockReady: !!this.redlock,\n containerRegistered: this.getContainerInfo().registered\n }\n };\n } catch (error) {\n return {\n status: 'unhealthy',\n details: {\n error: error instanceof Error ? error.message : 'Unknown error',\n initialized: this.isInitialized\n }\n };\n }\n }\n}","/*\n * @Description: \n * @Usage: \n * @Author: richen\n * @Date: 2024-01-16 19:53:14\n * @LastEditTime: 2024-11-07 16:47:58\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\n/**\n * 返回一个可取消的 Promise,在指定时间后 reject\n * @param ms 超时时间(毫秒)\n * @returns 带有 cancel 方法的 Promise\n */\nexport interface CancelablePromise<T> extends Promise<T> {\n cancel: () => void;\n}\n\nexport function timeoutPromise(ms: number): CancelablePromise<never> {\n let timeoutId: NodeJS.Timeout | null = null;\n \n const promise = new Promise<never>((resolve, reject) => {\n timeoutId = setTimeout(() => {\n timeoutId = null;\n reject(new Error('TIME_OUT_ERROR'));\n }, ms);\n }) as CancelablePromise<never>;\n\n // 添加取消方法,防止内存泄漏\n promise.cancel = () => {\n if (timeoutId !== null) {\n clearTimeout(timeoutId);\n timeoutId = null;\n }\n };\n\n return promise;\n}\n/**\n * @description: 使用 Promise.resolve 包装不确定的函数,并捕获错误\n * @param {Function} fn\n * @param {any} args\n * @return {*}\n */\nexport function wrappedPromise(fn: Function, args: any[]) {\n return new Promise((resolve, reject) => {\n try {\n const result = fn(...args);\n resolve(result);\n } catch (error) {\n reject(error);\n }\n });\n}\n","/*\n * @Description: Decorator preprocessing mechanism for koatty_schedule\n * @Usage: \n * @Author: richen\n * @Date: 2024-01-17 16:00:00\n * @LastEditTime: 2024-01-17 16:00:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport { IOCContainer } from \"koatty_container\";\nimport { RedLocker, RedLockOptions } from \"../locker/redlock\";\nimport { Helper } from \"koatty_lib\";\nimport { DefaultLogger as logger } from \"koatty_logger\";\nimport { Lock } from \"@sesamecare-oss/redlock\";\nimport { timeoutPromise } from \"../utils/lib\";\nimport { Koatty } from \"koatty_core\";\nimport { RedLockMethodOptions, getEffectiveRedLockOptions } from \"../config/config\";\n\n/**\n * Initiation schedule locker client.\n *\n * @param {RedLockOptions} options - RedLock 配置选项\n * @param {Koatty} app - Koatty 应用实例\n * @returns {Promise<void>} \n */\nexport async function initRedLock(options: RedLockOptions, app: Koatty): Promise<void> {\n if (!app || !Helper.isFunction(app.once)) {\n logger.Warn(`RedLock initialization skipped: Koatty app not available or not initialized`);\n return;\n }\n try {\n if (Helper.isEmpty(options)) {\n throw Error(`Missing RedLock configuration. Please write a configuration item with the key name 'RedLock' in the db.ts file.`);\n }\n // 获取RedLocker实例,在首次使用时自动初始化\n const redLocker = RedLocker.getInstance(options);\n await redLocker.initialize();\n logger.Info('RedLock initialized successfully');\n } catch (error) {\n logger.Error('Failed to initialize RedLock:', error);\n throw error;\n }\n}\n\n/**\n * Create redLocker Descriptor with improved error handling and type safety\n * @param descriptor - Property descriptor\n * @param name - Lock name\n * @param method - Method name\n * @param methodOptions - Method-level RedLock options\n * @returns Enhanced property descriptor\n */\nexport function redLockerDescriptor(\n descriptor: PropertyDescriptor,\n name: string,\n method: string,\n methodOptions?: RedLockMethodOptions\n): PropertyDescriptor {\n // 参数验证\n if (!descriptor) {\n throw new Error('Property descriptor is required');\n }\n if (!name || typeof name !== 'string') {\n throw new Error('Lock name must be a non-empty string');\n }\n if (!method || typeof method !== 'string') {\n throw new Error('Method name must be a non-empty string');\n }\n\n const { value, configurable, enumerable } = descriptor;\n\n // 验证原始函数\n if (typeof value !== 'function') {\n throw new Error('Descriptor value must be a function');\n }\n\n /**\n * Enhanced function wrapper with proper lock renewal and safety\n */\n const valueFunction = async (\n self: unknown,\n initialLock: Lock,\n lockTime: number,\n timeout: number,\n props: unknown[]\n ): Promise<unknown> => {\n let currentLock = initialLock;\n let remainingTime = timeout;\n const maxExtensions = 3; // 限制续期次数防止无限循环\n let extensionCount = 0;\n \n try {\n while (remainingTime > 0 && extensionCount < maxExtensions) {\n // 创建可取消的超时 Promise\n const timeoutHandler = timeoutPromise(remainingTime);\n \n try {\n // 执行业务方法,与超时竞争\n const result = await Promise.race([\n value.apply(self, props),\n timeoutHandler\n ]);\n \n // 成功执行,取消超时定时器防止内存泄漏\n timeoutHandler.cancel();\n return result;\n } catch (error) {\n // 无论什么错误,都要取消超时定时器\n timeoutHandler.cancel();\n \n // 处理超时错误,尝试续期锁\n if (error instanceof Error && error.message === 'TIME_OUT_ERROR') {\n extensionCount++;\n logger.Debug(`Method ${method} execution timeout, attempting lock extension ${extensionCount}/${maxExtensions}`);\n \n try {\n // 续期锁,获得新的锁实例\n currentLock = await currentLock.extend(lockTime);\n remainingTime = lockTime - 200; // 预留200ms用于锁操作\n logger.Debug(`Lock extended for method: ${method}, remaining time: ${remainingTime}ms`);\n \n // 继续循环,重新执行业务方法\n continue;\n } catch (extendError) {\n logger.Error(`Failed to extend lock for method: ${method}`, extendError);\n throw new Error(`Lock extension failed: ${extendError instanceof Error ? extendError.message : 'Unknown error'}`);\n }\n } else {\n // 非超时错误,直接抛出\n throw error;\n }\n }\n }\n \n // 达到最大续期次数或剩余时间不足\n throw new Error(`Method ${method} execution timeout after ${extensionCount} lock extensions`);\n } finally {\n // 确保锁被释放\n try {\n await currentLock.release();\n logger.Debug(`Lock released for method: ${method}`);\n } catch (releaseError) {\n logger.Warn(`Failed to release lock for method: ${method}`, releaseError);\n }\n }\n };\n\n return {\n configurable,\n enumerable,\n writable: true,\n async value(...props: unknown[]): Promise<unknown> {\n try {\n const redlock = RedLocker.getInstance();\n const lockOptions = getEffectiveRedLockOptions(methodOptions);\n // Acquire a lock.\n const lockTime = lockOptions.lockTimeOut || 10000;\n if (lockTime <= 200) {\n throw new Error(\"Lock timeout must be greater than 200ms to allow for proper execution\");\n }\n\n const lock = await redlock.acquire([method, name], lockTime);\n const timeout = lockTime - 200;\n\n logger.Debug(`Lock acquired for method: ${method}, timeout: ${timeout}ms`);\n return await valueFunction(this, lock, lockTime, timeout, props);\n } catch (error) {\n logger.Error(`RedLock operation failed for method: ${method}`, error);\n throw error;\n }\n },\n };\n}\n\n/**\n * Generate lock name for RedLock decorator\n */\nexport function generateLockName(configName: string | undefined, methodName: string, target: unknown): string {\n if (configName) {\n return configName;\n }\n\n try {\n const targetObj = target as object | Function;\n const identifier = IOCContainer.getIdentifier(targetObj);\n if (identifier) {\n return `${identifier}_${methodName}`;\n }\n } catch {\n // Fallback if IOC container is not available\n }\n\n const targetWithConstructor = target as { constructor?: Function };\n const className = targetWithConstructor.constructor?.name || 'Unknown';\n return `${className}_${methodName}`;\n}","/*\n * @Description: \n * @Usage: \n * @Author: richen\n * @Date: 2025-06-09 16:00:00\n * @LastEditTime: 2025-06-09 16:00:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport { IOCContainer } from \"koatty_container\";\nimport { RedLockMethodOptions, validateRedLockMethodOptions } from \"../config/config\";\nimport { redLockerDescriptor, generateLockName } from \"../process/locker\";\n\n/**\n * Redis-based distributed lock decorator\n *\n * @export\n * @param {string} [name] - The locker name. If name is duplicated, lock sharing contention will result.\n * If not provided, a unique name will be auto-generated using method name + random suffix.\n * IMPORTANT: Auto-generated names are unique per method deployment and not predictable.\n * @param {RedLockMethodOptions} [options] - Lock configuration options for this method\n * \n * @returns {MethodDecorator}\n * @throws {Error} When decorator is used on wrong class type or invalid configuration\n * \n * @example\n * ```typescript\n * class UserService {\n * @RedLock('user_update_lock', { lockTimeOut: 5000, maxRetries: 2 })\n * async updateUser(id: string, data: any) {\n * // This method will be protected by a distributed lock with predictable name\n * }\n * \n * @RedLock() // Auto-generated unique name like \"deleteUser_abc123_xyz789\"\n * async deleteUser(id: string) {\n * // This method will be protected by a distributed lock with auto-generated unique name\n * }\n * }\n * ```\n */\nexport function RedLock(lockName?: string, options?: RedLockMethodOptions): MethodDecorator {\n return (target: unknown, propertyKey: string | symbol, descriptor: PropertyDescriptor) => {\n const methodName = propertyKey.toString();\n\n // 验证装饰器使用的类型(从原型对象获取类构造函数)\n const targetClass = (target as any).constructor;\n const componentType = IOCContainer.getType(targetClass);\n if (componentType !== \"SERVICE\" && componentType !== \"COMPONENT\") {\n throw Error(\"@RedLock decorator can only be used on SERVICE or COMPONENT classes.\");\n }\n\n // 验证方法名\n if (!methodName || typeof methodName !== 'string') {\n throw Error(\"Method name is required for @RedLock decorator\");\n }\n\n // 验证方法描述符\n if (!descriptor || typeof descriptor.value !== 'function') {\n throw Error(\"@RedLock decorator can only be applied to methods\");\n }\n\n // 生成锁名称:用户指定的 > 基于类名和方法名生成\n const finalLockName = lockName || generateLockName(lockName, methodName, target);\n\n // 验证选项\n if (options) {\n validateRedLockMethodOptions(options);\n }\n\n // 保存类到IOC容器\n IOCContainer.saveClass(\"COMPONENT\", targetClass, targetClass.name);\n\n try {\n // 直接在装饰器中包装方法,而不是延迟处理\n const enhancedDescriptor = redLockerDescriptor(\n descriptor,\n finalLockName,\n methodName,\n options\n );\n\n return enhancedDescriptor;\n } catch (error) {\n throw new Error(`Failed to apply RedLock to ${methodName}: ${(error as Error).message}`);\n }\n };\n}","/*\n * @Description: \n * @Usage: \n * @Author: richen\n * @Date: 2025-06-09 16:00:00\n * @LastEditTime: 2025-06-09 16:00:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport { Helper } from \"koatty_lib\";\nimport { COMPONENT_SCHEDULED, DecoratorType, validateCronExpression } from \"../config/config\";\nimport { IOCContainer } from \"koatty_container\";\n\n/**\n * Schedule task decorator with optimized preprocessing\n *\n * @export\n * @param {string} cron - Cron expression for task scheduling\n * @param {string} [timezone='Asia/Beijing'] - Timezone for the schedule\n * \n * Cron expression format:\n * * Seconds: 0-59\n * * Minutes: 0-59\n * * Hours: 0-23\n * * Day of Month: 1-31\n * * Months: 1-12 (Jan-Dec)\n * * Day of Week: 1-7 (Sun-Sat)\n * \n * @returns {MethodDecorator}\n * @throws {Error} When cron expression is invalid or decorator is used on wrong class type\n */\nexport function Scheduled(cron: string, timezone = 'Asia/Beijing'): MethodDecorator {\n // 参数验证\n if (Helper.isEmpty(cron)) {\n throw Error(\"Cron expression is required and cannot be empty\");\n }\n\n // 验证cron表达式格式\n try {\n validateCronExpression(cron);\n } catch (error) {\n throw Error(`Invalid cron expression: ${(error as Error).message}`);\n }\n\n // 验证时区\n if (timezone && typeof timezone !== 'string') {\n throw Error(\"Timezone must be a string\");\n }\n\n return (target: unknown, propertyKey: string | symbol, descriptor: PropertyDescriptor) => {\n // 验证装饰器使用的类型(从原型对象获取类构造函数)\n const targetClass = (target as any).constructor;\n const componentType = IOCContainer.getType(targetClass);\n if (componentType !== \"SERVICE\" && componentType !== \"COMPONENT\") {\n throw Error(\"@Scheduled decorator can only be used on SERVICE or COMPONENT classes.\");\n }\n\n // 验证方法名\n const methodName = propertyKey.toString();\n if (!methodName || typeof methodName !== 'string') {\n throw Error(\"Method name is required for @Scheduled decorator\");\n }\n\n // 验证方法描述符\n if (!descriptor || typeof descriptor.value !== 'function') {\n throw Error(\"@Scheduled decorator can only be applied to methods\");\n }\n // 保存类到IOC容器\n IOCContainer.saveClass(\"COMPONENT\", targetClass, targetClass.name);\n // 保存调度元数据到 IOC 容器\n IOCContainer.attachClassMetadata(COMPONENT_SCHEDULED, DecoratorType.SCHEDULED, {\n method: methodName,\n cron,\n timezone // 保存确定的时区值\n }, target as object, methodName);\n };\n}\n","/**\n * @ author: richen\n * @ copyright: Copyright (c) - <richenlin(at)gmail.com>\n * @ license: MIT\n * @ version: 2020-07-06 10:29:20\n */\nimport { IOCContainer } from \"koatty_container\";\nimport { Helper } from \"koatty_lib\";\nimport { DefaultLogger as logger } from \"koatty_logger\";\nimport { CronJob } from \"cron\";\nimport { COMPONENT_SCHEDULED, DecoratorType, getEffectiveTimezone } from \"../config/config\";\nimport { Koatty } from \"koatty_core\";\n\n/**\n * 初始化调度任务系统\n * 在appReady时触发批量注入调度任务,确保所有初始化工作完成\n *\n * @param {Koatty} app - Koatty 应用实例\n * @param {any} options - 调度任务配置\n */\nexport async function initSchedule(options: any, app: Koatty): Promise<void> {\n if (!app || !Helper.isFunction(app.once)) {\n logger.Warn(`Schedule initialization skipped: Koatty app not available or not initialized`);\n return;\n }\n try {\n await injectSchedule(options);\n logger.Info('Schedule system initialized successfully');\n } catch (error) {\n logger.Error('Failed to initialize Schedule system:', error);\n throw error;\n }\n}\n\n/**\n * Inject schedule job with enhanced error handling and validation\n *\n * @param {unknown} target - Target class\n * @param {string} method - Method name\n * @param {string} cron - Cron expression\n * @param {string} [timezone] - Timezone\n */\n/**\n * 批量注入调度任务 - 从IOC容器读取类元数据并创建所有CronJob\n */\nexport async function injectSchedule(options: any): Promise<void> {\n try {\n logger.Debug('Starting batch schedule injection...');\n\n const componentList = IOCContainer.listClass(\"COMPONENT\");\n for (const component of componentList) {\n const classMetadata = IOCContainer.getClassMetadata(COMPONENT_SCHEDULED, DecoratorType.SCHEDULED,\n component.target);\n if (!classMetadata) {\n continue;\n }\n let scheduledCount = 0;\n\n for (const [className, metadata] of classMetadata) {\n try {\n const instance: any = IOCContainer.get(className);\n if (!instance) {\n continue;\n }\n\n // 查找所有调度方法的元数据\n for (const [key, value] of Object.entries(metadata)) {\n if (key.startsWith('SCHEDULED')) {\n const scheduleData = value as {\n method: string;\n cron: string;\n timezone?: string;\n };\n\n const targetMethod = instance[scheduleData.method];\n if (!Helper.isFunction(targetMethod)) {\n logger.Warn(`Schedule injection skipped: method ${scheduleData.method} is not a function in ${className}`);\n continue;\n }\n\n const taskName = `${className}_${scheduleData.method}`;\n const tz = getEffectiveTimezone(options, scheduleData.timezone);\n\n new CronJob(\n scheduleData.cron,\n () => {\n logger.Debug(`The schedule job ${taskName} started.`);\n Promise.resolve(targetMethod.call(instance))\n .then(() => {\n logger.Debug(`The schedule job ${taskName} completed.`);\n })\n .catch((error) => {\n logger.Error(`The schedule job ${taskName} failed:`, error);\n });\n },\n null, // onComplete\n true, // start\n tz // timeZone\n );\n\n scheduledCount++;\n logger.Debug(`Schedule job ${taskName} registered with cron: ${scheduleData.cron}`);\n }\n }\n } catch (error) {\n logger.Error(`Failed to process class ${className}:`, error);\n }\n }\n\n logger.Info(`Batch schedule injection completed. ${scheduledCount} jobs registered.`);\n }\n } catch (error) {\n logger.Error('Failed to inject schedules:', error);\n }\n}\n","/**\n * @ author: richen\n * @ copyright: Copyright (c) - <richenlin(at)gmail.com>\n * @ license: MIT\n * @ version: 2020-07-06 10:30:11\n */\n\nimport { Koatty } from \"koatty_core\";\nimport { RedLock } from \"./decorator/redlock\";\nimport { Scheduled } from \"./decorator/scheduled\";\nimport { initRedLock } from \"./process/locker\";\nimport { initSchedule } from \"./process/schedule\";\nimport { ScheduledOptions } from \"./config/config\";\nimport { RedisMode } from \"./locker/interface\";\n\n// Export the decorators\nexport { RedLock, Scheduled };\n\n// Export types and interfaces\nexport { RedLocker } from \"./locker/redlock\";\nexport type { RedLockOptions } from \"./locker/redlock\";\nexport { RedisMode } from \"./locker/interface\";\nexport type { \n IDistributedLock, \n IRedisClient, \n ILockOptions,\n RedisConfig,\n RedisStandaloneConfig,\n RedisSentinelConfig,\n RedisClusterConfig\n} from \"./locker/interface\";\nexport { RedisFactory, RedisClientAdapter } from \"./locker/redis-factory\";\n\n/**\n * @deprecated Use RedLock instead. This will be removed in v3.0.0\n */\nexport const SchedulerLock = RedLock;\n\n/** \n * defaultOptions\n */\n\nconst defaultOptions: ScheduledOptions = {\n timezone: \"Asia/Beijing\",\n lockTimeOut: 10000,\n clockDriftFactor: 0.01,\n maxRetries: 3,\n retryDelayMs: 200,\n redisConfig: {\n mode: RedisMode.STANDALONE,\n host: \"localhost\",\n port: 6379,\n password: \"\",\n db: 0,\n keyPrefix: \"redlock:\"\n }\n}\n\n/**\n * @param options - The options for the scheduled job\n * @param app - The Koatty application instance\n */\nexport async function KoattyScheduled(options: ScheduledOptions, app: Koatty) {\n options = { ...defaultOptions, ...options };\n \n app.once(\"appReady\", async function () {\n // 初始化RedLock\n await initRedLock(options, app);\n // 初始化调度任务系统\n await initSchedule(options, app);\n });\n}"]}
1
+ {"version":3,"sources":["../src/config/config.ts","../src/locker/interface.ts","../src/locker/redis-factory.ts","../src/locker/redlock.ts","../src/utils/lib.ts","../src/decorator/redlock.ts","../src/process/locker.ts","../src/decorator/scheduled.ts","../src/process/schedule.ts","../src/index.ts"],"names":["validateCronExpression","cron","Error","cronParts","trim","split","length","hasSecs","offset","seconds","minutes","hours","dayOfMonth","month","dayOfWeek","validateCronField","field","min","max","fieldName","fieldNameCN","allowedStrings","some","str","toUpperCase","includes","range","step","stepValue","parseInt","isNaN","start","end","startValue","endValue","values","value","numValue","validateRedLockMethodOptions","options","lockTimeOut","undefined","clockDriftFactor","maxRetries","retryDelayMs","validateRedLockOptions","retryCount","retryDelay","retryJitter","setGlobalScheduledOptions","globalScheduledOptions","getGlobalScheduledOptions","getEffectiveTimezone","userTimezone","timezone","getEffectiveRedLockOptions","methodOptions","globalOptions","COMPONENT_SCHEDULED","COMPONENT_REDLOCK","DecoratorType","RedisMode","RedisClientAdapter","RedisFactory","client","status","call","command","args","set","key","mode","duration","get","del","keys","exists","eval","script","numKeys","quit","disconnect","getClient","createClient","config","STANDALONE","logger","Debug","createStandaloneClient","SENTINEL","createSentinelClient","CLUSTER","createClusterClient","host","port","password","db","keyPrefix","connectTimeout","commandTimeout","maxRetriesPerRequest","retryStrategy","times","delay","Math","reconnectOnError","err","Warn","message","Redis","on","Info","name","sentinels","sentinelPassword","nodes","clusterOptions","redisOptions","clusterRetryStrategy","cluster","Cluster","address","validateConfig","validateStandaloneConfig","validateSentinelConfig","validateClusterConfig","defaultRedLockConfig","defaultRedlockSettings","RedLocker","redisConfig","driftFactor","automaticExtensionThreshold","instance","instanceLock","redlock","redisClient","isInitialized","initializationPromise","registerInContainer","RedLockerClass","IOCContainer","saveClass","setExistingInstance","_error","getInstance","containerInstance","resetInstance","close","catch","initialize","performInitialization","error","existingRedis","underlyingClient","userSettings","redlockSettings","Redlock","acquire","resources","ttl","Array","isArray","lockTtl","prefixedResources","map","resource","join","lock","release","extend","extendedLock","isReady","getConfig","updateConfig","getContainerInfo","registered","identifier","healthCheck","redisStatus","details","initialized","redisMode","redlockReady","containerRegistered","timeoutPromise","ms","timeoutId","promise","Promise","resolve","reject","setTimeout","cancel","clearTimeout","wrappedPromise","fn","result","initRedLock","app","Helper","isFunction","once","isEmpty","redLocker","redLockerDescriptor","descriptor","method","configurable","enumerable","valueFunction","self","initialLock","lockTime","timeout","props","currentLock","remainingTime","maxExtensions","extensionCount","timeoutHandler","race","apply","extendError","releaseError","writable","lockOptions","generateLockName","configName","methodName","target","targetObj","getIdentifier","targetWithConstructor","className","RedLock","lockName","createDecorator","context","addInitializer","targetClass","componentType","getType","originalMethod","Lock","resolvedLockName","Object","getPrototypeOf","finalLockName","enhancedDescriptor","Scheduled","attachClassMetadata","SCHEDULED","initSchedule","injectSchedule","totalScheduled","componentList","listClass","component","classMetadata","getClassMetadata","id","scheduleData","targetMethod","taskName","tz","CronJob","then","SchedulerLock","defaultOptions","KoattyScheduled"],"mappings":"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","file":"index.js","sourcesContent":["/*\n * @Description: Configuration management for koatty_schedule\n * @Usage: \n * @Author: richen\n * @Date: 2024-01-17 15:30:00\n * @LastEditTime: 2024-01-17 16:30:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport { RedLockOptions } from \"../locker/redlock\";\n\nexport const COMPONENT_SCHEDULED = 'COMPONENT_SCHEDULED';\nexport const COMPONENT_REDLOCK = 'COMPONENT_REDLOCK';\n\n/**\n * Scheduled global options interface\n */\nexport interface ScheduledOptions extends RedLockOptions {\n timezone?: string;\n}\n\n/**\n * RedLock method-level options (excluding Redis connection config)\n */\nexport interface RedLockMethodOptions {\n lockTimeOut?: number; // Lock timeout in milliseconds\n clockDriftFactor?: number; // Clock drift factor for lock timeout calculation\n maxRetries?: number; // Maximum number of retry attempts\n retryDelayMs?: number; // Delay between retry attempts in milliseconds\n}\n\n/**\n * RedLock decorator configuration \n */\nexport interface RedLockConfig {\n name?: string;\n options?: RedLockOptions;\n}\n\n/**\n * Decorator types supported by the system\n */\nexport enum DecoratorType {\n SCHEDULED = 'SCHEDULED',\n REDLOCK = 'REDLOCK'\n}\n\n/**\n * Validate cron expression format (supports both 5-part and 6-part formats)\n * \n * 6-part format: second minute hour day month weekday\n * 5-part format: minute hour day month weekday\n * \n * @param cron - Cron expression to validate\n * @throws {Error} When cron expression is invalid\n */\nexport function validateCronExpression(cron: string): void {\n if (!cron || typeof cron !== 'string') {\n throw new Error('Cron expression must be a non-empty string');\n }\n\n const cronParts = cron.trim().split(/\\s+/);\n \n // Cron expressions should have 5 or 6 parts (with or without seconds)\n if (cronParts.length < 5 || cronParts.length > 6) {\n throw new Error(`Invalid cron format. Expected 5 or 6 parts, got ${cronParts.length}`);\n }\n\n // Determine if this is a 6-part (with seconds) or 5-part expression\n const hasSecs = cronParts.length === 6;\n const offset = hasSecs ? 0 : -1;\n\n // Extract parts with proper indexing\n const seconds = hasSecs ? cronParts[0] : null;\n const minutes = cronParts[offset + 1];\n const hours = cronParts[offset + 2];\n const dayOfMonth = cronParts[offset + 3];\n const month = cronParts[offset + 4];\n const dayOfWeek = cronParts[offset + 5];\n\n // Validate seconds (0-59) if present\n if (seconds !== null) {\n validateCronField(seconds, 0, 59, 'seconds', '秒');\n }\n\n // Validate minutes (0-59)\n validateCronField(minutes, 0, 59, 'minutes', '分钟');\n\n // Validate hours (0-23)\n validateCronField(hours, 0, 23, 'hours', '小时');\n\n // Validate day of month (1-31)\n validateCronField(dayOfMonth, 1, 31, 'day of month', '日期');\n\n // Validate month (1-12 or JAN-DEC)\n validateCronField(month, 1, 12, 'month', '月份', ['JAN', 'FEB', 'MAR', 'APR', 'MAY', 'JUN', 'JUL', 'AUG', 'SEP', 'OCT', 'NOV', 'DEC']);\n\n // Validate day of week (0-7 or SUN-SAT, where 0 and 7 both represent Sunday)\n validateCronField(dayOfWeek, 0, 7, 'day of week', '星期', ['SUN', 'MON', 'TUE', 'WED', 'THU', 'FRI', 'SAT']);\n}\n\n/**\n * Validate individual cron field\n * @param field - Field value to validate\n * @param min - Minimum allowed value\n * @param max - Maximum allowed value\n * @param fieldName - English field name for error messages\n * @param fieldNameCN - Chinese field name for error messages\n * @param allowedStrings - Optional array of allowed string values (e.g., month/weekday names)\n */\nfunction validateCronField(\n field: string,\n min: number,\n max: number,\n fieldName: string,\n fieldNameCN: string,\n allowedStrings?: string[]\n): void {\n // Allow wildcard\n if (field === '*') {\n return;\n }\n\n // Allow question mark (for day of month / day of week)\n if (field === '?') {\n return;\n }\n\n // Check for allowed string values (month/weekday names)\n if (allowedStrings && allowedStrings.some(str => field.toUpperCase().includes(str))) {\n return;\n }\n\n // Step values (e.g., */5, 0-30/5)\n if (field.includes('/')) {\n const [range, step] = field.split('/');\n const stepValue = parseInt(step);\n \n if (isNaN(stepValue) || stepValue <= 0) {\n throw new Error(`Invalid step value for ${fieldName}: ${step}`);\n }\n \n if (range !== '*') {\n validateCronField(range, min, max, fieldName, fieldNameCN, allowedStrings);\n }\n return;\n }\n\n // Range values (e.g., 1-5)\n if (field.includes('-')) {\n const [start, end] = field.split('-');\n const startValue = parseInt(start);\n const endValue = parseInt(end);\n \n if (isNaN(startValue) || startValue < min || startValue > max) {\n throw new Error(`Invalid range start for ${fieldName}: ${start}, must be between ${min}-${max}`);\n }\n \n if (isNaN(endValue) || endValue < min || endValue > max) {\n throw new Error(`Invalid range end for ${fieldName}: ${end}, must be between ${min}-${max}`);\n }\n \n if (startValue > endValue) {\n throw new Error(`Invalid range for ${fieldName}: ${start}-${end}, start cannot be greater than end`);\n }\n return;\n }\n\n // List values (e.g., 1,3,5)\n if (field.includes(',')) {\n const values = field.split(',');\n for (const value of values) {\n validateCronField(value.trim(), min, max, fieldName, fieldNameCN, allowedStrings);\n }\n return;\n }\n\n // Single numeric value\n const numValue = parseInt(field);\n if (isNaN(numValue) || numValue < min || numValue > max) {\n throw new Error(`Invalid ${fieldName} value: ${field}, must be between ${min}-${max}`);\n }\n}\n\n/**\n * Validate RedLock method-level options\n * @param options - RedLock method options to validate\n * @throws {Error} When options are invalid\n */\nexport function validateRedLockMethodOptions(options: RedLockMethodOptions): void {\n if (!options || typeof options !== 'object') {\n throw new Error('RedLock method options must be an object');\n }\n\n if (options.lockTimeOut !== undefined) {\n if (typeof options.lockTimeOut !== 'number' || options.lockTimeOut <= 0) {\n throw new Error('lockTimeOut must be a positive number');\n }\n }\n\n if (options.clockDriftFactor !== undefined) {\n if (typeof options.clockDriftFactor !== 'number' || options.clockDriftFactor < 0 || options.clockDriftFactor > 1) {\n throw new Error('clockDriftFactor must be a number between 0 and 1');\n }\n }\n\n if (options.maxRetries !== undefined) {\n if (typeof options.maxRetries !== 'number' || options.maxRetries < 0) {\n throw new Error('maxRetries must be a non-negative number');\n }\n }\n\n if (options.retryDelayMs !== undefined) {\n if (typeof options.retryDelayMs !== 'number' || options.retryDelayMs < 0) {\n throw new Error('retryDelayMs must be a non-negative number');\n }\n }\n}\n\n/**\n * Validate RedLock options\n * @param options - RedLock options to validate\n * @throws {Error} When options are invalid\n */\nexport function validateRedLockOptions(options: RedLockOptions): void {\n if (!options || typeof options !== 'object') {\n throw new Error('RedLock options must be an object');\n }\n\n if (options.lockTimeOut !== undefined) {\n if (typeof options.lockTimeOut !== 'number' || options.lockTimeOut <= 0) {\n throw new Error('lockTimeOut must be a positive number');\n }\n }\n\n if (options.retryCount !== undefined) {\n if (typeof options.retryCount !== 'number' || options.retryCount < 0) {\n throw new Error('retryCount must be a non-negative number');\n }\n }\n\n if (options.retryDelay !== undefined) {\n if (typeof options.retryDelay !== 'number' || options.retryDelay < 0) {\n throw new Error('retryDelay must be a non-negative number');\n }\n }\n\n if (options.retryJitter !== undefined) {\n if (typeof options.retryJitter !== 'number' || options.retryJitter < 0) {\n throw new Error('retryJitter must be a non-negative number');\n }\n }\n}\n\n//==================== Global Configuration Management ====================\n\n/**\n * Global configuration storage\n */\nlet globalScheduledOptions: ScheduledOptions = {};\n\n/**\n * Set global scheduled options\n * @param options - Global scheduled options\n */\nexport function setGlobalScheduledOptions(options: ScheduledOptions): void {\n globalScheduledOptions = { ...options };\n}\n\n/**\n * Get global scheduled options\n * @returns Global scheduled options\n */\nexport function getGlobalScheduledOptions(): ScheduledOptions {\n return globalScheduledOptions;\n}\n\n/**\n * Get effective timezone with priority: user specified > global > default\n * @param userTimezone - User specified timezone\n * @returns Effective timezone\n */\nexport function getEffectiveTimezone(options: ScheduledOptions, userTimezone?: string): string {\n return userTimezone || options.timezone || 'Asia/Beijing';\n}\n\n\n\n/**\n * Get effective RedLock method options with priority: method options > global options > defaults\n * @param methodOptions - Method-level RedLock options\n * @returns Effective RedLock method options with all defaults applied\n */\nexport function getEffectiveRedLockOptions(methodOptions?: RedLockMethodOptions): RedLockMethodOptions {\n const globalOptions = getGlobalScheduledOptions();\n \n return {\n lockTimeOut: methodOptions?.lockTimeOut || globalOptions.lockTimeOut || 10000,\n clockDriftFactor: methodOptions?.clockDriftFactor || globalOptions.clockDriftFactor || 0.01,\n maxRetries: methodOptions?.maxRetries || globalOptions.maxRetries || 3,\n retryDelayMs: methodOptions?.retryDelayMs || globalOptions.retryDelayMs || 200\n };\n} ","/*\n * @Description: Abstract interfaces for Redis client and distributed lock\n * @Usage: \n * @Author: richen\n * @Date: 2025-10-30 12:00:00\n * @LastEditTime: 2025-10-30 12:00:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport type { Lock, Settings } from \"@sesamecare-oss/redlock\";\n\n/**\n * Redis connection mode\n */\nexport enum RedisMode {\n STANDALONE = 'standalone', // 单机模式\n SENTINEL = 'sentinel', // 哨兵模式\n CLUSTER = 'cluster' // 集群模式\n}\n\n/**\n * Base Redis configuration\n */\nexport interface BaseRedisConfig {\n mode?: RedisMode;\n host?: string;\n port?: number;\n password?: string;\n db?: number;\n keyPrefix?: string;\n connectTimeout?: number;\n commandTimeout?: number;\n maxRetriesPerRequest?: number;\n}\n\n/**\n * Sentinel configuration\n */\nexport interface RedisSentinelConfig extends BaseRedisConfig {\n mode: RedisMode.SENTINEL;\n sentinels: Array<{ host: string; port: number }>;\n name: string; // sentinel master name\n sentinelPassword?: string;\n}\n\n/**\n * Cluster configuration\n */\nexport interface RedisClusterConfig extends BaseRedisConfig {\n mode: RedisMode.CLUSTER;\n nodes: Array<{ host: string; port: number }>;\n redisOptions?: {\n password?: string;\n db?: number;\n };\n}\n\n/**\n * Standalone configuration\n */\nexport interface RedisStandaloneConfig extends BaseRedisConfig {\n mode?: RedisMode.STANDALONE;\n host: string;\n port: number;\n}\n\n/**\n * Union type for all Redis configurations\n */\nexport type RedisConfig = RedisStandaloneConfig | RedisSentinelConfig | RedisClusterConfig;\n\n/**\n * Abstract Redis client interface\n * Provides unified interface for different Redis implementations\n */\nexport interface IRedisClient {\n /**\n * Get connection status\n */\n readonly status: string;\n\n /**\n * Execute Redis command\n * @param command - Command name\n * @param args - Command arguments\n */\n call(command: string, ...args: any[]): Promise<any>;\n\n /**\n * Set a key-value pair\n * @param key - Key name\n * @param value - Value\n * @param mode - Optional mode (e.g., 'EX' for expiration)\n * @param duration - Optional duration in seconds\n */\n set(key: string, value: string | Buffer, mode?: string, duration?: number): Promise<'OK' | null>;\n\n /**\n * Get value by key\n * @param key - Key name\n */\n get(key: string): Promise<string | null>;\n\n /**\n * Delete one or more keys\n * @param keys - Key names\n */\n del(...keys: string[]): Promise<number>;\n\n /**\n * Check if key exists\n * @param key - Key name\n */\n exists(key: string): Promise<number>;\n\n /**\n * Evaluate Lua script\n * @param script - Lua script\n * @param numKeys - Number of keys\n * @param args - Script arguments\n */\n eval(script: string, numKeys: number, ...args: any[]): Promise<any>;\n\n /**\n * Close the connection\n */\n quit(): Promise<'OK'>;\n\n /**\n * Disconnect immediately\n */\n disconnect(): void;\n}\n\n/**\n * Abstract distributed lock interface\n * Allows for different lock implementations (RedLock, Zookeeper, etc.)\n */\nexport interface IDistributedLock {\n /**\n * Initialize the lock system\n */\n initialize(): Promise<void>;\n\n /**\n * Acquire a distributed lock\n * @param resources - Resource identifiers\n * @param ttl - Time to live in milliseconds\n */\n acquire(resources: string[], ttl: number): Promise<Lock>;\n\n /**\n * Release a lock\n * @param lock - Lock instance\n */\n release(lock: Lock): Promise<void>;\n\n /**\n * Extend lock TTL\n * @param lock - Lock instance\n * @param ttl - New TTL in milliseconds\n */\n extend(lock: Lock, ttl: number): Promise<Lock>;\n\n /**\n * Check if the lock system is ready\n */\n isReady(): boolean;\n\n /**\n * Get current configuration\n */\n getConfig(): any;\n\n /**\n * Close and cleanup\n */\n close(): Promise<void>;\n\n /**\n * Health check\n */\n healthCheck(): Promise<{ status: 'healthy' | 'unhealthy'; details: Record<string, any> }>;\n}\n\n/**\n * Lock configuration options\n */\nexport interface ILockOptions extends Partial<Settings> {\n lockTimeOut?: number;\n clockDriftFactor?: number;\n maxRetries?: number;\n retryDelayMs?: number;\n redisConfig?: RedisConfig;\n}\n\n","/*\n * @Description: Redis client factory supporting multiple modes\n * @Usage: \n * @Author: richen\n * @Date: 2025-10-30 12:00:00\n * @LastEditTime: 2025-10-30 12:00:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport Redis, { Cluster, RedisOptions, ClusterOptions } from \"ioredis\";\nimport { DefaultLogger as logger } from \"koatty_logger\";\nimport {\n IRedisClient,\n RedisConfig,\n RedisMode,\n RedisStandaloneConfig,\n RedisSentinelConfig,\n RedisClusterConfig\n} from \"./interface\";\n\n/**\n * Redis client wrapper that implements IRedisClient interface\n * Wraps ioredis client to provide unified interface\n */\nclass RedisClientAdapter implements IRedisClient {\n constructor(private client: Redis | Cluster) {}\n\n get status(): string {\n return this.client.status;\n }\n\n async call(command: string, ...args: any[]): Promise<any> {\n return this.client.call(command, ...args);\n }\n\n async set(key: string, value: string | Buffer, mode?: string, duration?: number): Promise<'OK' | null> {\n if (mode && duration) {\n // Use type assertion for mode parameter due to ioredis strict typing\n return this.client.set(key, value, mode as any, duration) as Promise<'OK' | null>;\n }\n return this.client.set(key, value);\n }\n\n async get(key: string): Promise<string | null> {\n return this.client.get(key);\n }\n\n async del(...keys: string[]): Promise<number> {\n return this.client.del(...keys);\n }\n\n async exists(key: string): Promise<number> {\n return this.client.exists(key);\n }\n\n async eval(script: string, numKeys: number, ...args: any[]): Promise<any> {\n return this.client.eval(script, numKeys, ...args);\n }\n\n async quit(): Promise<'OK'> {\n return this.client.quit();\n }\n\n disconnect(): void {\n this.client.disconnect();\n }\n\n /**\n * Get underlying Redis/Cluster instance\n * Used for RedLock initialization\n */\n getClient(): Redis | Cluster {\n return this.client;\n }\n}\n\n/**\n * Redis client factory\n * Creates appropriate Redis client based on configuration\n */\nexport class RedisFactory {\n /**\n * Create Redis client based on configuration mode\n * @param config - Redis configuration\n * @returns Redis client adapter\n */\n static createClient(config: RedisConfig): RedisClientAdapter {\n const mode = config.mode || RedisMode.STANDALONE;\n\n logger.Debug(`Creating Redis client in ${mode} mode`);\n\n switch (mode) {\n case RedisMode.STANDALONE:\n return this.createStandaloneClient(config as RedisStandaloneConfig);\n \n case RedisMode.SENTINEL:\n return this.createSentinelClient(config as RedisSentinelConfig);\n \n case RedisMode.CLUSTER:\n return this.createClusterClient(config as RedisClusterConfig);\n \n default:\n throw new Error(`Unsupported Redis mode: ${mode}`);\n }\n }\n\n /**\n * Create standalone Redis client\n * @param config - Standalone configuration\n */\n private static createStandaloneClient(config: RedisStandaloneConfig): RedisClientAdapter {\n logger.Debug(`Creating standalone Redis client: ${config.host}:${config.port}`);\n\n const options: RedisOptions = {\n host: config.host,\n port: config.port,\n password: config.password || undefined,\n db: config.db || 0,\n keyPrefix: config.keyPrefix || '',\n connectTimeout: config.connectTimeout || 10000,\n commandTimeout: config.commandTimeout || 5000,\n maxRetriesPerRequest: config.maxRetriesPerRequest || 3,\n retryStrategy: (times: number) => {\n const delay = Math.min(times * 50, 2000);\n logger.Debug(`Redis reconnecting, attempt ${times}, delay ${delay}ms`);\n return delay;\n },\n reconnectOnError: (err: Error) => {\n logger.Warn('Redis connection error, attempting reconnect:', err.message);\n return true;\n }\n };\n\n const client = new Redis(options);\n\n client.on('connect', () => {\n logger.Info('Redis standalone client connected successfully');\n });\n\n client.on('error', (err: Error) => {\n logger.Error('Redis standalone client error:', err);\n });\n\n return new RedisClientAdapter(client);\n }\n\n /**\n * Create sentinel Redis client\n * @param config - Sentinel configuration\n */\n private static createSentinelClient(config: RedisSentinelConfig): RedisClientAdapter {\n logger.Debug(`Creating sentinel Redis client for master: ${config.name}`);\n\n const options: RedisOptions = {\n sentinels: config.sentinels,\n name: config.name,\n password: config.password || undefined,\n sentinelPassword: config.sentinelPassword || undefined,\n db: config.db || 0,\n keyPrefix: config.keyPrefix || '',\n connectTimeout: config.connectTimeout || 10000,\n commandTimeout: config.commandTimeout || 5000,\n maxRetriesPerRequest: config.maxRetriesPerRequest || 3,\n retryStrategy: (times: number) => {\n const delay = Math.min(times * 50, 2000);\n logger.Debug(`Sentinel Redis reconnecting, attempt ${times}, delay ${delay}ms`);\n return delay;\n }\n };\n\n const client = new Redis(options);\n\n client.on('connect', () => {\n logger.Info(`Redis sentinel client connected to master: ${config.name}`);\n });\n\n client.on('error', (err: Error) => {\n logger.Error('Redis sentinel client error:', err);\n });\n\n return new RedisClientAdapter(client);\n }\n\n /**\n * Create cluster Redis client\n * @param config - Cluster configuration\n */\n private static createClusterClient(config: RedisClusterConfig): RedisClientAdapter {\n logger.Debug(`Creating cluster Redis client with ${config.nodes.length} nodes`);\n\n const clusterOptions: ClusterOptions = {\n redisOptions: {\n password: config.redisOptions?.password || config.password || undefined,\n db: config.redisOptions?.db || config.db || 0,\n keyPrefix: config.keyPrefix || '',\n connectTimeout: config.connectTimeout || 10000,\n commandTimeout: config.commandTimeout || 5000,\n maxRetriesPerRequest: config.maxRetriesPerRequest || 3\n },\n clusterRetryStrategy: (times: number) => {\n const delay = Math.min(times * 50, 2000);\n logger.Debug(`Cluster Redis reconnecting, attempt ${times}, delay ${delay}ms`);\n return delay;\n }\n };\n\n const cluster = new Cluster(config.nodes, clusterOptions);\n\n cluster.on('connect', () => {\n logger.Info('Redis cluster client connected successfully');\n });\n\n cluster.on('error', (err: Error) => {\n logger.Error('Redis cluster client error:', err);\n });\n\n cluster.on('node error', (err: Error, address: string) => {\n logger.Error(`Redis cluster node error at ${address}:`, err);\n });\n\n return new RedisClientAdapter(cluster);\n }\n\n /**\n * Validate Redis configuration\n * @param config - Redis configuration to validate\n */\n static validateConfig(config: RedisConfig): void {\n if (!config) {\n throw new Error('Redis configuration cannot be empty');\n }\n\n const mode = config.mode || RedisMode.STANDALONE;\n\n switch (mode) {\n case RedisMode.STANDALONE:\n this.validateStandaloneConfig(config as RedisStandaloneConfig);\n break;\n \n case RedisMode.SENTINEL:\n this.validateSentinelConfig(config as RedisSentinelConfig);\n break;\n \n case RedisMode.CLUSTER:\n this.validateClusterConfig(config as RedisClusterConfig);\n break;\n \n default:\n throw new Error(`Unsupported Redis mode: ${mode}`);\n }\n }\n\n private static validateStandaloneConfig(config: RedisStandaloneConfig): void {\n if (!config.host) {\n throw new Error('Standalone mode requires host configuration');\n }\n if (!config.port) {\n throw new Error('Standalone mode requires port configuration');\n }\n }\n\n private static validateSentinelConfig(config: RedisSentinelConfig): void {\n if (!config.sentinels || config.sentinels.length === 0) {\n throw new Error('Sentinel mode requires at least one sentinel node');\n }\n if (!config.name) {\n throw new Error('Sentinel mode requires master name');\n }\n }\n\n private static validateClusterConfig(config: RedisClusterConfig): void {\n if (!config.nodes || config.nodes.length === 0) {\n throw new Error('Cluster mode requires at least one node');\n }\n }\n}\n\nexport { RedisClientAdapter };\n\n","/*\n * @Description: RedLock utility for distributed locks\n * @Usage: \n * @Author: richen\n * @Date: 2021-11-17 16:18:33\n * @LastEditTime: 2024-01-17 15:00:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport { Redlock, Lock, Settings } from \"@sesamecare-oss/redlock\";\nimport { DefaultLogger as logger } from \"koatty_logger\";\nimport { IOCContainer } from \"koatty_container\";\nimport { IDistributedLock, ILockOptions, RedisConfig, RedisMode } from \"./interface\";\nimport { RedisFactory, RedisClientAdapter } from \"./redis-factory\";\n\n/**\n * Configuration options for RedLock\n * @deprecated Use ILockOptions from interface instead\n */\nexport interface RedLockOptions extends ILockOptions {\n redisConfig?: RedisConfig;\n}\n\n/**\n * Default RedLock configuration\n */\nconst defaultRedLockConfig: RedLockOptions = {\n lockTimeOut: 10000,\n clockDriftFactor: 0.01,\n maxRetries: 3,\n retryDelayMs: 200,\n redisConfig: {\n mode: RedisMode.STANDALONE,\n host: '127.0.0.1',\n port: 6379,\n password: '',\n db: 0,\n keyPrefix: 'redlock:'\n }\n};\n\n/**\n * Default Redlock Settings for @sesamecare-oss/redlock\n */\nconst defaultRedlockSettings: Partial<Settings> = {\n driftFactor: 0.01,\n retryCount: 3,\n retryDelay: 200,\n retryJitter: 200,\n automaticExtensionThreshold: 500\n};\n\n/**\n * RedLock distributed lock manager\n * Integrated with koatty IOC container\n * Implements singleton pattern for safe instance management\n * Implements IDistributedLock interface for abstraction\n */\nexport class RedLocker implements IDistributedLock {\n private static instance: RedLocker | null = null;\n private static readonly instanceLock = Symbol('RedLocker.instanceLock');\n \n private redlock: Redlock | null = null;\n private redisClient: RedisClientAdapter | null = null;\n private config: RedLockOptions;\n private isInitialized = false;\n private initializationPromise: Promise<void> | null = null;\n\n // 私有构造函数防止外部直接实例化\n private constructor(options?: RedLockOptions) {\n this.config = { ...defaultRedLockConfig, ...options };\n // Register this instance in IOC container\n this.registerInContainer();\n }\n\n /**\n * Register RedLocker in IOC container\n * @private\n */\n private registerInContainer(): void {\n try {\n const RedLockerClass = this.constructor as Function;\n IOCContainer.saveClass('COMPONENT', RedLockerClass, 'RedLocker');\n IOCContainer.setExistingInstance(RedLockerClass, this);\n logger.Debug('RedLocker registered in IOC container');\n } catch (_error) {\n logger.Warn('Failed to register RedLocker in IOC container:', _error);\n }\n }\n\n /**\n * Get RedLocker singleton instance with thread-safe initialization\n * @static\n * @param options - RedLock configuration options (only used for first initialization)\n * @returns RedLocker singleton instance\n */\n public static getInstance(options?: RedLockOptions): RedLocker {\n // 双重检查锁定模式确保线程安全\n if (!RedLocker.instance) {\n // 首次创建时使用选项,后续调用忽略选项参数\n if (RedLocker.instance === null) {\n try {\n // 尝试从IOC容器获取已存在的实例\n const containerInstance = IOCContainer.get('RedLocker', 'COMPONENT') as RedLocker;\n if (containerInstance) {\n RedLocker.instance = containerInstance;\n logger.Debug('Retrieved existing RedLocker instance from IOC container');\n } else {\n // 创建新的单例实例\n RedLocker.instance = new RedLocker(options);\n logger.Debug('Created new RedLocker singleton instance');\n }\n } catch {\n // IOC容器不可用时直接创建\n RedLocker.instance = new RedLocker(options);\n logger.Debug('Created new RedLocker instance outside IOC container');\n }\n }\n } else if (options) {\n // 如果实例已存在但传入了新选项,记录警告\n logger.Warn('RedLocker instance already exists, ignoring new options. Use updateConfig() to change configuration.');\n }\n \n return RedLocker.instance;\n }\n\n /**\n * Reset singleton instance (主要用于测试)\n * @static\n */\n public static resetInstance(): void {\n if (RedLocker.instance) {\n RedLocker.instance.close().catch(err => \n logger.Warn('Error while closing RedLocker instance during reset:', err)\n );\n RedLocker.instance = null;\n }\n }\n\n /**\n * Initialize RedLock with Redis connection\n * Uses cached promise to avoid duplicate initialization\n * @private\n */\n public async initialize(): Promise<void> {\n // 如果已经初始化,直接返回\n if (this.isInitialized) {\n return;\n }\n \n // 如果正在初始化,等待现有的初始化完成\n if (this.initializationPromise) {\n return this.initializationPromise;\n }\n \n // 创建初始化Promise并缓存\n this.initializationPromise = this.performInitialization();\n \n try {\n await this.initializationPromise;\n } catch (error) {\n // 初始化失败时完整清理状态,允许重试\n this.initializationPromise = null;\n this.isInitialized = false;\n this.redlock = null;\n // 注意:不清理 redis 连接,因为它可能来自 IOC 容器\n logger.Warn('RedLocker initialization failed, state has been reset for retry');\n throw error;\n }\n }\n \n /**\n * 执行实际的初始化操作\n * @private\n */\n private async performInitialization(): Promise<void> {\n\n try {\n // Validate Redis configuration\n if (this.config.redisConfig) {\n RedisFactory.validateConfig(this.config.redisConfig);\n }\n\n // Try to get Redis instance from IOC container first\n try {\n const existingRedis = IOCContainer.get('Redis', 'COMPONENT');\n // If Redis instance exists in container, wrap it\n if (existingRedis) {\n // Check if it's already a RedisClientAdapter\n if (existingRedis instanceof RedisClientAdapter) {\n this.redisClient = existingRedis;\n } else {\n // Wrap raw Redis/Cluster instance (type assertion needed)\n this.redisClient = new RedisClientAdapter(existingRedis as any);\n }\n logger.Debug('Using Redis instance from IOC container');\n }\n } catch {\n // IOC container doesn't have Redis, create new connection\n }\n\n // Create new Redis connection if not available in container\n if (!this.redisClient && this.config.redisConfig) {\n this.redisClient = RedisFactory.createClient(this.config.redisConfig);\n logger.Debug('Created new Redis connection for RedLocker');\n }\n\n if (!this.redisClient) {\n throw new Error('Failed to initialize Redis connection: no configuration provided');\n }\n\n // Get underlying client for Redlock\n const underlyingClient = this.redisClient.getClient();\n\n // Merge default settings with user configuration\n // Extract Settings properties from config (which extends Partial<Settings>)\n const userSettings: any = this.config;\n const redlockSettings: Partial<Settings> = {\n ...defaultRedlockSettings,\n ...(userSettings.driftFactor !== undefined && { driftFactor: userSettings.driftFactor }),\n ...(userSettings.retryCount !== undefined && { retryCount: userSettings.retryCount }),\n ...(userSettings.retryDelay !== undefined && { retryDelay: userSettings.retryDelay }),\n ...(userSettings.retryJitter !== undefined && { retryJitter: userSettings.retryJitter }),\n ...(userSettings.automaticExtensionThreshold !== undefined && { \n automaticExtensionThreshold: userSettings.automaticExtensionThreshold \n })\n };\n\n // Initialize Redlock with the Redis instance\n this.redlock = new Redlock([underlyingClient], redlockSettings);\n\n // Set up error handlers\n this.redlock.on('clientError', (err: Error) => {\n logger.Error('Redis client error in RedLock:', err);\n });\n\n this.isInitialized = true;\n logger.Info('RedLocker initialized successfully');\n } catch (error) {\n this.isInitialized = false;\n logger.Error('Failed to initialize RedLocker:', error);\n throw new Error(`RedLocker initialization failed: ${error instanceof Error ? error.message : 'Unknown error'}`);\n }\n }\n\n /**\n * Acquire a distributed lock\n * @param resources - Resource identifiers to lock\n * @param ttl - Time to live in milliseconds\n * @returns Promise<Lock>\n */\n async acquire(resources: string[], ttl?: number): Promise<Lock> {\n if (!Array.isArray(resources) || resources.length === 0) {\n throw new Error('Resources array cannot be empty');\n }\n\n const lockTtl = ttl || this.config.lockTimeOut;\n if (lockTtl <= 0) {\n throw new Error('Lock TTL must be positive');\n }\n\n // Ensure RedLocker is initialized\n await this.initialize();\n\n if (!this.redlock) {\n throw new Error('RedLock is not initialized');\n }\n\n try {\n // Add key prefix to resources\n const prefixedResources = resources.map(resource => \n `${this.config.redisConfig.keyPrefix}${resource}`\n );\n\n logger.Debug(`Acquiring lock for resources: ${prefixedResources.join(', ')} with TTL: ${lockTtl}ms`);\n \n const lock = await this.redlock.acquire(prefixedResources, lockTtl);\n logger.Debug(`Lock acquired successfully for resources: ${prefixedResources.join(', ')}`);\n \n return lock;\n } catch (error) {\n logger.Error(`Failed to acquire lock for resources: ${resources.join(', ')}`, error);\n // 保留原始错误信息,避免过度包装\n if (error instanceof Error) {\n error.message = `Lock acquisition failed: ${error.message}`;\n throw error;\n }\n throw new Error(`Lock acquisition failed: Unknown error`);\n }\n }\n\n /**\n * Release a lock\n * @param lock - Lock instance to release\n */\n async release(lock: Lock): Promise<void> {\n if (!lock) {\n throw new Error('Lock instance is required');\n }\n\n try {\n await lock.release();\n logger.Debug('Lock released successfully');\n } catch (error) {\n logger.Error('Failed to release lock:', error);\n // 保留原始错误信息\n if (error instanceof Error) {\n error.message = `Lock release failed: ${error.message}`;\n throw error;\n }\n throw new Error(`Lock release failed: Unknown error`);\n }\n }\n\n /**\n * Extend a lock's TTL\n * @param lock - Lock instance to extend\n * @param ttl - New TTL in milliseconds\n * @returns Extended lock\n */\n async extend(lock: Lock, ttl: number): Promise<Lock> {\n if (!lock) {\n throw new Error('Lock instance is required');\n }\n\n if (ttl <= 0) {\n throw new Error('TTL must be positive');\n }\n\n try {\n const extendedLock = await lock.extend(ttl);\n logger.Debug(`Lock extended successfully with TTL: ${ttl}ms`);\n return extendedLock;\n } catch (error) {\n logger.Error('Failed to extend lock:', error);\n throw new Error(`Lock extension failed: ${error instanceof Error ? error.message : 'Unknown error'}`);\n }\n }\n\n /**\n * Check if RedLocker is initialized\n * @returns true if initialized, false otherwise\n */\n isReady(): boolean {\n return this.isInitialized && !!this.redlock && !!this.redisClient;\n }\n\n /**\n * Get current configuration\n * @returns Current RedLock configuration\n */\n getConfig(): RedLockOptions {\n return { ...this.config };\n }\n\n /**\n * Update configuration (requires reinitialization)\n * @param options - New RedLock options\n */\n updateConfig(options?: Partial<RedLockOptions>): void {\n if (options) {\n this.config = { ...this.config, ...options };\n }\n\n // 清理初始化状态,强制重新初始化\n this.isInitialized = false;\n this.initializationPromise = null;\n this.redlock = null;\n \n logger.Debug('RedLocker configuration updated, will reinitialize on next use');\n }\n\n /**\n * Close Redis connection and cleanup\n */\n async close(): Promise<void> {\n try {\n if (this.redisClient && this.redisClient.status === 'ready') {\n await this.redisClient.quit();\n logger.Debug('Redis connection closed');\n }\n \n this.redisClient = null;\n this.redlock = null;\n this.isInitialized = false;\n } catch (error) {\n logger.Error('Error closing RedLocker:', error);\n }\n }\n\n /**\n * Get container registration status\n * @returns Registration information\n */\n getContainerInfo(): { registered: boolean; identifier: string } {\n try {\n const instance = IOCContainer.get('RedLocker', 'COMPONENT');\n return {\n registered: !!instance,\n identifier: 'RedLocker'\n };\n } catch {\n return {\n registered: false,\n identifier: 'RedLocker'\n };\n }\n }\n\n /**\n * Health check for RedLocker\n * @returns Health status\n */\n async healthCheck(): Promise<{ status: 'healthy' | 'unhealthy'; details: Record<string, any> }> {\n try {\n await this.initialize();\n \n const redisStatus = this.redisClient?.status || 'unknown';\n const isReady = this.isReady();\n \n return {\n status: isReady ? 'healthy' : 'unhealthy',\n details: {\n initialized: this.isInitialized,\n redisStatus,\n redisMode: this.config.redisConfig?.mode || 'unknown',\n redlockReady: !!this.redlock,\n containerRegistered: this.getContainerInfo().registered\n }\n };\n } catch (error) {\n return {\n status: 'unhealthy',\n details: {\n error: error instanceof Error ? error.message : 'Unknown error',\n initialized: this.isInitialized\n }\n };\n }\n }\n}","/*\n * @Description: \n * @Usage: \n * @Author: richen\n * @Date: 2024-01-16 19:53:14\n * @LastEditTime: 2024-11-07 16:47:58\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\n/**\n * 返回一个可取消的 Promise,在指定时间后 reject\n * @param ms 超时时间(毫秒)\n * @returns 带有 cancel 方法的 Promise\n */\nexport interface CancelablePromise<T> extends Promise<T> {\n cancel: () => void;\n}\n\nexport function timeoutPromise(ms: number): CancelablePromise<never> {\n let timeoutId: NodeJS.Timeout | null = null;\n \n const promise = new Promise<never>((resolve, reject) => {\n timeoutId = setTimeout(() => {\n timeoutId = null;\n reject(new Error('TIME_OUT_ERROR'));\n }, ms);\n }) as CancelablePromise<never>;\n\n // 添加取消方法,防止内存泄漏\n promise.cancel = () => {\n if (timeoutId !== null) {\n clearTimeout(timeoutId);\n timeoutId = null;\n }\n };\n\n return promise;\n}\n/**\n * @description: 使用 Promise.resolve 包装不确定的函数,并捕获错误\n * @param {Function} fn\n * @param {any} args\n * @return {*}\n */\nexport function wrappedPromise(fn: Function, args: any[]) {\n return new Promise((resolve, reject) => {\n try {\n const result = fn(...args);\n resolve(result);\n } catch (error) {\n reject(error);\n }\n });\n}\n","/*\n * @Description: \n * @Usage: \n * @Author: richen\n * @Date: 2025-06-09 16:00:00\n * @LastEditTime: 2025-06-09 16:00:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport { IOCContainer } from \"koatty_container\";\nimport { RedLockMethodOptions, validateRedLockMethodOptions } from \"../config/config\";\nimport { redLockerDescriptor, generateLockName } from \"../process/locker\";\n\n/**\n * Redis-based distributed lock decorator\n *\n * @export\n * @param {string} [name] - The locker name. If name is duplicated, lock sharing contention will result.\n * If not provided, a unique name will be auto-generated using method name + random suffix.\n * IMPORTANT: Auto-generated names are unique per method deployment and not predictable.\n * @param {RedLockMethodOptions} [options] - Lock configuration options for this method\n * \n * @returns {MethodDecorator}\n * @throws {Error} When decorator is used on wrong class type or invalid configuration\n * \n * @example\n * ```typescript\n * class UserService {\n * @RedLock('user_update_lock', { lockTimeOut: 5000, maxRetries: 2 })\n * async updateUser(id: string, data: any) {\n * // This method will be protected by a distributed lock with predictable name\n * }\n * \n * @RedLock() // Auto-generated unique name like \"deleteUser_abc123_xyz789\"\n * async deleteUser(id: string) {\n * // This method will be protected by a distributed lock with auto-generated unique name\n * }\n * }\n * ```\n */\nexport function RedLock(lockName?: string, options?: RedLockMethodOptions) {\n return IOCContainer.createDecorator(({ target, methodName, descriptor, method, context }) => {\n if (context) {\n // TC39 path\n if (!methodName || typeof methodName !== 'string') {\n throw Error(\"Method name is required for @RedLock decorator\");\n }\n\n if (options) {\n validateRedLockMethodOptions(options);\n }\n\n context.addInitializer?.(function (this: any) {\n const targetClass = this.constructor;\n const componentType = IOCContainer.getType(targetClass);\n if (componentType !== \"SERVICE\" && componentType !== \"COMPONENT\") {\n throw Error(\"@RedLock decorator can only be used on SERVICE or COMPONENT classes.\");\n }\n IOCContainer.saveClass(\"COMPONENT\", targetClass, targetClass.name);\n });\n\n const originalMethod = method!;\n return async function (this: any, ...props: any[]): Promise<unknown> {\n try {\n const { RedLocker } = await import(\"../locker/redlock\");\n const { getEffectiveRedLockOptions } = await import(\"../config/config\");\n const { timeoutPromise } = await import(\"../utils/lib\");\n const { Lock } = await import(\"@sesamecare-oss/redlock\");\n\n const resolvedLockName = lockName || generateLockName(lockName, methodName, Object.getPrototypeOf(this));\n\n const redlock = RedLocker.getInstance();\n const lockOptions = getEffectiveRedLockOptions(options);\n const lockTime = lockOptions.lockTimeOut || 10000;\n if (lockTime <= 200) {\n throw new Error(\"Lock timeout must be greater than 200ms to allow for proper execution\");\n }\n\n const lock = await redlock.acquire([methodName, resolvedLockName], lockTime);\n const timeout = lockTime - 200;\n\n try {\n const result = await Promise.race([\n originalMethod.apply(this, props),\n timeoutPromise(timeout)\n ]);\n return result;\n } catch (error) {\n throw error;\n } finally {\n try {\n await lock.release();\n } catch (releaseError) {\n // Ignore release errors\n }\n }\n } catch (error) {\n throw error;\n }\n };\n } else {\n // Legacy path\n // 验证装饰器使用的类型(从原型对象获取类构造函数)\n const targetClass = (target as any).constructor;\n const componentType = IOCContainer.getType(targetClass);\n if (componentType !== \"SERVICE\" && componentType !== \"COMPONENT\") {\n throw Error(\"@RedLock decorator can only be used on SERVICE or COMPONENT classes.\");\n }\n\n // 验证方法名\n if (!methodName || typeof methodName !== 'string') {\n throw Error(\"Method name is required for @RedLock decorator\");\n }\n\n // 验证方法描述符\n if (!descriptor || typeof descriptor.value !== 'function') {\n throw Error(\"@RedLock decorator can only be applied to methods\");\n }\n\n // 生成锁名称:用户指定的 > 基于类名和方法名生成\n const finalLockName = lockName || generateLockName(lockName, methodName, target);\n\n // 验证选项\n if (options) {\n validateRedLockMethodOptions(options);\n }\n\n // 保存类到IOC容器\n IOCContainer.saveClass(\"COMPONENT\", targetClass, targetClass.name);\n\n try {\n // 直接在装饰器中包装方法,而不是延迟处理\n const enhancedDescriptor = redLockerDescriptor(\n descriptor,\n finalLockName,\n methodName,\n options\n );\n\n return enhancedDescriptor;\n } catch (error) {\n throw new Error(`Failed to apply RedLock to ${methodName}: ${(error as Error).message}`);\n }\n }\n }, 'method');\n}","/*\n * @Description: Decorator preprocessing mechanism for koatty_schedule\n * @Usage: \n * @Author: richen\n * @Date: 2024-01-17 16:00:00\n * @LastEditTime: 2024-01-17 16:00:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport { IOCContainer } from \"koatty_container\";\nimport { RedLocker, RedLockOptions } from \"../locker/redlock\";\nimport { Helper } from \"koatty_lib\";\nimport { DefaultLogger as logger } from \"koatty_logger\";\nimport { Lock } from \"@sesamecare-oss/redlock\";\nimport { timeoutPromise } from \"../utils/lib\";\nimport { Koatty } from \"koatty_core\";\nimport { RedLockMethodOptions, getEffectiveRedLockOptions } from \"../config/config\";\n\n/**\n * Initiation schedule locker client.\n *\n * @param {RedLockOptions} options - RedLock 配置选项\n * @param {Koatty} app - Koatty 应用实例\n * @returns {Promise<void>} \n */\nexport async function initRedLock(options: RedLockOptions, app: Koatty): Promise<void> {\n if (!app || !Helper.isFunction(app.once)) {\n logger.Warn(`RedLock initialization skipped: Koatty app not available or not initialized`);\n return;\n }\n try {\n if (Helper.isEmpty(options)) {\n throw Error(`Missing RedLock configuration. Please write a configuration item with the key name 'RedLock' in the db.ts file.`);\n }\n // 获取RedLocker实例,在首次使用时自动初始化\n const redLocker = RedLocker.getInstance(options);\n await redLocker.initialize();\n logger.Info('RedLock initialized successfully');\n } catch (error) {\n logger.Error('Failed to initialize RedLock:', error);\n throw error;\n }\n}\n\n/**\n * Create redLocker Descriptor with improved error handling and type safety\n * @param descriptor - Property descriptor\n * @param name - Lock name\n * @param method - Method name\n * @param methodOptions - Method-level RedLock options\n * @returns Enhanced property descriptor\n */\nexport function redLockerDescriptor(\n descriptor: PropertyDescriptor,\n name: string,\n method: string,\n methodOptions?: RedLockMethodOptions\n): PropertyDescriptor {\n // 参数验证\n if (!descriptor) {\n throw new Error('Property descriptor is required');\n }\n if (!name || typeof name !== 'string') {\n throw new Error('Lock name must be a non-empty string');\n }\n if (!method || typeof method !== 'string') {\n throw new Error('Method name must be a non-empty string');\n }\n\n const { value, configurable, enumerable } = descriptor;\n\n // 验证原始函数\n if (typeof value !== 'function') {\n throw new Error('Descriptor value must be a function');\n }\n\n /**\n * Enhanced function wrapper with proper lock renewal and safety\n */\n const valueFunction = async (\n self: unknown,\n initialLock: Lock,\n lockTime: number,\n timeout: number,\n props: unknown[]\n ): Promise<unknown> => {\n let currentLock = initialLock;\n let remainingTime = timeout;\n const maxExtensions = 3; // 限制续期次数防止无限循环\n let extensionCount = 0;\n \n try {\n while (remainingTime > 0 && extensionCount < maxExtensions) {\n // 创建可取消的超时 Promise\n const timeoutHandler = timeoutPromise(remainingTime);\n \n try {\n // 执行业务方法,与超时竞争\n const result = await Promise.race([\n value.apply(self, props),\n timeoutHandler\n ]);\n \n // 成功执行,取消超时定时器防止内存泄漏\n timeoutHandler.cancel();\n return result;\n } catch (error) {\n // 无论什么错误,都要取消超时定时器\n timeoutHandler.cancel();\n \n // 处理超时错误,尝试续期锁\n if (error instanceof Error && error.message === 'TIME_OUT_ERROR') {\n extensionCount++;\n logger.Debug(`Method ${method} execution timeout, attempting lock extension ${extensionCount}/${maxExtensions}`);\n \n try {\n // 续期锁,获得新的锁实例\n currentLock = await currentLock.extend(lockTime);\n remainingTime = lockTime - 200; // 预留200ms用于锁操作\n logger.Debug(`Lock extended for method: ${method}, remaining time: ${remainingTime}ms`);\n \n // 继续循环,重新执行业务方法\n continue;\n } catch (extendError) {\n logger.Error(`Failed to extend lock for method: ${method}`, extendError);\n throw new Error(`Lock extension failed: ${extendError instanceof Error ? extendError.message : 'Unknown error'}`);\n }\n } else {\n // 非超时错误,直接抛出\n throw error;\n }\n }\n }\n \n // 达到最大续期次数或剩余时间不足\n throw new Error(`Method ${method} execution timeout after ${extensionCount} lock extensions`);\n } finally {\n // 确保锁被释放\n try {\n await currentLock.release();\n logger.Debug(`Lock released for method: ${method}`);\n } catch (releaseError) {\n logger.Warn(`Failed to release lock for method: ${method}`, releaseError);\n }\n }\n };\n\n return {\n configurable,\n enumerable,\n writable: true,\n async value(...props: unknown[]): Promise<unknown> {\n try {\n const redlock = RedLocker.getInstance();\n const lockOptions = getEffectiveRedLockOptions(methodOptions);\n // Acquire a lock.\n const lockTime = lockOptions.lockTimeOut || 10000;\n if (lockTime <= 200) {\n throw new Error(\"Lock timeout must be greater than 200ms to allow for proper execution\");\n }\n\n const lock = await redlock.acquire([method, name], lockTime);\n const timeout = lockTime - 200;\n\n logger.Debug(`Lock acquired for method: ${method}, timeout: ${timeout}ms`);\n return await valueFunction(this, lock, lockTime, timeout, props);\n } catch (error) {\n logger.Error(`RedLock operation failed for method: ${method}`, error);\n throw error;\n }\n },\n };\n}\n\n/**\n * Generate lock name for RedLock decorator\n */\nexport function generateLockName(configName: string | undefined, methodName: string, target: unknown): string {\n if (configName) {\n return configName;\n }\n\n try {\n const targetObj = target as object | Function;\n const identifier = IOCContainer.getIdentifier(targetObj);\n if (identifier) {\n return `${identifier}_${methodName}`;\n }\n } catch {\n // Fallback if IOC container is not available\n }\n\n const targetWithConstructor = target as { constructor?: Function };\n const className = targetWithConstructor.constructor?.name || 'Unknown';\n return `${className}_${methodName}`;\n}","/*\n * @Description: \n * @Usage: \n * @Author: richen\n * @Date: 2025-06-09 16:00:00\n * @LastEditTime: 2025-06-09 16:00:00\n * @License: BSD (3-Clause)\n * @Copyright (c): <richenlin(at)gmail.com>\n */\n\nimport { Helper } from \"koatty_lib\";\nimport { COMPONENT_SCHEDULED, DecoratorType, validateCronExpression } from \"../config/config\";\nimport { IOCContainer } from \"koatty_container\";\n\n/**\n * Schedule task decorator with optimized preprocessing\n *\n * @export\n * @param {string} cron - Cron expression for task scheduling\n * @param {string} [timezone='Asia/Beijing'] - Timezone for the schedule\n * \n * Cron expression format:\n * * Seconds: 0-59\n * * Minutes: 0-59\n * * Hours: 0-23\n * * Day of Month: 1-31\n * * Months: 1-12 (Jan-Dec)\n * * Day of Week: 1-7 (Sun-Sat)\n * \n * @returns {MethodDecorator}\n * @throws {Error} When cron expression is invalid or decorator is used on wrong class type\n */\nexport function Scheduled(cron: string, timezone = 'Asia/Beijing') {\n // 参数验证\n if (Helper.isEmpty(cron)) {\n throw Error(\"Cron expression is required and cannot be empty\");\n }\n\n // 验证cron表达式格式\n try {\n validateCronExpression(cron);\n } catch (error) {\n throw Error(`Invalid cron expression: ${(error as Error).message}`);\n }\n\n // 验证时区\n if (timezone && typeof timezone !== 'string') {\n throw Error(\"Timezone must be a string\");\n }\n\n return IOCContainer.createDecorator(({ target, methodName, descriptor, method, context }) => {\n if (context) {\n // TC39 path\n context.addInitializer?.(function (this: any) {\n const targetClass = this.constructor;\n const componentType = IOCContainer.getType(targetClass);\n if (componentType !== \"SERVICE\" && componentType !== \"COMPONENT\") {\n throw Error(\"@Scheduled decorator can only be used on SERVICE or COMPONENT classes.\");\n }\n\n // 验证方法名\n if (!methodName || typeof methodName !== 'string') {\n throw Error(\"Method name is required for @Scheduled decorator\");\n }\n\n // 保存类到IOC容器\n IOCContainer.saveClass(\"COMPONENT\", targetClass, targetClass.name);\n // 保存调度元数据到 IOC 容器\n IOCContainer.attachClassMetadata(COMPONENT_SCHEDULED, DecoratorType.SCHEDULED, {\n method: methodName,\n cron,\n timezone\n }, this, methodName);\n });\n\n return method;\n } else {\n // Legacy path\n // 验证装饰器使用的类型(从原型对象获取类构造函数)\n const targetClass = (target as any).constructor;\n const componentType = IOCContainer.getType(targetClass);\n if (componentType !== \"SERVICE\" && componentType !== \"COMPONENT\") {\n throw Error(\"@Scheduled decorator can only be used on SERVICE or COMPONENT classes.\");\n }\n\n // 验证方法名\n if (!methodName || typeof methodName !== 'string') {\n throw Error(\"Method name is required for @Scheduled decorator\");\n }\n\n // 验证方法描述符\n if (!descriptor || typeof descriptor.value !== 'function') {\n throw Error(\"@Scheduled decorator can only be applied to methods\");\n }\n // 保存类到IOC容器\n IOCContainer.saveClass(\"COMPONENT\", targetClass, targetClass.name);\n // 保存调度元数据到 IOC 容器\n IOCContainer.attachClassMetadata(COMPONENT_SCHEDULED, DecoratorType.SCHEDULED, {\n method: methodName,\n cron,\n timezone // 保存确定的时区值\n }, target as object, methodName);\n }\n }, 'method');\n}\n","/**\n * @ author: richen\n * @ copyright: Copyright (c) - <richenlin(at)gmail.com>\n * @ license: MIT\n * @ version: 2020-07-06 10:29:20\n */\nimport { IOCContainer } from \"koatty_container\";\nimport { Helper } from \"koatty_lib\";\nimport { DefaultLogger as logger } from \"koatty_logger\";\nimport { CronJob } from \"cron\";\nimport { COMPONENT_SCHEDULED, DecoratorType, getEffectiveTimezone } from \"../config/config\";\nimport { Koatty } from \"koatty_core\";\n\n/**\n * 初始化调度任务系统\n * 在appReady时触发批量注入调度任务,确保所有初始化工作完成\n *\n * @param {Koatty} app - Koatty 应用实例\n * @param {any} options - 调度任务配置\n */\nexport async function initSchedule(options: any, app: Koatty): Promise<void> {\n if (!app || !Helper.isFunction(app.once)) {\n logger.Warn(`Schedule initialization skipped: Koatty app not available or not initialized`);\n return;\n }\n try {\n await injectSchedule(options);\n logger.Info('Schedule system initialized successfully');\n } catch (error) {\n logger.Error('Failed to initialize Schedule system:', error);\n throw error;\n }\n}\n\n/**\n * Inject schedule job with enhanced error handling and validation\n *\n * @param {unknown} target - Target class\n * @param {string} method - Method name\n * @param {string} cron - Cron expression\n * @param {string} [timezone] - Timezone\n */\n/**\n * 批量注入调度任务 - 从IOC容器读取类元数据并创建所有CronJob\n */\nexport async function injectSchedule(options: any): Promise<void> {\n try {\n logger.Debug('Starting batch schedule injection...');\n let totalScheduled = 0;\n const componentList = IOCContainer.listClass(\"COMPONENT\");\n for (const component of componentList) {\n const classMetadata = IOCContainer.getClassMetadata(COMPONENT_SCHEDULED, DecoratorType.SCHEDULED,\n component.target);\n if (!classMetadata || !Array.isArray(classMetadata)) {\n continue;\n }\n\n const instance: any = IOCContainer.get(component.id);\n if (!instance) {\n continue;\n }\n\n for (const scheduleData of classMetadata) {\n try {\n if (!scheduleData || !scheduleData.method) {\n continue;\n }\n\n const targetMethod = instance[scheduleData.method];\n if (!Helper.isFunction(targetMethod)) {\n logger.Warn(`Schedule injection skipped: method ${scheduleData.method} is not a function in ${component.id}`);\n continue;\n }\n\n const taskName = `${component.id}_${scheduleData.method}`;\n const tz = getEffectiveTimezone(options, scheduleData.timezone);\n\n new CronJob(\n scheduleData.cron,\n () => {\n logger.Debug(`The schedule job ${taskName} started.`);\n Promise.resolve(targetMethod.call(instance))\n .then(() => {\n logger.Debug(`The schedule job ${taskName} completed.`);\n })\n .catch((error) => {\n logger.Error(`The schedule job ${taskName} failed:`, error);\n });\n },\n null,\n true,\n tz\n );\n\n totalScheduled++;\n logger.Debug(`Schedule job ${taskName} registered with cron: ${scheduleData.cron}`);\n } catch (error) {\n logger.Error(`Failed to process schedule for ${component.id}:`, error);\n }\n }\n }\n\n logger.Info(`Batch schedule injection completed. ${totalScheduled} jobs registered.`);\n } catch (error) {\n logger.Error('Failed to inject schedules:', error);\n }\n}\n","/**\n * @ author: richen\n * @ copyright: Copyright (c) - <richenlin(at)gmail.com>\n * @ license: MIT\n * @ version: 2020-07-06 10:30:11\n */\n\nimport { Koatty } from \"koatty_core\";\nimport { RedLock } from \"./decorator/redlock\";\nimport { Scheduled } from \"./decorator/scheduled\";\nimport { initRedLock } from \"./process/locker\";\nimport { initSchedule } from \"./process/schedule\";\nimport { ScheduledOptions } from \"./config/config\";\nimport { RedisMode } from \"./locker/interface\";\n\n// Export the decorators\nexport { RedLock, Scheduled };\n\n// Export types and interfaces\nexport { RedLocker } from \"./locker/redlock\";\nexport type { RedLockOptions } from \"./locker/redlock\";\nexport { RedisMode } from \"./locker/interface\";\nexport type { \n IDistributedLock, \n IRedisClient, \n ILockOptions,\n RedisConfig,\n RedisStandaloneConfig,\n RedisSentinelConfig,\n RedisClusterConfig\n} from \"./locker/interface\";\nexport { RedisFactory, RedisClientAdapter } from \"./locker/redis-factory\";\n\n/**\n * @deprecated Use RedLock instead. This will be removed in v3.0.0\n */\nexport const SchedulerLock = RedLock;\n\n/** \n * defaultOptions\n */\n\nconst defaultOptions: ScheduledOptions = {\n timezone: \"Asia/Beijing\",\n lockTimeOut: 10000,\n clockDriftFactor: 0.01,\n maxRetries: 3,\n retryDelayMs: 200,\n redisConfig: {\n mode: RedisMode.STANDALONE,\n host: \"localhost\",\n port: 6379,\n password: \"\",\n db: 0,\n keyPrefix: \"redlock:\"\n }\n}\n\n/**\n * @param options - The options for the scheduled job\n * @param app - The Koatty application instance\n */\nexport async function KoattyScheduled(options: ScheduledOptions, app: Koatty) {\n options = { ...defaultOptions, ...options };\n \n app.once(\"appReady\", async function () {\n // 初始化RedLock\n await initRedLock(options, app);\n // 初始化调度任务系统\n await initSchedule(options, app);\n });\n}"]}