@ha-bits/cortex-core 0.1.0-next.69 → 1.1.15
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/index.cjs +240 -1729
- package/index.cjs.map +4 -4
- package/index.d.ts +17 -0
- package/index.js +245 -1722
- package/index.js.map +4 -4
- package/package.json +2 -10
package/index.js.map
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
{
|
|
2
2
|
"version": 3,
|
|
3
|
-
"sources": ["../../../../packages/cortex/core/src/WorkflowExecutor.ts", "../../../../packages/bindings/src/runtime.ts", "../../../../packages/bindings/src/fs.ts", "../../../../packages/bindings/src/path.ts", "../../../../packages/bindings/src/shell.ts", "../../../../packages/core/src/logger/types.ts", "../../../../packages/core/src/logger/Logger.ts", "../../../../packages/core/src/logger/ConfigResolver.ts", "../../../../packages/core/src/logger/transports/Transport.ts", "../../../../packages/core/src/logger/transports/ConsoleTransport.ts", "../../../../packages/core/src/logger/transports/FileTransport.ts", "../../../../packages/core/src/logger/formatters/Formatter.ts", "../../../../packages/core/src/logger/formatters/JsonFormatter.ts", "../../../../packages/core/src/logger/transports/JsonTransport.ts", "../../../../packages/core/src/logger/formatters/TextFormatter.ts", "../../../../packages/core/src/logger/LoggerFactory.ts", "../../../../packages/cortex/core/src/utils/utils.ts", "../../../../packages/cortex/core/src/utils/customRequire.ts", "../../../../packages/cortex/core/src/utils/moduleCloner.ts", "../../../../packages/cortex/core/src/utils/moduleLoader.ts", "../../../../packages/cortex/core/src/n8n/executionContext.ts", "../../../../packages/
|
|
4
|
-
"sourcesContent": ["import { v4 as uuidv4 } from 'uuid';\nimport { Cron } from 'croner';\nimport { executeN8nModule } from './n8n/n8nExecutor';\nimport { executeActivepiecesModule } from './activepieces/activepiecesExecutor';\nimport { triggerHelper, TriggerHookType } from './activepieces/activepiecesTrigger';\nimport { executeBitsModule, pieceFromModule } from './bits/bitsDoer';\nimport { bitsTriggerHelper, TriggerHookType as BitsTriggerHookType } from './bits/bitsWatcher';\nimport { executeScriptModule } from './script/scriptExecutor';\nimport { ensureModuleInstalled } from './utils/moduleLoader';\nimport { getSecurityConfig, scanInputForSecurity } from './security/inputScanner';\nimport { LoggerFactory, ILogger } from '@ha-bits/core/logger';\nimport { IWebhookHandler } from './WebhookHandler';\nimport {\n Workflow,\n WorkflowNode,\n WorkflowEdge,\n ExecutionResult,\n WorkflowExecution,\n NodeDependencies,\n NodeExecutionStatus,\n WebhookTriggerInfo,\n WorkflowConfig,\n WorkflowReference,\n LoadedWorkflow,\n StreamCallback,\n StreamEvent,\n FlowControlMetadata,\n} from '@habits/shared/types';\n\n// ============================================================================\n// Workflow Executor\n// ============================================================================\n\n/**\n * Options for initializing WorkflowExecutor from in-memory data\n */\nexport interface InitFromDataOptions {\n /** The workflow configuration (equivalent to config.json content) */\n config: WorkflowConfig;\n /** Map of workflow id to workflow object (instead of loading from file paths) */\n workflows: Map<string, Workflow> | Record<string, Workflow>;\n /** Environment variables to set (equivalent to .env file content parsed) */\n env?: Record<string, string>;\n}\n\nexport class WorkflowExecutor {\n private executions: Map<string, WorkflowExecution> = new Map();\n private loadedWorkflows: Map<string, LoadedWorkflow> = new Map();\n private config: WorkflowConfig | null = null;\n private logger: ILogger = LoggerFactory.getRoot();\n private env: Record<string, string | undefined> = {};\n \n /** Active polling cron jobs - keyed by workflowId:nodeId */\n private pollingCronJobs: Map<string, Cron> = new Map();\n\n /**\n * Initialize from in-memory data (no file system access needed)\n * This is the ONLY initialization method - it's platform-agnostic (works in browser and Node.js)\n */\n async initFromData(options: InitFromDataOptions): Promise<void> {\n const { config, workflows, env } = options;\n\n // Store environment variables in class property (platform-agnostic)\n if (env) {\n this.env = { ...env };\n // Also set process.env for Node.js compatibility with modules that read it directly\n if (typeof process !== 'undefined' && process.env) {\n for (const [key, value] of Object.entries(env)) {\n process.env[key] = value;\n }\n }\n }\n\n // Initialize logger from config (env vars are applied automatically by ConfigResolver)\n this.logger = LoggerFactory.initRoot(config.logging);\n this.logger.info('Environment variables set from config');\n\n this.config = config;\n this.logger.info('Loading workflow configuration from data');\n this.logger.debug('Config details', { \n version: this.config.version || 'not specified',\n workflowCount: this.config.workflows.length \n });\n\n // Convert Record to Map if needed\n const workflowsMap = workflows instanceof Map \n ? workflows \n : new Map(Object.entries(workflows));\n\n // Load each workflow from the provided map\n for (const workflowRef of this.config.workflows) {\n if (workflowRef.enabled === false) {\n this.logger.log(` \u23ED\uFE0F Skipping disabled workflow: ${workflowRef.id || workflowRef.path}`);\n continue;\n }\n\n // Try to find workflow by id first, then by path (as a key)\n const workflowId = workflowRef.id || workflowRef.path;\n let workflow = workflowsMap.get(workflowId);\n \n // Also try the path as a fallback key\n if (!workflow && workflowRef.path) {\n workflow = workflowsMap.get(workflowRef.path);\n }\n\n if (!workflow) {\n this.logger.error(` \u274C Workflow not found in data: ${workflowId}`);\n continue;\n }\n\n try {\n const finalWorkflowId = workflowRef.id || workflow.id || workflowId;\n\n if (!finalWorkflowId) {\n this.logger.error(` \u274C No id found for workflow - please specify id in config or workflow`);\n continue;\n }\n\n // Update workflow id to match the resolved id\n workflow.id = finalWorkflowId;\n\n // Update reference with resolved id for consistency\n const resolvedRef = { ...workflowRef, id: finalWorkflowId };\n\n this.loadedWorkflows.set(finalWorkflowId, {\n reference: resolvedRef,\n workflow\n });\n\n this.logger.log(` \u2705 Loaded workflow: ${finalWorkflowId} (${workflow.name})`);\n\n // Print all env variables starting with HABITS_, only the names not values\n this.logger.log(` \uD83D\uDD11 Environment variables:`);\n for (const key of Object.keys(this.env)) {\n if (key.startsWith('HABITS_')) {\n this.logger.log(` - ${key}: ${this.env[key] !== undefined ? '(Set but a secret you know)' : '(not set)'}`);\n }\n }\n\n // Log resolvable params that start with \"habits.\"\n this.logger.log(` \uD83D\uDCCB Resolvable habits params in workflow:`);\n const habitsParams = this.findHabitsParams(workflow);\n if (habitsParams.length > 0) {\n for (const param of habitsParams) {\n if (param.startsWith('habits.env.')) {\n const envVar = param.slice('habits.env.'.length);\n const value = this.env[envVar];\n this.logger.log(` - {{${param}}} \u2192 ${value !== undefined ? '(Set but a secret you know)' : '(not set)'}`);\n } else {\n this.logger.log(` - {{${param}}} \u2192 (resolved at runtime)`);\n }\n }\n } else {\n this.logger.log(` (none found)`);\n }\n } catch (error: any) {\n this.logger.error(` \u274C Failed to load workflow ${workflowRef.id || workflowRef.path}: ${error.message}`);\n }\n }\n\n // Make sure no repeated workflowId\n const workflowIds = Array.from(this.loadedWorkflows.keys());\n const duplicates = workflowIds.filter((id, index) => workflowIds.indexOf(id) !== index);\n if (duplicates.length > 0) {\n throw new Error(`Duplicate workflow IDs found: ${duplicates.join(', ')}`);\n }\n\n this.logger.log(`\\n\uD83D\uDCE6 Successfully loaded ${this.loadedWorkflows.size} workflow(s)\\n`);\n\n // Pre-load all modules to ensure they're ready before first request\n await this.preloadModules();\n }\n\n /**\n * Pre-load all modules referenced in loaded workflows\n * This ensures dependencies are cloned/installed before the first request\n */\n private async preloadModules(): Promise<void> {\n const modulesToPreload: Set<string> = new Set();\n const moduleDefinitions: Map<string, { framework: string; source: string; module: string }> = new Map();\n\n // Scan all loaded workflows for modules\n for (const [workflowId, { workflow }] of this.loadedWorkflows) {\n for (const node of workflow.nodes || []) {\n const { framework, source, module: moduleName } = node.data;\n // Skip inline scripts - they don't need preloading\n if (source === 'inline') {\n continue;\n }\n if (framework && source && moduleName) {\n const key = `${framework}:${source}:${moduleName}`;\n if (!modulesToPreload.has(key)) {\n modulesToPreload.add(key);\n moduleDefinitions.set(key, { framework, source, module: moduleName });\n }\n }\n }\n }\n\n if (modulesToPreload.size === 0) {\n this.logger.log(`\\n\uD83D\uDCE6 No modules to preload\\n`);\n return;\n }\n\n this.logger.log(`\\n\uD83D\uDCE6 Pre-loading ${modulesToPreload.size} module(s)...`);\n\n // Preload all modules in parallel\n const preloadPromises = Array.from(moduleDefinitions.entries()).map(async ([key, def]) => {\n try {\n this.logger.log(` \u23F3 Preloading: ${def.module}`);\n await ensureModuleInstalled({\n framework: def.framework,\n source: def.source as 'github' | 'npm',\n repository: def.module,\n });\n this.logger.log(` \u2705 Preloaded: ${def.module}`);\n } catch (error: any) {\n this.logger.error(` \u274C Failed to preload ${def.module}: ${error.message}`);\n }\n });\n\n await Promise.all(preloadPromises);\n this.logger.log(`\\n\uD83D\uDCE6 Module preloading complete\\n`);\n\n // Hook polling triggers for activepieces modules\n await this.hookPollingTriggers();\n \n // Register bits polling triggers with cron scheduling\n await this.registerBitsPollingTriggers();\n }\n\n /**\n * Hook polling triggers for all loaded workflows\n * This sets up activepieces polling triggers to run immediately\n */\n private async hookPollingTriggers(): Promise<void> {\n for (const [workflowId, { workflow }] of this.loadedWorkflows) {\n for (const node of workflow.nodes || []) {\n // Check if this is an activepieces polling trigger\n if (triggerHelper.isActivepiecesTrigger(node) && node.data?.triggerType === 'polling') {\n const triggerName = node.data.operation;\n if (!triggerName) {\n this.logger.warn(`\u26A0\uFE0F No operation specified for polling trigger: ${node.id}`);\n continue;\n }\n\n this.logger.log(`\\n\uD83D\uDD14 Hooking polling trigger: ${node.id} (${triggerName}) in workflow ${workflowId}`);\n \n try {\n const moduleDefinition = {\n framework: node.data.framework,\n source: node.data.source as 'github' | 'npm',\n repository: node.data.module || '',\n };\n\n // Resolve template strings in params and credentials\n const resolvedParams = this.resolveParameters(node.data.params || {}, {});\n const resolvedCredentials = this.resolveParameters(node.data.credentials || {}, {});\n\n // Merge params and credentials for trigger input\n const triggerInput = {\n ...resolvedParams,\n credentials: resolvedCredentials,\n };\n\n this.logger.log(` \uD83D\uDCCB Trigger input: ${JSON.stringify(triggerInput, null, 2)}`);\n\n // Execute the specific trigger immediately\n this.logger.log(` \uD83D\uDE80 Running trigger ${triggerName} immediately...`);\n const result = await triggerHelper.executeActivepiecesTrigger({\n moduleDefinition,\n triggerName,\n input: triggerInput,\n });\n\n this.logger.log(`\\n\uD83D\uDCEC Trigger result for ${triggerName}:`);\n this.logger.log(` Success: ${result.success}`);\n this.logger.log(` Output items: ${result.output?.length || 0}`);\n if (result.output && result.output.length > 0) {\n this.logger.log(` Output: ${JSON.stringify(result.output, null, 2)}`);\n \n // Trigger returned data - execute workflow continuation\n this.logger.log(`\\n\uD83D\uDE80 Trigger ${node.id} returned data, executing workflow continuation...`);\n for (const item of result.output) {\n try {\n // Execute workflow with trigger node pre-populated\n const executionResult = await this.executeWorkflow(workflowId, {\n startFromNode: node.id,\n triggerData: { [node.id]: item },\n });\n this.logger.log(` \u2705 Workflow execution completed: ${executionResult.status}`);\n } catch (execError: any) {\n this.logger.error(` \u274C Workflow execution failed: ${execError.message}`);\n }\n }\n }\n } catch (error: any) {\n this.logger.error(` \u274C Failed to hook trigger ${node.id}: ${error.message}`);\n }\n }\n }\n }\n }\n\n /**\n * Register bits polling triggers with cron scheduling.\n * Scans workflows for polling trigger nodes, calls their onEnable() to get schedule,\n * then creates cron jobs using croner to periodically call run().\n */\n async registerBitsPollingTriggers(): Promise<void> {\n const workflows = this.getAllWorkflows();\n this.logger.log(`\\n\u23F0 Scanning ${workflows.length} workflow(s) for polling triggers...`);\n \n let registeredCount = 0;\n \n for (const { reference, workflow } of workflows) {\n if (reference.enabled === false) continue;\n \n const workflowId = reference.id || workflow.id;\n \n for (const node of workflow.nodes || []) {\n // Check if this is a polling trigger node (bits framework)\n const nodeData = node.data as any;\n const isTrigger = nodeData?.isTrigger === true || node.type === 'trigger';\n const isBits = nodeData?.framework === 'bits';\n const hasModule = !!nodeData?.module;\n \n if (!isTrigger || !isBits || !hasModule) continue;\n \n const moduleName = nodeData.module;\n const triggerName = nodeData.operation || 'default';\n \n try {\n // Load the bit module to check trigger type\n let bitPiece: any = null;\n const moduleDefinition = { \n source: (nodeData.source || 'npm') as 'npm' | 'local' | 'github' | 'link', \n module: moduleName,\n framework: 'bits' as const,\n repository: moduleName,\n };\n \n try {\n bitPiece = await pieceFromModule(moduleDefinition);\n } catch (loadError) {\n this.logger.warn(` \u26A0\uFE0F Could not load module ${moduleName}: ${loadError}`);\n continue;\n }\n \n // Get the trigger definition\n const triggers = typeof bitPiece.triggers === 'function' ? bitPiece.triggers() : bitPiece.triggers;\n const trigger = triggers?.[triggerName];\n \n if (!trigger) {\n this.logger.warn(` \u26A0\uFE0F Trigger ${triggerName} not found in module ${moduleName}`);\n continue;\n }\n \n // Check if it's a polling trigger type\n const triggerType = trigger.type?.toUpperCase?.() || trigger.type;\n if (triggerType !== 'POLLING') {\n continue; // Not a polling trigger\n }\n \n // Extract trigger props from node params and resolve env expressions\n const rawProps = nodeData.params || {};\n const triggerProps = this.resolveParameters(rawProps, {});\n \n this.logger.log(` \u23F0 Enabling polling trigger: ${workflowId}/${node.id} (${moduleName}:${triggerName})`);\n \n // Call onEnable to get the schedule options\n const result = await bitsTriggerHelper.executeTrigger({\n moduleDefinition,\n triggerName,\n input: triggerProps,\n hookType: BitsTriggerHookType.ON_ENABLE,\n trigger,\n workflowId,\n nodeId: node.id,\n });\n \n if (!result.success) {\n this.logger.warn(` \u26A0\uFE0F Failed to enable ${workflowId}/${node.id}: ${result.message}`);\n continue;\n }\n \n // Get schedule options from the result\n const scheduleOptions = result.scheduleOptions;\n if (!scheduleOptions?.cronExpression) {\n this.logger.warn(` \u26A0\uFE0F No schedule returned from onEnable for ${workflowId}/${node.id}`);\n continue;\n }\n \n const cronKey = `${workflowId}:${node.id}`;\n const { cronExpression, timezone = 'UTC' } = scheduleOptions;\n \n this.logger.log(` \uD83D\uDCC5 Creating cron job: ${cronExpression} (${timezone}) for ${cronKey}`);\n \n // Create the cron job\n const cronJob = new Cron(cronExpression, { timezone, name: cronKey }, async () => {\n const triggeredAt = new Date().toISOString();\n this.logger.log(` \u23F0 Cron fired: ${cronKey} at ${triggeredAt}`);\n \n try {\n // Call trigger.run() to get the polling results\n const runResult = await bitsTriggerHelper.executeTrigger({\n moduleDefinition,\n triggerName,\n input: triggerProps,\n hookType: BitsTriggerHookType.RUN,\n trigger,\n workflowId,\n nodeId: node.id,\n });\n \n // If run() returned data, execute the workflow for EACH item\n if (runResult.success && runResult.output && runResult.output.length > 0) {\n this.logger.log(` \uD83D\uDCE6 Trigger returned ${runResult.output.length} item(s), executing workflow for each...`);\n \n // Get the workflow\n const loadedWorkflow = this.getWorkflow(workflowId);\n if (!loadedWorkflow) {\n this.logger.error(` \u274C Workflow ${workflowId} not found`);\n return;\n }\n \n // Execute workflow for EACH item (like Activepieces does for polling triggers)\n for (let i = 0; i < runResult.output.length; i++) {\n const item = runResult.output[i];\n this.logger.log(` \uD83D\uDD04 Processing item ${i + 1}/${runResult.output.length}`);\n \n try {\n const execution = await this.executeWorkflow(loadedWorkflow.workflow, {\n initialContext: {\n 'habits.input': item, // Single item, not array\n __pollingTrigger: true,\n __pollingNodeId: node.id,\n __triggeredAt: triggeredAt,\n __pollingItemIndex: i,\n },\n skipTriggerWait: true,\n triggerNodeId: node.id,\n });\n \n this.logger.log(` \u2705 Item ${i + 1} processed: ${execution.status}`);\n } catch (itemErr: any) {\n this.logger.error(` \u274C Item ${i + 1} failed: ${itemErr.message}`);\n }\n }\n \n this.logger.log(` \u2705 Workflow ${workflowId} completed processing ${runResult.output.length} item(s)`);\n } else {\n this.logger.log(` \u23F3 No new items from trigger, skipping workflow execution`);\n }\n } catch (err: any) {\n this.logger.error(` \u274C Error in polling trigger: ${err.message}`);\n }\n });\n \n // Store the cron job\n this.pollingCronJobs.set(cronKey, cronJob);\n registeredCount++;\n this.logger.log(` \u2705 Registered: ${workflowId}/${node.id} (${triggerName}) -> ${cronExpression}`);\n } catch (error: any) {\n this.logger.error(` \u274C Error enabling polling trigger for ${workflowId}/${node.id}: ${error}`);\n }\n }\n }\n \n this.logger.log(`\u23F0 Enabled ${registeredCount} polling trigger(s)\\n`);\n }\n\n /**\n * Stop all polling cron jobs\n */\n stopPollingTriggers(): void {\n for (const [key, cron] of this.pollingCronJobs) {\n cron.stop();\n this.logger.log(` \u23F9\uFE0F Stopped polling trigger: ${key}`);\n }\n this.pollingCronJobs.clear();\n }\n\n /**\n * Find all template params starting with \"habits.\" in a workflow\n */\n private findHabitsParams(workflow: Workflow): string[] {\n const habitsParams: Set<string> = new Set();\n const templateRegex = /\\{\\{(habits\\.[^}]+)\\}\\}/g;\n\n const scanObject = (obj: any) => {\n if (typeof obj === 'string') {\n let match;\n while ((match = templateRegex.exec(obj)) !== null) {\n habitsParams.add(match[1].trim());\n }\n } else if (Array.isArray(obj)) {\n obj.forEach(item => scanObject(item));\n } else if (typeof obj === 'object' && obj !== null) {\n Object.values(obj).forEach(value => scanObject(value));\n }\n };\n\n // Scan nodes\n workflow.nodes?.forEach(node => scanObject(node.data));\n // Scan output\n if (workflow.output) scanObject(workflow.output);\n if ((workflow as any).outputs) scanObject((workflow as any).outputs);\n\n return Array.from(habitsParams).sort();\n }\n\n /**\n * Get a loaded workflow by ID\n */\n getWorkflow(workflowId: string): LoadedWorkflow | undefined {\n return this.loadedWorkflows.get(workflowId);\n }\n\n /**\n * Get all loaded workflows\n */\n getAllWorkflows(): LoadedWorkflow[] {\n return Array.from(this.loadedWorkflows.values());\n }\n\n /**\n * Add a workflow programmatically (for OpenAPI generation without file loading)\n */\n addWorkflow(workflow: Workflow, reference?: Partial<WorkflowReference>): void {\n const workflowId = reference?.id || workflow.id;\n if (!workflowId) {\n throw new Error('Workflow must have an id');\n }\n \n const fullReference: WorkflowReference = {\n id: workflowId,\n path: reference?.path || `inline:${workflowId}`,\n enabled: reference?.enabled !== false,\n ...(reference?.webhookTimeout && { webhookTimeout: reference.webhookTimeout }),\n };\n \n this.loadedWorkflows.set(workflowId, {\n reference: fullReference,\n workflow: { ...workflow, id: workflowId },\n });\n }\n\n /**\n * Get the current config\n */\n getConfig(): WorkflowConfig | null {\n return this.config;\n }\n\n /**\n * Execute a complete workflow using dependency-based execution\n */\n async executeWorkflow(workflowOrId: Workflow | string, options?: {\n webhookHandler?: IWebhookHandler; // Optional webhook handler for workflow triggers (Node.js server only)\n webhookTimeout?: number;\n initialContext?: Record<string, any>;\n onStream?: StreamCallback;\n triggerData?: Record<string, any>; // Pre-populate trigger node outputs\n startFromNode?: string; // Start execution from a specific node\n skipTriggerWait?: boolean; // Skip waiting for webhook trigger (payload provided via initialContext)\n triggerNodeId?: string; // The trigger node ID when skipping trigger wait\n /** Per-user OAuth tokens from request cookies (for multi-user server mode) */\n oauthTokens?: Record<string, { accessToken: string; refreshToken?: string; tokenType: string; expiresAt?: number }>;\n }): Promise<WorkflowExecution> {\n // Resolve workflow from ID if string provided\n let workflow: Workflow;\n if (typeof workflowOrId === 'string') {\n const loaded = this.loadedWorkflows.get(workflowOrId);\n if (!loaded) {\n throw new Error(`Workflow not found: ${workflowOrId}`);\n }\n workflow = loaded.workflow;\n } else {\n workflow = workflowOrId;\n }\n\n const executionId = uuidv4();\n const execution: WorkflowExecution = {\n id: executionId,\n workflowId: workflow.id,\n status: 'running',\n results: [],\n nodeStatuses: [],\n startTime: new Date(),\n };\n\n this.executions.set(executionId, execution);\n this.logger.log(`\\n\uD83D\uDE80 Starting workflow execution: ${workflow.name} (${executionId})`);\n\n // Helper function to emit stream events\n const emitStreamEvent = (event: Omit<StreamEvent, 'timestamp' | 'executionId' | 'workflowId'>) => {\n if (options?.onStream) {\n const completedCount = execution.nodeStatuses.filter(s => s.status === 'completed' || s.status === 'failed').length;\n const totalCount = workflow.nodes.length;\n options.onStream({\n ...event,\n timestamp: new Date().toISOString(),\n executionId,\n workflowId: workflow.id,\n progress: {\n completed: completedCount,\n total: totalCount,\n percentage: totalCount > 0 ? Math.round((completedCount / totalCount) * 100) : 0\n }\n });\n }\n };\n\n // Emit execution started event\n emitStreamEvent({\n type: 'execution_started',\n status: 'running'\n });\n\n try {\n // Scan for webhook triggers\n const webhookTriggers = this.findWebhookTriggers(workflow.nodes);\n\n // If there are webhook triggers, ensure a webhook handler is provided (unless skipping trigger wait)\n if (webhookTriggers.length > 0 && !options?.skipTriggerWait) {\n if (!options?.webhookHandler) {\n throw new Error(\n `Workflow \"${workflow.name}\" contains ${webhookTriggers.length} webhook trigger(s) but no webhookHandler was provided. ` +\n `Webhook triggers are only supported in Node.js server environments. ` +\n `Provide a webhookHandler via options or remove webhook triggers from the workflow.`\n );\n }\n\n this.logger.log(`\\n\uD83D\uDCCB Detected ${webhookTriggers.length} webhook trigger(s):`);\n for (const trigger of webhookTriggers) {\n this.logger.log(` - Node: ${trigger.nodeId}`);\n }\n this.logger.log('\\n\u23F3 Waiting for webhook(s) to be triggered...\\n');\n } else if (webhookTriggers.length > 0 && options?.skipTriggerWait) {\n this.logger.log(`\\n\uD83D\uDCCB Detected ${webhookTriggers.length} webhook trigger(s) - using pre-provided payload`);\n }\n\n // Build dependency arrays\n const dependencies = this.buildDependencyMap(workflow.nodes, workflow?.edges || []);\n\n // Initialize node statuses\n execution.nodeStatuses = workflow.nodes.map(node => ({\n nodeId: node.id,\n status: 'pending' as const\n }));\n\n // Execution context to share data between nodes\n // Initialize with any provided initial context (e.g., habits.input, habits.headers, habits.cookies)\n let context: Record<string, any> = options?.initialContext ? { ...options.initialContext } : {};\n\n // Store per-user OAuth tokens in context for multi-user server mode\n // These are passed through to bits execution and take precedence over the global token store\n if (options?.oauthTokens) {\n context._oauthTokens = options.oauthTokens;\n }\n\n // Initialize habits namespace if not present\n if (!context.habits) {\n context.habits = {};\n }\n\n // Add habits.context with workflow execution metadata\n context.habits.context = {\n workflowId: workflow.id,\n workflowName: workflow.name,\n executionId,\n timestamp: new Date().toISOString(),\n startTime: execution.startTime.toISOString(),\n nodeId: '', // Will be set per-node during execution\n };\n\n // Security scanning on habits.input.* data (DLP, PII, Moderation)\n const securityConfig = getSecurityConfig();\n if (context.habits?.input) {\n context.habits.input = await scanInputForSecurity(context.habits.input, securityConfig, this.logger);\n }\n\n // If triggerData provided, mark trigger nodes as completed and add to context\n if (options?.triggerData) {\n for (const [nodeId, data] of Object.entries(options.triggerData)) {\n // Security scanning on trigger output data\n const scannedData = await scanInputForSecurity(data, securityConfig, this.logger);\n context[nodeId] = scannedData;\n this.updateNodeStatus(execution, nodeId, 'completed', { result: data });\n this.logger.log(`\uD83D\uDCCD Pre-populated trigger node: ${nodeId}`);\n \n // Add result to execution\n execution.results.push({\n nodeId,\n success: true,\n result: data,\n duration: 0,\n timestamp: new Date(),\n });\n }\n }\n\n // Keep executing until all nodes are completed or failed\n while (this.hasRunnableNodes(execution.nodeStatuses, dependencies)) {\n const runnableNodes = this.findRunnableNodes(execution.nodeStatuses, dependencies);\n\n if (runnableNodes.length === 0) {\n this.logger.log('\u26A0\uFE0F No runnable nodes found, stopping execution');\n break;\n }\n\n // Execute all runnable nodes in parallel\n const nodeExecutionPromises = runnableNodes.map(async (nodeId) => {\n const node = workflow.nodes.find(n => n.id === nodeId);\n if (!node) return;\n\n // Check flow control - skip nodes on non-activated branches\n const flowControlResult = this.checkFlowControl(nodeId, dependencies, context);\n if (flowControlResult === 'skip') {\n // Mark node as skipped and add minimal context\n context[nodeId] = { _skipped: true, _reason: 'Branch not activated by upstream flow control' };\n this.updateNodeStatus(execution, nodeId, 'skipped');\n \n // Emit node skipped event\n emitStreamEvent({\n type: 'node_completed',\n nodeId,\n nodeName: node.data.label,\n status: 'skipped',\n result: { _skipped: true },\n duration: 0\n });\n return;\n }\n\n execution.currentNode = nodeId;\n this.logger.log(`\\n\uD83D\uDCDD Executing node: ${nodeId} (${node.data.label})`);\n\n // Update habits.context.nodeId for the current node\n if (context.habits?.context) {\n context.habits.context.nodeId = nodeId;\n }\n\n // Update node status to running\n this.updateNodeStatus(execution, nodeId, 'running');\n\n // Emit node started event\n emitStreamEvent({\n type: 'node_started',\n nodeId,\n nodeName: node.data.label,\n status: 'running'\n });\n\n try {\n // Check if this is a polling trigger node being executed from cron\n const isPollingTriggerNode = context.__pollingTrigger && \n context.__pollingNodeId === nodeId &&\n (node.type === 'trigger' || (node.data as any)?.isTrigger);\n \n if (isPollingTriggerNode) {\n // Use the pre-fetched polling data from habits.input\n this.logger.log(`\u23F0 Using pre-fetched polling data for trigger node: ${nodeId}`);\n const pollingData = context['habits.input'];\n \n const scannedResult = await scanInputForSecurity(pollingData, securityConfig, this.logger);\n \n // Update context with polling result\n context[`${nodeId}`] = scannedResult;\n context[nodeId] = scannedResult;\n context.previous_result = scannedResult;\n \n this.updateNodeStatus(execution, nodeId, 'completed', {\n result: scannedResult,\n startTime: new Date(),\n endTime: new Date(),\n duration: 0\n });\n\n // Emit node completed event\n emitStreamEvent({\n type: 'node_completed',\n nodeId,\n nodeName: node.data.label,\n status: 'completed',\n result: scannedResult,\n duration: 0\n });\n }\n // Check if this is a webhook trigger node\n else if (this.isWebhookTriggerNode(node)) {\n // Check if we should skip waiting for webhook (payload provided directly)\n const skipWait = options?.skipTriggerWait && \n (options?.triggerNodeId === nodeId || !options?.triggerNodeId);\n \n if (skipWait && context.webhookPayload) {\n // Use the provided webhook payload from initialContext\n this.logger.log(`\uD83D\uDD14 Using pre-provided webhook payload for trigger node: ${nodeId}`);\n \n const scannedResult = await scanInputForSecurity(context.webhookPayload, securityConfig, this.logger);\n \n // Update context with webhook result\n context[`${nodeId}`] = scannedResult;\n context[nodeId] = scannedResult;\n context.previous_result = scannedResult;\n \n this.updateNodeStatus(execution, nodeId, 'completed', {\n result: scannedResult,\n startTime: new Date(),\n endTime: new Date(),\n duration: 0\n });\n\n // Emit node completed event\n emitStreamEvent({\n type: 'node_completed',\n nodeId,\n nodeName: node.data.label,\n status: 'completed',\n result: scannedResult,\n duration: 0\n });\n } else {\n // webhookHandler is guaranteed to exist here - we validated at the start of executeWorkflow\n const webhookResult = await this.handleWebhookTrigger(node, context, execution, options!.webhookHandler!, options?.webhookTimeout);\n\n // Security scanning on webhook trigger output data\n const scannedResult = await scanInputForSecurity(webhookResult.result, securityConfig, this.logger);\n\n // Update context with scanned webhook result\n context[`${nodeId}`] = scannedResult;\n context[nodeId] = scannedResult;\n context.previous_result = scannedResult;\n context.webhookPayload = scannedResult; // Also store as webhookPayload for easy access\n\n this.updateNodeStatus(execution, nodeId, webhookResult.success ? 'completed' : 'failed', {\n result: scannedResult,\n error: webhookResult.error,\n startTime: new Date(webhookResult.timestamp.getTime() - webhookResult.duration),\n endTime: webhookResult.timestamp,\n duration: webhookResult.duration\n });\n\n // Emit node completed/failed event\n emitStreamEvent({\n type: webhookResult.success ? 'node_completed' : 'node_failed',\n nodeId,\n nodeName: node.data.label,\n status: webhookResult.success ? 'completed' : 'failed',\n result: scannedResult,\n error: webhookResult.error,\n duration: webhookResult.duration\n });\n\n if (!webhookResult.success) {\n this.logger.error(`\u274C Webhook trigger ${nodeId} failed: ${webhookResult.error}`);\n }\n }\n } else {\n const nodeResult = await this.executeNode(node, context, execution);\n\n // Update context with node result\n context[`${nodeId}`] = nodeResult.result;\n context[nodeId] = nodeResult.result; // Also store by node ID for easier access\n context.previous_result = nodeResult.result;\n\n // Update node status based on result\n this.updateNodeStatus(execution, nodeId, nodeResult.success ? 'completed' : 'failed', {\n result: nodeResult.result,\n error: nodeResult.error,\n startTime: new Date(nodeResult.timestamp.getTime() - nodeResult.duration),\n endTime: nodeResult.timestamp,\n duration: nodeResult.duration\n });\n\n // Emit node completed/failed event\n emitStreamEvent({\n type: nodeResult.success ? 'node_completed' : 'node_failed',\n nodeId,\n nodeName: node.data.label,\n status: nodeResult.success ? 'completed' : 'failed',\n result: nodeResult.result,\n error: nodeResult.error,\n duration: nodeResult.duration\n });\n\n // If node failed, we might want to stop (depending on strategy)\n if (!nodeResult.success) {\n this.logger.error(`\u274C Workflow Node ${nodeId} failed: ${nodeResult.error}`);\n // For now, continue with other nodes - could add failure strategies later\n }\n }\n\n } catch (error: any) {\n this.logger.error(`\u274C Node ${nodeId} execution failed: ${error.message}`);\n this.updateNodeStatus(execution, nodeId, 'failed', {\n error: error.message,\n startTime: new Date(),\n endTime: new Date(),\n duration: 0\n });\n\n // Emit node failed event\n emitStreamEvent({\n type: 'node_failed',\n nodeId,\n nodeName: node.data.label,\n status: 'failed',\n error: error.message,\n duration: 0\n });\n }\n });\n\n // Wait for all parallel node executions to complete\n await Promise.all(nodeExecutionPromises);\n\n // Wait one second before next iteration to avoid tight loop, disabling for now, making stuff slow as hell if serving a backend!!\n // await new Promise(resolve => setTimeout(resolve, 1000));\n }\n\n // Determine final execution status\n const failedNodes = execution.nodeStatuses.filter(s => s.status === 'failed');\n const completedNodes = execution.nodeStatuses.filter(s => s.status === 'completed');\n const skippedNodes = execution.nodeStatuses.filter(s => s.status === 'skipped');\n const totalProcessed = completedNodes.length + skippedNodes.length;\n\n if (failedNodes.length > 0) {\n execution.status = 'failed';\n this.logger.log(`\u274C Workflow failed - ${failedNodes.length} nodes failed`);\n } else if (totalProcessed === workflow.nodes.length) {\n execution.status = 'completed';\n if (skippedNodes.length > 0) {\n this.logger.log(`\u2705 Workflow completed successfully - ${completedNodes.length} nodes executed, ${skippedNodes.length} skipped (flow control)`);\n } else {\n this.logger.log(`\u2705 Workflow completed successfully - all ${completedNodes.length} nodes executed`);\n }\n } else {\n execution.status = 'failed';\n this.logger.log(`\u26A0\uFE0F Workflow incomplete - ${totalProcessed}/${workflow.nodes.length} nodes processed (${completedNodes.length} completed, ${skippedNodes.length} skipped)`);\n }\n\n // Process workflow output if defined (support both 'output' and 'outputs' keys)\n const workflowOutput = workflow. output || (workflow as any).outputs;\n if (workflowOutput) {\n try {\n this.logger.log(`\\n\uD83D\uDCE4 Processing workflow output...`);\n execution.output = this.resolveParameters(workflowOutput, context);\n this.logger.log(` Output resolved successfully`);\n } catch (error: any) {\n this.logger.error(`\u26A0\uFE0F Failed to resolve workflow output: ${error.message}`);\n execution.output = { error: `Failed to resolve output: ${error.message}` };\n }\n }\n\n // Emit execution completed/failed event\n emitStreamEvent({\n type: execution.status === 'completed' ? 'execution_completed' : 'execution_failed',\n status: execution.status as any,\n output: execution.output\n });\n\n } catch (error: any) {\n this.logger.error(`\u274C Workflow execution failed: ${error.message}`);\n this.logger.error(error.stack);\n execution.status = 'failed';\n execution.results.push({\n nodeId: 'workflow',\n success: false,\n error: error.message,\n timestamp: new Date(),\n duration: 0,\n });\n\n // Emit execution failed event\n emitStreamEvent({\n type: 'execution_failed',\n status: 'failed',\n error: error.message\n });\n } finally {\n execution.endTime = new Date();\n execution.currentNode = undefined;\n this.logger.log(`\\n\u2705 Workflow execution completed: ${execution.status}`);\n }\n\n return execution;\n }\n\n /**\n * Find all webhook trigger nodes in the workflow\n */\n private findWebhookTriggers(nodes: WorkflowNode[]): WebhookTriggerInfo[] {\n return nodes\n .filter(node => this.isWebhookTriggerNode(node))\n .map(node => triggerHelper.getWebhookConfig(node));\n }\n\n /**\n * Check if a node is a webhook trigger\n */\n private isWebhookTriggerNode(node: WorkflowNode): boolean {\n return triggerHelper.isWebhookTrigger(node);\n }\n\n /**\n * Handle webhook trigger execution - waits for webhook to be received\n * Requires a webhookHandler to be passed (typically provided by the server layer)\n */\n private async handleWebhookTrigger(\n node: WorkflowNode,\n context: Record<string, any>,\n execution: WorkflowExecution,\n webhookHandler: IWebhookHandler,\n timeout?: number\n ): Promise<ExecutionResult> {\n const startTime = Date.now();\n const result: ExecutionResult = {\n nodeId: node.id,\n success: false,\n timestamp: new Date(),\n duration: 0,\n };\n\n try {\n const workflowId = execution.workflowId;\n this.logger.log(`\uD83D\uDD14 Waiting for webhook for workflow ${workflowId}, node ${node.id}`);\n\n // Wait for the webhook to be triggered (with workflow ID)\n const webhookPayload = await webhookHandler.waitForWebhook(node.id, timeout || 300000, workflowId);\n\n this.logger.log(`\u2705 Webhook received for workflow ${workflowId}, node ${node.id}`);\n\n // Execute the webhook trigger handler\n const triggerResult = await triggerHelper.executeWebhookTrigger(\n node.id,\n webhookPayload.payload,\n webhookPayload.headers,\n webhookPayload.query\n );\n\n if (triggerResult.success) {\n result.success = true;\n result.result = triggerResult.output?.[0] || webhookPayload;\n this.logger.log(`\u2705 Webhook trigger ${node.id} executed successfully`);\n } else {\n result.success = false;\n result.error = triggerResult.message || 'Webhook trigger execution failed';\n }\n\n } catch (error: any) {\n this.logger.error(`\u274C Webhook trigger ${node.id} failed: ${error.message}`);\n result.success = false;\n result.error = error.message;\n }\n\n result.duration = Date.now() - startTime;\n execution.results.push(result);\n\n return result;\n }\n\n /**\n * Build dependency map from workflow nodes and edges\n * Now includes detailed edge information for flow control\n */\n private buildDependencyMap(nodes: WorkflowNode[], edges: WorkflowEdge[]): Map<string, NodeDependencies> {\n const dependencyMap = new Map<string, NodeDependencies>();\n\n // Initialize dependency map for all nodes\n nodes.forEach(node => {\n dependencyMap.set(node.id, {\n nodeId: node.id,\n dependsOn: [],\n optionalDependsOn: [],\n dependencyFor: [],\n incomingEdges: [], // Track detailed edge info for flow control\n });\n });\n\n // Build dependency relationships from edges\n (edges || []).forEach(edge => {\n const sourceDeps = dependencyMap.get(edge.source);\n const targetDeps = dependencyMap.get(edge.target);\n\n if (sourceDeps && targetDeps) {\n // Target depends on source - check if optional\n if (edge.optional) {\n targetDeps.optionalDependsOn.push(edge.source);\n } else {\n targetDeps.dependsOn.push(edge.source);\n }\n // Source is a dependency for target\n sourceDeps.dependencyFor.push(edge.target);\n \n // Store detailed edge info for flow control\n targetDeps.incomingEdges!.push({\n sourceNodeId: edge.source,\n sourceHandle: edge.sourceHandle,\n targetHandle: edge.targetHandle,\n optional: edge.optional,\n });\n }\n });\n\n return dependencyMap;\n }\n\n /**\n * Check if there are any runnable nodes\n */\n private hasRunnableNodes(nodeStatuses: NodeExecutionStatus[], dependencies: Map<string, NodeDependencies>): boolean {\n return nodeStatuses.some(status =>\n status.status === 'pending' && this.areAllDependenciesSatisfied(status.nodeId, nodeStatuses, dependencies)\n );\n }\n\n /**\n * Find all nodes that can be executed (no pending dependencies)\n */\n private findRunnableNodes(nodeStatuses: NodeExecutionStatus[], dependencies: Map<string, NodeDependencies>): string[] {\n return nodeStatuses\n .filter(status =>\n status.status === 'pending' &&\n this.areAllDependenciesSatisfied(status.nodeId, nodeStatuses, dependencies)\n )\n .map(status => status.nodeId);\n }\n\n /**\n * Check if all dependencies for a node are satisfied (completed or skipped)\n * For required dependencies: ALL must be completed or skipped\n * For optional dependencies: ANY one being completed/skipped is sufficient (OR logic)\n * Note: 'skipped' nodes are treated as satisfied for dependency purposes\n */\n private areAllDependenciesSatisfied(nodeId: string, nodeStatuses: NodeExecutionStatus[], dependencies: Map<string, NodeDependencies>): boolean {\n const nodeDeps = dependencies.get(nodeId);\n if (!nodeDeps) {\n return true; // No dependencies info\n }\n \n const hasRequiredDeps = nodeDeps.dependsOn.length > 0;\n const hasOptionalDeps = nodeDeps.optionalDependsOn.length > 0;\n \n // Helper to check if a node status is \"done\" (completed or skipped)\n const isDone = (status: NodeExecutionStatus['status'] | undefined) => \n status === 'completed' || status === 'skipped';\n \n // If no dependencies at all, node can run\n if (!hasRequiredDeps) {\n return true;\n }\n\n // Check required dependencies - ALL must be completed or skipped\n const allRequiredSatisfied = nodeDeps.dependsOn.every(depNodeId => {\n const depStatus = nodeStatuses.find(s => s.nodeId === depNodeId);\n return isDone(depStatus?.status);\n });\n\n // If has required deps and they're not all satisfied, can't run\n if (hasRequiredDeps && !allRequiredSatisfied) {\n return false;\n }\n\n // Check optional dependencies - ANY one being completed/skipped is sufficient\n if (hasOptionalDeps) {\n const anyOptionalSatisfied = nodeDeps.optionalDependsOn.some(depNodeId => {\n const depStatus = nodeStatuses.find(s => s.nodeId === depNodeId);\n return isDone(depStatus?.status);\n });\n \n // If only optional deps exist, need at least one satisfied\n if (!hasRequiredDeps) {\n return anyOptionalSatisfied;\n }\n // If both required and optional exist, required must all be done, \n // and at least one optional must be done\n return allRequiredSatisfied && anyOptionalSatisfied;\n }\n\n // Only required deps, and they're all satisfied\n return allRequiredSatisfied;\n }\n\n /**\n * Check if a node should be skipped due to flow control from upstream nodes.\n * Flow control nodes (like bit-if) can specify which branches are activated.\n * Nodes connected via non-activated branches should be skipped.\n * \n * @returns 'execute' if the node should execute, 'skip' if it should be skipped\n */\n private checkFlowControl(\n nodeId: string,\n dependencies: Map<string, NodeDependencies>,\n context: Record<string, any>\n ): 'execute' | 'skip' {\n const nodeDeps = dependencies.get(nodeId);\n if (!nodeDeps || !nodeDeps.incomingEdges?.length) {\n return 'execute'; // No incoming edges, execute normally\n }\n\n // Check each incoming edge for flow control\n for (const edge of nodeDeps.incomingEdges) {\n const sourceResult = context[edge.sourceNodeId];\n if (!sourceResult) {\n continue; // Source hasn't executed yet or has no result\n }\n\n // Check if the source node returned flow control metadata\n // Can be in _flowControl field or directly in the result\n const flowControl: FlowControlMetadata | undefined = \n sourceResult._flowControl || \n (sourceResult.controlsFlow ? sourceResult : undefined);\n\n if (!flowControl?.controlsFlow) {\n continue; // Source doesn't control flow\n }\n\n // Source controls flow - check if this edge's sourceHandle is activated\n const { activeBranches, skipBranches } = flowControl;\n const edgeHandle = edge.sourceHandle || 'default';\n\n if (activeBranches && activeBranches.length > 0) {\n // If activeBranches is specified, only those branches execute\n if (!activeBranches.includes(edgeHandle)) {\n this.logger.log(`\u23ED\uFE0F Skipping node ${nodeId}: branch \"${edgeHandle}\" not in activeBranches [${activeBranches.join(', ')}]`);\n return 'skip';\n }\n } else if (skipBranches && skipBranches.length > 0) {\n // If skipBranches is specified, those branches are skipped\n if (skipBranches.includes(edgeHandle)) {\n this.logger.log(`\u23ED\uFE0F Skipping node ${nodeId}: branch \"${edgeHandle}\" in skipBranches [${skipBranches.join(', ')}]`);\n return 'skip';\n }\n }\n }\n\n return 'execute';\n }\n\n /**\n * Update node execution status\n */\n private updateNodeStatus(\n execution: WorkflowExecution,\n nodeId: string,\n status: NodeExecutionStatus['status'],\n additionalData?: Partial<NodeExecutionStatus>\n ): void {\n const nodeStatus = execution.nodeStatuses.find(s => s.nodeId === nodeId);\n if (nodeStatus) {\n nodeStatus.status = status;\n if (additionalData) {\n Object.assign(nodeStatus, additionalData);\n }\n }\n }\n\n /**\n * Execute a single workflow node\n */\n private async executeNode(\n node: WorkflowNode,\n context: Record<string, any>,\n execution: WorkflowExecution\n ): Promise<ExecutionResult> {\n const startTime = Date.now();\n const result: ExecutionResult = {\n nodeId: node.id,\n success: false,\n timestamp: new Date(),\n duration: 0,\n };\n let fullParams;\n try {\n \n // Resolve dynamic parameters using context\n const resolvedParams = this.resolveParameters(node.data.params || {}, context);\n // Resolve credentials as well (they may contain {{process.env.XXX}} templates)\n const resolvedCredentials = node.data.credentials\n ? this.resolveParameters(node.data.credentials, context)\n : undefined;\n\n \n // Add additional node data to params\n fullParams = {\n ...resolvedParams,\n ...(node.data.resource && { resource: node.data.resource }),\n ...(node.data.operation && { operation: node.data.operation }),\n ...(resolvedCredentials && { credentials: resolvedCredentials })\n };\n\n // Execute based on framework\n let nodeResult: any;\n switch (node.data.framework) {\n case 'activepieces':\n if (triggerHelper.isActivepiecesTrigger(node)) {\n const triggerResult = await triggerHelper.executeActivepiecesTrigger({\n moduleDefinition: {\n framework: node.data.framework,\n source: (node.data.source as 'github' | 'npm') || 'npm',\n repository: node.data.module || 'unknown',\n },\n triggerName: node.data.operation || 'unknown',\n input: fullParams,\n payload: context.triggerPayload || context.webhookPayload || {},\n webhookUrl: context.webhookUrl,\n });\n\n if (!triggerResult.success) {\n throw new Error(triggerResult.message || 'Trigger execution failed');\n }\n nodeResult = triggerResult.output;\n } else {\n // Regular action execution\n const output = await executeActivepiecesModule({ source: node.data.source!, framework: node.data.framework, moduleName: node.data.module || 'unknown', params: fullParams });\n nodeResult = output.result;\n }\n break;\n case 'n8n':\n // Pass full execution params including source\n nodeResult = await executeN8nModule({\n framework: 'n8n',\n source: node.data.source || 'npm',\n moduleName: node.data.module || 'unknown',\n params: fullParams\n });\n break;\n case 'script':\n nodeResult = await executeScriptModule({\n framework: 'script',\n source: (node.data.source as 'local' | 'hub' | 'inline') || 'local',\n moduleName: node.data.module || 'unknown',\n params: fullParams,\n script: {\n type: fullParams.type || 'script',\n language: fullParams.language || 'deno',\n content: fullParams.script,\n },\n });\n break;\n case 'bits':\n // Bits framework - independent of activepieces dependencies\n if (bitsTriggerHelper.isBitsTrigger(node)) {\n const triggerResult = await bitsTriggerHelper.executeBitsTrigger({\n moduleDefinition: {\n framework: node.data.framework,\n source: (node.data.source as 'github' | 'npm') || 'npm',\n repository: node.data.module || 'unknown',\n },\n triggerName: node.data.operation || 'unknown',\n input: fullParams,\n payload: context.triggerPayload || context.webhookPayload || {},\n webhookUrl: context.webhookUrl,\n executor: this,\n workflowId: execution.workflowId,\n nodeId: node.id,\n });\n\n if (!triggerResult.success) {\n throw new Error(triggerResult.message || 'Trigger execution failed');\n }\n nodeResult = triggerResult.output;\n } else {\n // Regular action execution\n const output = await executeBitsModule({\n source: node.data.source!,\n framework: node.data.framework,\n moduleName: node.data.module || 'unknown',\n params: fullParams,\n logger: this.logger,\n workflowId: execution.workflowId,\n nodeId: node.id,\n executionId: execution.id,\n executor: this,\n // Pass per-user OAuth tokens from context (for multi-user server mode)\n oauthTokens: context._oauthTokens,\n });\n nodeResult = output.result;\n }\n break;\n default:\n throw new Error(`Unsupported framework: ${node.data.framework}`);\n }\n\n result.success = true;\n result.result = nodeResult;\n\n this.logger.info(`Node ${node.id} executed successfully`);\n\n } catch (error: any) {\n this.logger.error(`Node ${node.id} failed`, { \n error: error.message, \n inputs: fullParams \n });\n result.success = false;\n result.error = error.message;\n }\n\n result.duration = Date.now() - startTime;\n execution.results.push(result);\n\n return result;\n }\n\n\n\n /**\n * Resolve dynamic parameters using context\n */\n private resolveParameters(params: Record<string, any>, context: Record<string, any>): Record<string, any> {\n const resolved: Record<string, any> = {};\n\n for (const [key, value] of Object.entries(params)) {\n if (typeof value === 'string' && value.startsWith('{{') && value.endsWith('}}')) {\n // Template variable like {{previous_result.id}}\n const expression = value.slice(2, -2).trim();\n resolved[key] = this.evaluateExpression(expression, context);\n } else if (typeof value === 'string' && value.includes('{{') && value.includes('}}')) {\n // Handle mixed templates like \"{{step_abc.value}}_suffix\"\n // If an object, serialize it\n let resolvedString = value;\n const templateRegex = /\\{\\{([^}]+)\\}\\}/g;\n let match;\n while ((match = templateRegex.exec(value)) !== null) {\n const expression = match[1].trim();\n const evaluatedValue = this.evaluateExpression(expression, context);\n if (typeof evaluatedValue === 'object') {\n // If the evaluated value is an object, serialize it to JSON\n this.logger.warn(`\u26A0\uFE0F Evaluated value for expression \"${expression}\" is an object, serializing to JSON string`);\n resolvedString = resolvedString.replace(match[0], JSON.stringify(evaluatedValue));\n continue;\n }\n resolvedString = resolvedString.replace(match[0], String(evaluatedValue));\n }\n resolved[key] = resolvedString;\n } else if (typeof value === 'object' && value !== null && !Array.isArray(value)) {\n resolved[key] = this.resolveParameters(value, context);\n } else if (Array.isArray(value)) {\n resolved[key] = value.map(item => {\n if (typeof item === 'string' && item.startsWith('{{') && item.endsWith('}}')) {\n // Template variable in array\n const expression = item.slice(2, -2).trim();\n return this.evaluateExpression(expression, context);\n } else if (typeof item === 'string' && item.includes('{{') && item.includes('}}')) {\n // Mixed template in array\n let resolvedString = item;\n const templateRegex = /\\{\\{([^}]+)\\}\\}/g;\n let match;\n while ((match = templateRegex.exec(item)) !== null) {\n const expression = match[1].trim();\n const evaluatedValue = this.evaluateExpression(expression, context);\n resolvedString = resolvedString.replace(match[0], String(evaluatedValue));\n }\n return resolvedString;\n } else if (typeof item === 'object' && item !== null) {\n return this.resolveParameters(item, context);\n }\n return item;\n });\n } else {\n resolved[key] = value;\n }\n }\n\n return resolved;\n }\n\n /**\n * Evaluate a JavaScript expression in the given context\n * Supports default values with || operator: {{habits.input.value || 'default'}}\n */\n private evaluateExpression(expression: string, context: Record<string, any>): any {\n try {\n // Handle default value syntax: expression || 'default' or expression || \"default\"\n // Match || followed by a quoted string or number\n const defaultMatch = expression.match(/^(.+?)\\s*\\|\\|\\s*(['\"`])(.*)(\\2)$/);\n if (defaultMatch) {\n const [, mainExpr, , defaultValue] = defaultMatch;\n const result = this.evaluateExpression(mainExpr.trim(), context);\n // Return default if result is undefined, null, empty string, or the original expression (failed evaluation)\n if (result === undefined || result === null || result === '' || result === mainExpr.trim()) {\n return defaultValue;\n }\n return result;\n }\n\n // Handle default value with unquoted fallback (e.g., number or boolean)\n const defaultUnquotedMatch = expression.match(/^(.+?)\\s*\\|\\|\\s*([^'\"`].*)$/);\n if (defaultUnquotedMatch) {\n const [, mainExpr, defaultValue] = defaultUnquotedMatch;\n const result = this.evaluateExpression(mainExpr.trim(), context);\n if (result === undefined || result === null || result === '' || result === mainExpr.trim()) {\n // Try to parse the default as number/boolean\n const trimmedDefault = defaultValue.trim();\n if (trimmedDefault === 'true') return true;\n if (trimmedDefault === 'false') return false;\n if (trimmedDefault === 'null') return null;\n const num = Number(trimmedDefault);\n if (!isNaN(num)) return num;\n return trimmedDefault;\n }\n return result;\n }\n\n // Handle habits.env. variables (special case for environment variables)\n // Allow access to any environment variable via habits.env.VAR_NAME\n if (expression.startsWith('habits.env.')) {\n // Strip 'habits.env.' prefix to get the actual env var name\n const envVar = expression.slice('habits.env.'.length);\n // Check this.env first (platform-agnostic), fall back to process.env for Node.js\n const value = this.env[envVar] ?? (typeof process !== 'undefined' ? process.env?.[envVar] : undefined);\n if (value === undefined) {\n this.logger.warn(`\u26A0\uFE0F Environment variable ${envVar} is not set`);\n }\n return value || '';\n }\n\n // Handle habits.function.* - utility functions\n if (expression.startsWith('habits.function.')) {\n const funcCall = expression.slice('habits.function.'.length);\n return this.evaluateHabitsFunction(funcCall);\n }\n\n // Handle habits.context.* - workflow execution context\n if (expression.startsWith('habits.context.')) {\n const contextKey = expression.slice('habits.context.'.length);\n const habitsContext = context.habits?.context || {};\n if (contextKey in habitsContext) {\n return habitsContext[contextKey];\n }\n this.logger.warn(`\u26A0\uFE0F Context key '${contextKey}' not found`);\n return '';\n }\n\n // Handle habits.header.* - HTTP request headers (alias for habits.headers.*)\n if (expression.startsWith('habits.header.')) {\n const headerName = expression.slice('habits.header.'.length).toLowerCase();\n const headers = context.habits?.headers || {};\n // Headers are case-insensitive, find the matching header\n for (const [key, value] of Object.entries(headers)) {\n if (key.toLowerCase() === headerName) {\n return value;\n }\n }\n this.logger.warn(`\u26A0\uFE0F Header '${headerName}' not found`);\n return '';\n }\n\n // Handle simple property access like habits.input.userId or step_abc.value\n // Also supports array indexing like result[0].base64\n if (expression.includes('.') || expression.includes('[')) {\n // Parse the expression to handle both dot notation and array indexing\n // e.g., \"text-to-speech.result[0].base64\" -> [\"text-to-speech\", \"result\", \"0\", \"base64\"]\n const parts: string[] = [];\n let current = '';\n let i = 0;\n while (i < expression.length) {\n const char = expression[i];\n if (char === '.') {\n if (current) parts.push(current);\n current = '';\n } else if (char === '[') {\n if (current) parts.push(current);\n current = '';\n // Find the closing bracket\n i++;\n while (i < expression.length && expression[i] !== ']') {\n current += expression[i];\n i++;\n }\n if (current) parts.push(current);\n current = '';\n } else {\n current += char;\n }\n i++;\n }\n if (current) parts.push(current);\n\n let result = context;\n for (const part of parts) {\n // Handle numeric indices for arrays\n const index = /^\\d+$/.test(part) ? parseInt(part, 10) : part;\n\n if (result && typeof result === 'object' && (Array.isArray(result) ? index in result : part in result)) {\n result = (result as any)[index];\n } else {\n throw new Error(`Property ${part} not found`);\n }\n }\n return result;\n }\n\n // Handle direct context access\n if (expression in context) {\n return context[expression];\n }\n\n // Fallback to Function evaluation\n const func = new Function(...Object.keys(context), `return ${expression}`);\n return func(...Object.values(context));\n } catch (error: any) {\n this.logger.warn(`\u26A0\uFE0F Failed to evaluate expression: ${expression} - ${error.message}`);\n return expression; // Return original if evaluation fails\n }\n }\n\n /**\n * Evaluate a condition expression\n */\n private evaluateCondition(condition: string, context: Record<string, any>): boolean {\n try {\n return Boolean(this.evaluateExpression(condition, context));\n } catch {\n return false;\n }\n }\n\n // TODO: Allow functions to use context and node outputs\n // TODO: Implement a way to register custom functions that can be used in habits.function.* expressions, with access to context and other utilities\n /**\n * Evaluate habits.function.* utility functions\n * Supported functions:\n * - date() - Returns current date in ISO format\n * - now() - Alias for date()\n * - timestamp() - Returns Unix timestamp in milliseconds\n * - uuid() - Generates a random UUID\n * - random(min, max) - Generates random number in range\n * - stringify(value) - Converts value to JSON string (value should be context path)\n */\n private evaluateHabitsFunction(funcCall: string): any {\n // Parse function name and arguments\n const funcMatch = funcCall.match(/^(\\w+)\\((.*)\\)$/);\n if (!funcMatch) {\n this.logger.warn(`\u26A0\uFE0F Invalid function call: ${funcCall}`);\n return '';\n }\n\n const [, funcName, argsStr] = funcMatch;\n const args = argsStr ? argsStr.split(',').map(a => a.trim()) : [];\n\n switch (funcName) {\n case 'date':\n case 'now':\n return new Date().toISOString();\n\n case 'timestamp':\n return Date.now();\n\n case 'uuid':\n return uuidv4();\n\n case 'random': {\n const min = args[0] ? parseFloat(args[0]) : 0;\n const max = args[1] ? parseFloat(args[1]) : 1;\n return Math.random() * (max - min) + min;\n }\n\n case 'randomInt': {\n const min = args[0] ? parseInt(args[0], 10) : 0;\n const max = args[1] ? parseInt(args[1], 10) : 100;\n return Math.floor(Math.random() * (max - min + 1)) + min;\n }\n\n case 'stringify':\n // For stringify, the arg should be a value in context, but without context here\n // we'll just return the stringified arg itself\n if (args[0]) {\n try {\n return JSON.stringify(args[0]);\n } catch {\n return String(args[0]);\n }\n }\n return '';\n\n default:\n this.logger.warn(`\u26A0\uFE0F Unknown function: ${funcName}`);\n return '';\n }\n }\n\n /**\n * Get execution status\n */\n getExecution(executionId: string): WorkflowExecution | undefined {\n return this.executions.get(executionId);\n }\n\n /**\n * List all executions\n */\n listExecutions(): WorkflowExecution[] {\n return Array.from(this.executions.values());\n }\n\n /**\n * Cancel a running execution\n */\n cancelExecution(executionId: string): boolean {\n const execution = this.executions.get(executionId);\n if (execution && execution.status === 'running') {\n execution.status = 'cancelled';\n execution.endTime = new Date();\n return true;\n }\n return false;\n }\n}\n", "/**\n * Runtime detection for platform bindings\n * \n * Detects whether we're running in a Tauri environment or Node.js.\n * Uses globalThis.__TAURI__ for Tauri plugin access (requires withGlobalTauri: true in tauri.conf.json).\n */\n\n// Import types from Tauri packages (type-only imports, no runtime dependency)\nimport type * as TauriFsTypes from '@tauri-apps/plugin-fs';\nimport type * as TauriShellTypes from '@tauri-apps/plugin-shell';\nimport type * as TauriProcessTypes from '@tauri-apps/plugin-process';\nimport type * as TauriHttpTypes from '@tauri-apps/plugin-http';\n\n/**\n * Tauri filesystem plugin type\n */\nexport type TauriFsPlugin = typeof TauriFsTypes;\n\n/**\n * Tauri shell plugin type\n */\nexport type TauriShellPlugin = typeof TauriShellTypes;\n\n/**\n * Tauri process plugin type\n */\nexport type TauriProcessPlugin = typeof TauriProcessTypes;\n\n/**\n * Tauri HTTP plugin type\n */\nexport type TauriHttpPlugin = typeof TauriHttpTypes;\n\n/**\n * Tauri global interface (available when withGlobalTauri: true)\n */\nexport interface TauriGlobal {\n convertFileSrc?: (path: string) => string;\n fs?: TauriFsPlugin;\n shell?: TauriShellPlugin;\n process?: TauriProcessPlugin;\n http?: TauriHttpPlugin;\n [key: string]: unknown;\n}\n\n/**\n * Check if we're running in a Tauri environment\n * \n * Detection strategy:\n * 1. Check for globalThis.__TAURI__ object (Tauri v2 with withGlobalTauri)\n * 2. Check for globalThis.__TAURI_INTERNALS__ (Tauri v2 internals)\n * \n * @returns true if running in Tauri, false if in Node.js or browser without Tauri\n */\nexport function isTauri(): boolean {\n const g = globalThis as any;\n return !!(g.__TAURI__ || g.__TAURI_INTERNALS__);\n}\n\n/**\n * Get the Tauri global object\n * \n * @returns The __TAURI__ global or null if not in Tauri\n */\nexport function getTauri(): TauriGlobal | null {\n if (!isTauri()) return null;\n return (globalThis as any).__TAURI__ as TauriGlobal;\n}\n\n/**\n * Get a Tauri plugin from the global object\n * \n * @param pluginName - Name of the plugin (e.g., 'fs', 'shell', 'process')\n * @throws Error if plugin is not available\n */\nexport function getTauriPlugin<K extends keyof TauriGlobal>(pluginName: K): NonNullable<TauriGlobal[K]> {\n const tauri = getTauri();\n if (!tauri) {\n throw new Error(`Tauri is not available. Make sure withGlobalTauri is enabled in tauri.conf.json.`);\n }\n \n const plugin = tauri[pluginName];\n if (!plugin) {\n throw new Error(`Tauri plugin '${pluginName}' is not available. Make sure the plugin is installed and enabled.`);\n }\n \n return plugin as NonNullable<TauriGlobal[K]>;\n}\n\n/**\n * Check if we're running in Node.js\n * \n * @returns true if running in Node.js environment\n */\nexport function isNode(): boolean {\n return typeof process !== 'undefined' && \n process.versions != null && \n process.versions.node != null;\n}\n\n/**\n * Check if we're running in a browser (without Tauri)\n * \n * @returns true if running in browser without Tauri\n */\nexport function isBrowser(): boolean {\n return typeof window !== 'undefined' && !isTauri();\n}\n\n/**\n * Get the current runtime environment\n * \n * @returns 'tauri' | 'node' | 'browser'\n */\nexport function getRuntime(): 'tauri' | 'node' | 'browser' {\n if (isTauri()) {\n return 'tauri';\n }\n if (isNode()) {\n return 'node';\n }\n return 'browser';\n}\n\n/**\n * Assert that we're running in a supported environment for the given feature\n * \n * @param feature - Name of the feature requiring this check\n * @param supportedRuntimes - List of supported runtimes\n * @throws Error if current runtime is not supported\n */\nexport function assertRuntime(feature: string, supportedRuntimes: ('tauri' | 'node' | 'browser')[]): void {\n const runtime = getRuntime();\n if (!supportedRuntimes.includes(runtime)) {\n throw new Error(\n `${feature} is not supported in ${runtime} environment. ` +\n `Supported environments: ${supportedRuntimes.join(', ')}`\n );\n }\n}\n", "/**\n * Filesystem binding\n * \n * Provides cross-platform filesystem operations that work in both Node.js and Tauri.\n * In Node.js, delegates to the native 'fs' module.\n * In Tauri, uses globalThis.__TAURI__.fs (requires withGlobalTauri: true).\n */\n\nimport { isTauri, isNode, assertRuntime, getTauriPlugin, type TauriFsPlugin } from './runtime';\n\n// Conditionally import modules\nlet nodeFs: typeof import('fs') | null = null;\n\n// Initialize Node.js fs if available\nif (isNode()) {\n // eslint-disable-next-line @typescript-eslint/no-var-requires\n nodeFs = require('fs');\n}\n\n/**\n * Get Tauri fs plugin from globalThis.__TAURI__\n */\nfunction getTauriFs(): TauriFsPlugin {\n return getTauriPlugin('fs');\n}\n\n// ============================================================================\n// Async Operations\n// ============================================================================\n\n/**\n * Read a file as text\n * \n * @param path - Path to the file\n * @param encoding - Text encoding (default: 'utf-8')\n * @returns File contents as string\n */\nexport async function readFile(path: string, encoding: BufferEncoding = 'utf-8'): Promise<string> {\n if (isTauri()) {\n const fs = getTauriFs();\n return await fs.readTextFile(path);\n }\n \n if (nodeFs) {\n return nodeFs.promises.readFile(path, { encoding });\n }\n \n throw new Error('readFile is not supported in this environment');\n}\n\n/**\n * Read a file as binary data\n * \n * @param path - Path to the file\n * @returns File contents as Uint8Array\n */\nexport async function readBinaryFile(path: string): Promise<Uint8Array> {\n if (isTauri()) {\n const fs = getTauriFs();\n return await fs.readFile(path);\n }\n \n if (nodeFs) {\n const buffer = await nodeFs.promises.readFile(path);\n return new Uint8Array(buffer);\n }\n \n throw new Error('readBinaryFile is not supported in this environment');\n}\n\n/**\n * Write text to a file\n * \n * @param path - Path to the file\n * @param contents - Text content to write\n */\nexport async function writeFile(path: string, contents: string): Promise<void> {\n if (isTauri()) {\n const fs = getTauriFs();\n await fs.writeTextFile(path, contents);\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.writeFile(path, contents, 'utf-8');\n return;\n }\n \n throw new Error('writeFile is not supported in this environment');\n}\n\n/**\n * Write binary data to a file\n * \n * @param path - Path to the file\n * @param contents - Binary content to write\n */\nexport async function writeBinaryFile(path: string, contents: Uint8Array): Promise<void> {\n if (isTauri()) {\n const fs = getTauriFs();\n await fs.writeFile(path, contents);\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.writeFile(path, Buffer.from(contents));\n return;\n }\n \n throw new Error('writeBinaryFile is not supported in this environment');\n}\n\n/**\n * Check if a file or directory exists\n * \n * @param path - Path to check\n * @returns true if the path exists\n */\nexport async function exists(path: string): Promise<boolean> {\n if (isTauri()) {\n const fs = getTauriFs();\n return await fs.exists(path);\n }\n \n if (nodeFs) {\n try {\n await nodeFs.promises.access(path);\n return true;\n } catch {\n return false;\n }\n }\n \n throw new Error('exists is not supported in this environment');\n}\n\n/**\n * Create a directory\n * \n * @param path - Path to create\n * @param options - Options for directory creation\n */\nexport async function mkdir(path: string, options?: { recursive?: boolean }): Promise<void> {\n if (isTauri()) {\n const fs = getTauriFs();\n await fs.mkdir(path, { recursive: options?.recursive });\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.mkdir(path, { recursive: options?.recursive });\n return;\n }\n \n throw new Error('mkdir is not supported in this environment');\n}\n\n/**\n * Remove a file\n * \n * @param path - Path to remove\n */\nexport async function remove(path: string): Promise<void> {\n if (isTauri()) {\n const fs = getTauriFs();\n await fs.remove(path);\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.unlink(path);\n return;\n }\n \n throw new Error('remove is not supported in this environment');\n}\n\n/**\n * Remove a directory\n * \n * @param path - Path to remove\n * @param options - Options for removal\n */\nexport async function rmdir(path: string, options?: { recursive?: boolean }): Promise<void> {\n if (isTauri()) {\n const fs = getTauriFs();\n await fs.remove(path, { recursive: options?.recursive });\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.rm(path, { recursive: options?.recursive });\n return;\n }\n \n throw new Error('rmdir is not supported in this environment');\n}\n\n/**\n * Directory entry info\n */\nexport interface DirEntry {\n name: string;\n isDirectory: boolean;\n isFile: boolean;\n isSymlink: boolean;\n}\n\n/**\n * Read a directory\n * \n * @param path - Path to read\n * @returns Array of directory entries\n */\nexport async function readDir(path: string): Promise<DirEntry[]> {\n if (isTauri()) {\n const fs = getTauriFs();\n const entries = await fs.readDir(path);\n return entries.map(entry => ({\n name: entry.name,\n isDirectory: entry.isDirectory,\n isFile: entry.isFile,\n isSymlink: entry.isSymlink,\n }));\n }\n \n if (nodeFs) {\n const entries = await nodeFs.promises.readdir(path, { withFileTypes: true });\n return entries.map(entry => ({\n name: entry.name,\n isDirectory: entry.isDirectory(),\n isFile: entry.isFile(),\n isSymlink: entry.isSymbolicLink(),\n }));\n }\n \n throw new Error('readDir is not supported in this environment');\n}\n\n/**\n * Copy a file\n * \n * @param src - Source path\n * @param dest - Destination path\n */\nexport async function copyFile(src: string, dest: string): Promise<void> {\n if (isTauri()) {\n const fs = getTauriFs();\n await fs.copyFile(src, dest);\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.copyFile(src, dest);\n return;\n }\n \n throw new Error('copyFile is not supported in this environment');\n}\n\n/**\n * Rename/move a file or directory\n * \n * @param oldPath - Current path\n * @param newPath - New path\n */\nexport async function rename(oldPath: string, newPath: string): Promise<void> {\n if (isTauri()) {\n const fs = getTauriFs();\n await fs.rename(oldPath, newPath);\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.rename(oldPath, newPath);\n return;\n }\n \n throw new Error('rename is not supported in this environment');\n}\n\n/**\n * File/directory stats (Node.js-compatible interface with methods)\n */\nexport interface FileStats {\n /** Check if this is a regular file */\n isFile(): boolean;\n /** Check if this is a directory */\n isDirectory(): boolean;\n /** Check if this is a symbolic link */\n isSymbolicLink(): boolean;\n /** File size in bytes */\n size: number;\n /** Last modified time */\n mtime: Date | null;\n /** Last accessed time */\n atime: Date | null;\n /** Creation time */\n ctime: Date | null;\n}\n\n/**\n * Create a FileStats object with methods\n */\nfunction createFileStats(data: {\n isFile: boolean;\n isDirectory: boolean;\n isSymlink: boolean;\n size: number;\n mtime: Date | null;\n atime: Date | null;\n ctime: Date | null;\n}): FileStats {\n return {\n isFile: () => data.isFile,\n isDirectory: () => data.isDirectory,\n isSymbolicLink: () => data.isSymlink,\n size: data.size,\n mtime: data.mtime,\n atime: data.atime,\n ctime: data.ctime,\n };\n}\n\n/**\n * Get file/directory stats\n * \n * @param path - Path to stat\n * @returns File stats\n */\nexport async function stat(path: string): Promise<FileStats> {\n if (isTauri()) {\n const fs = getTauriFs();\n const stats = await fs.stat(path);\n return createFileStats({\n isFile: stats.isFile,\n isDirectory: stats.isDirectory,\n isSymlink: stats.isSymlink,\n size: stats.size,\n mtime: stats.mtime ? new Date(stats.mtime) : null,\n atime: stats.atime ? new Date(stats.atime) : null,\n ctime: null, // Tauri doesn't provide ctime\n });\n }\n \n if (nodeFs) {\n const stats = await nodeFs.promises.stat(path);\n return createFileStats({\n isFile: stats.isFile(),\n isDirectory: stats.isDirectory(),\n isSymlink: stats.isSymbolicLink(),\n size: stats.size,\n mtime: stats.mtime,\n atime: stats.atime,\n ctime: stats.ctime,\n });\n }\n \n throw new Error('stat is not supported in this environment');\n}\n\n// ============================================================================\n// Sync Operations (Node.js only)\n// ============================================================================\n\n/**\n * Read a file synchronously (Node.js only)\n * \n * @param path - Path to the file\n * @param encoding - Text encoding (default: 'utf-8')\n * @returns File contents as string\n */\nexport function readFileSync(path: string, encoding: BufferEncoding = 'utf-8'): string {\n assertRuntime('readFileSync', ['node']);\n \n if (nodeFs) {\n return nodeFs.readFileSync(path, { encoding });\n }\n \n throw new Error('readFileSync is not supported in this environment');\n}\n\n/**\n * Write a file synchronously (Node.js only)\n * \n * @param path - Path to the file\n * @param contents - Text content to write\n * @param encoding - Text encoding (default: 'utf-8')\n */\nexport function writeFileSync(path: string, contents: string, encoding: BufferEncoding = 'utf-8'): void {\n assertRuntime('writeFileSync', ['node']);\n \n if (nodeFs) {\n nodeFs.writeFileSync(path, contents, encoding);\n return;\n }\n \n throw new Error('writeFileSync is not supported in this environment');\n}\n\n/**\n * Check if a file or directory exists synchronously (Node.js only)\n * \n * @param path - Path to check\n * @returns true if the path exists\n */\nexport function existsSync(path: string): boolean {\n assertRuntime('existsSync', ['node']);\n \n if (nodeFs) {\n return nodeFs.existsSync(path);\n }\n \n return false;\n}\n\n/**\n * Create a directory synchronously (Node.js only)\n * \n * @param path - Path to create\n * @param options - Options for directory creation\n */\nexport function mkdirSync(path: string, options?: { recursive?: boolean }): void {\n assertRuntime('mkdirSync', ['node']);\n \n if (nodeFs) {\n nodeFs.mkdirSync(path, { recursive: options?.recursive });\n return;\n }\n \n throw new Error('mkdirSync is not supported in this environment');\n}\n\n/**\n * Directory entry with file type methods (for Node.js compatibility)\n */\nexport interface DirentLike {\n name: string;\n isDirectory(): boolean;\n isFile(): boolean;\n isSymbolicLink(): boolean;\n}\n\n/**\n * Read directory synchronously (Node.js only) - returns string[]\n */\nexport function readdirSync(path: string): string[];\n/**\n * Read directory synchronously (Node.js only) - returns DirentLike[] when withFileTypes is true\n */\nexport function readdirSync(path: string, options: { withFileTypes: true }): DirentLike[];\n/**\n * Read directory synchronously (Node.js only) - returns string[] when withFileTypes is false/undefined\n */\nexport function readdirSync(path: string, options: { withFileTypes?: false }): string[];\n/**\n * Read directory synchronously (Node.js only)\n * \n * @param path - Path to read\n * @param options - Options (withFileTypes returns Dirent-like objects)\n * @returns Array of file names or Dirent-like objects\n */\nexport function readdirSync(path: string, options?: { withFileTypes?: boolean }): string[] | DirentLike[] {\n assertRuntime('readdirSync', ['node']);\n \n if (nodeFs) {\n if (options?.withFileTypes) {\n const entries = nodeFs.readdirSync(path, { withFileTypes: true });\n return entries.map(entry => ({\n name: entry.name,\n isDirectory: () => entry.isDirectory(),\n isFile: () => entry.isFile(),\n isSymbolicLink: () => entry.isSymbolicLink(),\n }));\n }\n return nodeFs.readdirSync(path);\n }\n \n throw new Error('readdirSync is not supported in this environment');\n}\n\n/**\n * Copy a file or directory synchronously (Node.js only)\n * \n * @param src - Source path\n * @param dest - Destination path\n * @param options - Copy options\n */\nexport function cpSync(src: string, dest: string, options?: { recursive?: boolean }): void {\n assertRuntime('cpSync', ['node']);\n \n if (nodeFs && typeof (nodeFs as any).cpSync === 'function') {\n (nodeFs as any).cpSync(src, dest, options);\n return;\n }\n \n throw new Error('cpSync is not supported in this environment (requires Node.js 16.7+)');\n}\n\n/**\n * Remove a file or directory synchronously (Node.js only)\n * \n * @param path - Path to remove\n * @param options - Removal options\n */\nexport function rmSync(path: string, options?: { recursive?: boolean; force?: boolean }): void {\n assertRuntime('rmSync', ['node']);\n \n if (nodeFs && typeof (nodeFs as any).rmSync === 'function') {\n (nodeFs as any).rmSync(path, options);\n return;\n }\n \n throw new Error('rmSync is not supported in this environment (requires Node.js 14.14+)');\n}\n\n/**\n * Create a symbolic link synchronously (Node.js only)\n * \n * @param target - Path the symlink points to\n * @param path - Path of the symlink itself\n * @param type - Type of symlink ('file', 'dir', or 'junction' on Windows)\n */\nexport function symlinkSync(target: string, path: string, type?: 'file' | 'dir' | 'junction'): void {\n assertRuntime('symlinkSync', ['node']);\n \n if (nodeFs) {\n nodeFs.symlinkSync(target, path, type);\n return;\n }\n \n throw new Error('symlinkSync is not supported in this environment');\n}\n\n/**\n * Get file stats synchronously without following symlinks (Node.js only)\n * \n * @param path - Path to stat\n * @returns File stats (isSymbolicLink() will return true for symlinks)\n */\nexport function lstatSync(path: string): FileStats {\n assertRuntime('lstatSync', ['node']);\n \n if (nodeFs) {\n const stats = nodeFs.lstatSync(path);\n return createFileStats({\n isFile: stats.isFile(),\n isDirectory: stats.isDirectory(),\n isSymlink: stats.isSymbolicLink(),\n size: stats.size,\n mtime: stats.mtime,\n atime: stats.atime,\n ctime: stats.ctime,\n });\n }\n \n throw new Error('lstatSync is not supported in this environment');\n}\n\n/**\n * Read the target of a symbolic link synchronously (Node.js only)\n * \n * @param path - Path of the symlink\n * @returns The path the symlink points to\n */\nexport function readlinkSync(path: string): string {\n assertRuntime('readlinkSync', ['node']);\n \n if (nodeFs) {\n return nodeFs.readlinkSync(path, 'utf-8');\n }\n \n throw new Error('readlinkSync is not supported in this environment');\n}\n\n/**\n * Get file stats synchronously (Node.js only)\n * \n * @param path - Path to stat\n * @returns File stats\n */\nexport function statSync(path: string): FileStats {\n assertRuntime('statSync', ['node']);\n \n if (nodeFs) {\n const stats = nodeFs.statSync(path);\n return createFileStats({\n isFile: stats.isFile(),\n isDirectory: stats.isDirectory(),\n isSymlink: stats.isSymbolicLink(),\n size: stats.size,\n mtime: stats.mtime,\n atime: stats.atime,\n ctime: stats.ctime,\n });\n }\n \n throw new Error('statSync is not supported in this environment');\n}\n\n// Default export\nexport default {\n readFile,\n readBinaryFile,\n writeFile,\n writeBinaryFile,\n exists,\n mkdir,\n remove,\n rmdir,\n readDir,\n copyFile,\n rename,\n stat,\n readFileSync,\n writeFileSync,\n existsSync,\n mkdirSync,\n readdirSync,\n cpSync,\n rmSync,\n symlinkSync,\n readlinkSync,\n lstatSync,\n statSync,\n};\n", "/**\n * Path utilities binding\n * \n * Provides cross-platform path manipulation that works in both Node.js and Tauri/browser.\n * In Node.js, delegates to the native 'path' module.\n * In Tauri/browser, provides a pure JavaScript implementation.\n */\n\nimport { isNode } from './runtime';\n\n// Conditionally import Node.js path module\nlet nodePath: typeof import('path') | null = null;\n\nif (isNode()) {\n // Dynamic import for Node.js environment\n // eslint-disable-next-line @typescript-eslint/no-var-requires\n nodePath = require('path');\n}\n\n/**\n * Platform-specific path separator\n */\nexport const sep = isNode() && nodePath ? nodePath.sep : '/';\n\n/**\n * Platform-specific path delimiter (for PATH environment variable)\n */\nexport const delimiter = isNode() && nodePath ? nodePath.delimiter : ':';\n\n/**\n * Join path segments together\n * \n * @param segments - Path segments to join\n * @returns Joined path\n */\nexport function join(...segments: string[]): string {\n if (nodePath) {\n return nodePath.join(...segments);\n }\n \n // Browser/Tauri implementation\n const parts: string[] = [];\n \n for (const segment of segments) {\n if (!segment) continue;\n \n // Split by both / and \\\n const segmentParts = segment.split(/[/\\\\]+/);\n \n for (const part of segmentParts) {\n if (part === '..') {\n parts.pop();\n } else if (part !== '.' && part !== '') {\n parts.push(part);\n }\n }\n }\n \n // Preserve leading slash if first segment had one\n const firstSegment = segments.find(s => s);\n const leadingSlash = firstSegment && firstSegment.startsWith('/') ? '/' : '';\n \n return leadingSlash + parts.join('/');\n}\n\n/**\n * Resolve path segments to an absolute path\n * \n * @param segments - Path segments to resolve\n * @returns Absolute path\n */\nexport function resolve(...segments: string[]): string {\n if (nodePath) {\n return nodePath.resolve(...segments);\n }\n \n // Browser/Tauri implementation - use join and ensure absolute\n let resolvedPath = join(...segments);\n \n // If not absolute, we can't really resolve in browser\n // Return as-is (would need cwd from process binding)\n if (!resolvedPath.startsWith('/')) {\n resolvedPath = '/' + resolvedPath;\n }\n \n return resolvedPath;\n}\n\n/**\n * Get the directory name of a path\n * \n * @param p - Path to get directory from\n * @returns Directory portion of the path\n */\nexport function dirname(p: string): string {\n if (nodePath) {\n return nodePath.dirname(p);\n }\n \n // Browser/Tauri implementation\n const normalized = p.replace(/\\\\/g, '/').replace(/\\/+$/, '');\n const lastSlash = normalized.lastIndexOf('/');\n \n if (lastSlash === -1) {\n return '.';\n }\n if (lastSlash === 0) {\n return '/';\n }\n \n return normalized.slice(0, lastSlash);\n}\n\n/**\n * Get the base name of a path\n * \n * @param p - Path to get base name from\n * @param ext - Optional extension to remove\n * @returns Base name of the path\n */\nexport function basename(p: string, ext?: string): string {\n if (nodePath) {\n return nodePath.basename(p, ext);\n }\n \n // Browser/Tauri implementation\n const normalized = p.replace(/\\\\/g, '/').replace(/\\/+$/, '');\n const lastSlash = normalized.lastIndexOf('/');\n let name = lastSlash === -1 ? normalized : normalized.slice(lastSlash + 1);\n \n if (ext && name.endsWith(ext)) {\n name = name.slice(0, -ext.length);\n }\n \n return name;\n}\n\n/**\n * Get the extension of a path\n * \n * @param p - Path to get extension from\n * @returns Extension of the path (including the dot)\n */\nexport function extname(p: string): string {\n if (nodePath) {\n return nodePath.extname(p);\n }\n \n // Browser/Tauri implementation\n const name = basename(p);\n const lastDot = name.lastIndexOf('.');\n \n if (lastDot <= 0) {\n return '';\n }\n \n return name.slice(lastDot);\n}\n\n/**\n * Check if a path is absolute\n * \n * @param p - Path to check\n * @returns true if the path is absolute\n */\nexport function isAbsolute(p: string): boolean {\n if (nodePath) {\n return nodePath.isAbsolute(p);\n }\n \n // Browser/Tauri implementation\n // Unix: starts with /\n // Windows: starts with drive letter or UNC\n return p.startsWith('/') || /^[a-zA-Z]:[\\\\/]/.test(p) || p.startsWith('\\\\\\\\');\n}\n\n/**\n * Normalize a path\n * \n * @param p - Path to normalize\n * @returns Normalized path\n */\nexport function normalize(p: string): string {\n if (nodePath) {\n return nodePath.normalize(p);\n }\n \n // Browser/Tauri implementation\n return join(p);\n}\n\n/**\n * Get relative path from one path to another\n * \n * @param from - Source path\n * @param to - Destination path\n * @returns Relative path\n */\nexport function relative(from: string, to: string): string {\n if (nodePath) {\n return nodePath.relative(from, to);\n }\n \n // Browser/Tauri implementation\n const fromParts = from.replace(/\\\\/g, '/').split('/').filter(Boolean);\n const toParts = to.replace(/\\\\/g, '/').split('/').filter(Boolean);\n \n // Find common base\n let commonLength = 0;\n while (\n commonLength < fromParts.length &&\n commonLength < toParts.length &&\n fromParts[commonLength] === toParts[commonLength]\n ) {\n commonLength++;\n }\n \n // Build relative path\n const upCount = fromParts.length - commonLength;\n const relativeParts = [\n ...Array(upCount).fill('..'),\n ...toParts.slice(commonLength)\n ];\n \n return relativeParts.join('/') || '.';\n}\n\n/**\n * Parse a path into its components\n * \n * @param p - Path to parse\n * @returns Parsed path object\n */\nexport function parse(p: string): {\n root: string;\n dir: string;\n base: string;\n ext: string;\n name: string;\n} {\n if (nodePath) {\n return nodePath.parse(p);\n }\n \n // Browser/Tauri implementation\n const dir = dirname(p);\n const base = basename(p);\n const ext = extname(p);\n const name = basename(p, ext);\n \n // Determine root\n let root = '';\n if (p.startsWith('/')) {\n root = '/';\n } else if (/^[a-zA-Z]:[\\\\/]/.test(p)) {\n root = p.slice(0, 3);\n }\n \n return { root, dir, base, ext, name };\n}\n\n/**\n * Format a path from its components\n * \n * @param pathObject - Object with path components\n * @returns Formatted path\n */\nexport function format(pathObject: {\n root?: string;\n dir?: string;\n base?: string;\n ext?: string;\n name?: string;\n}): string {\n if (nodePath) {\n return nodePath.format(pathObject);\n }\n \n // Browser/Tauri implementation\n const { dir, root, base, name, ext } = pathObject;\n const fileName = base || (name || '') + (ext || '');\n \n if (dir) {\n return dir + '/' + fileName;\n }\n if (root) {\n return root + fileName;\n }\n \n return fileName;\n}\n\n// Default export for compatibility\nexport default {\n sep,\n delimiter,\n join,\n resolve,\n dirname,\n basename,\n extname,\n isAbsolute,\n normalize,\n relative,\n parse,\n format,\n};\n", "/**\n * Shell/Process execution binding\n * \n * Provides cross-platform process execution that works in both Node.js and Tauri.\n * In Node.js, delegates to the native 'child_process' module.\n * In Tauri, uses globalThis.__TAURI__.shell (requires withGlobalTauri: true).\n */\n\nimport { isTauri, isNode, assertRuntime, getTauriPlugin, type TauriShellPlugin } from './runtime';\n\n// Conditionally import modules\nlet nodeChildProcess: typeof import('child_process') | null = null;\nlet nodeUtil: typeof import('util') | null = null;\n\n// Initialize Node.js modules if available\nif (isNode()) {\n // eslint-disable-next-line @typescript-eslint/no-var-requires\n nodeChildProcess = require('child_process');\n // eslint-disable-next-line @typescript-eslint/no-var-requires\n nodeUtil = require('util');\n}\n\n/**\n * Get Tauri shell plugin from globalThis.__TAURI__\n */\nfunction getTauriShell(): TauriShellPlugin {\n return getTauriPlugin('shell');\n}\n\n/**\n * Filter out undefined values from env object (Tauri requires string values only)\n */\nfunction filterEnv(env?: Record<string, string | undefined>): Record<string, string> | undefined {\n if (!env) return undefined;\n const result: Record<string, string> = {};\n for (const [key, value] of Object.entries(env)) {\n if (value !== undefined) {\n result[key] = value;\n }\n }\n return result;\n}\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport interface ExecOptions {\n cwd?: string;\n env?: Record<string, string | undefined>;\n timeout?: number;\n maxBuffer?: number;\n encoding?: BufferEncoding;\n}\n\nexport interface ExecResult {\n stdout: string;\n stderr: string;\n code: number | null;\n}\n\nexport interface SpawnOptions {\n cwd?: string;\n env?: Record<string, string | undefined>;\n stdio?: 'pipe' | 'inherit' | 'ignore';\n}\n\nexport interface SpawnedProcess {\n pid?: number;\n kill: () => Promise<void>;\n write: (data: string) => Promise<void>;\n onStdout: (callback: (data: string) => void) => void;\n onStderr: (callback: (data: string) => void) => void;\n onClose: (callback: (code: number | null) => void) => void;\n onError: (callback: (error: Error) => void) => void;\n}\n\n// ============================================================================\n// Async Operations\n// ============================================================================\n\n/**\n * Execute a shell command and return the output\n * \n * @param command - Command to execute\n * @param options - Execution options\n * @returns Command output\n */\nexport async function exec(command: string, options: ExecOptions = {}): Promise<ExecResult> {\n if (isTauri()) {\n const shell = getTauriShell();\n \n // Tauri shell uses Command class with args\n // For shell execution, we use the shell program with -c flag\n const shellProgram = process.platform === 'win32' ? 'cmd' : 'sh';\n const shellArgs = process.platform === 'win32' ? ['/c', command] : ['-c', command];\n \n const cmd = shell.Command.create(shellProgram, shellArgs, {\n cwd: options.cwd,\n env: filterEnv(options.env),\n });\n \n const output = await cmd.execute();\n \n return {\n stdout: output.stdout,\n stderr: output.stderr,\n code: output.code,\n };\n }\n \n if (nodeChildProcess && nodeUtil) {\n const execPromise = nodeUtil.promisify(nodeChildProcess.exec);\n \n try {\n const { stdout, stderr } = await execPromise(command, {\n cwd: options.cwd,\n env: options.env ? { ...process.env, ...options.env } : undefined,\n timeout: options.timeout,\n maxBuffer: options.maxBuffer || 50 * 1024 * 1024, // 50MB default\n encoding: options.encoding || 'utf-8',\n });\n \n return {\n stdout: stdout || '',\n stderr: stderr || '',\n code: 0,\n };\n } catch (error: any) {\n return {\n stdout: error.stdout || '',\n stderr: error.stderr || error.message,\n code: error.code || 1,\n };\n }\n }\n \n throw new Error('exec is not supported in this environment');\n}\n\n/**\n * Spawn a process\n * \n * @param program - Program to run\n * @param args - Arguments to pass\n * @param options - Spawn options\n * @returns Spawned process handle\n */\nexport async function spawn(\n program: string,\n args: string[] = [],\n options: SpawnOptions = {}\n): Promise<SpawnedProcess> {\n if (isTauri()) {\n const shell = getTauriShell();\n \n const cmd = shell.Command.create(program, args, {\n cwd: options.cwd,\n env: filterEnv(options.env),\n });\n \n const childProcess = await cmd.spawn();\n \n let stdoutCallback: ((data: string) => void) | null = null;\n let stderrCallback: ((data: string) => void) | null = null;\n let closeCallback: ((code: number | null) => void) | null = null;\n let errorCallback: ((error: Error) => void) | null = null;\n \n // Note: Tauri's Child type uses different event handling\n // We cast to any to work around type differences between versions\n const child = childProcess as any;\n \n // Set up event handlers if available\n if (typeof child.on === 'function') {\n child.on('close', (data: any) => {\n if (closeCallback) {\n closeCallback(data?.code ?? null);\n }\n });\n \n child.on('error', (error: any) => {\n if (errorCallback) {\n errorCallback(new Error(String(error)));\n }\n });\n }\n \n return {\n pid: childProcess.pid,\n kill: async () => {\n await childProcess.kill();\n },\n write: async (data: string) => {\n await childProcess.write(new TextEncoder().encode(data));\n },\n onStdout: (callback) => {\n stdoutCallback = callback;\n if (typeof child.on === 'function') {\n child.on('data', (event: any) => {\n if (event?.type === 'Stdout' && stdoutCallback) {\n stdoutCallback(event.data);\n }\n });\n }\n },\n onStderr: (callback) => {\n stderrCallback = callback;\n if (typeof child.on === 'function') {\n child.on('data', (event: any) => {\n if (event?.type === 'Stderr' && stderrCallback) {\n stderrCallback(event.data);\n }\n });\n }\n },\n onClose: (callback) => {\n closeCallback = callback;\n },\n onError: (callback) => {\n errorCallback = callback;\n },\n };\n }\n \n if (nodeChildProcess) {\n const child = nodeChildProcess.spawn(program, args, {\n cwd: options.cwd,\n env: options.env ? { ...process.env, ...options.env } : undefined,\n stdio: ['pipe', 'pipe', 'pipe'],\n });\n \n let stdoutCallback: ((data: string) => void) | null = null;\n let stderrCallback: ((data: string) => void) | null = null;\n let closeCallback: ((code: number | null) => void) | null = null;\n let errorCallback: ((error: Error) => void) | null = null;\n \n child.stdout?.on('data', (data) => {\n if (stdoutCallback) {\n stdoutCallback(data.toString());\n }\n });\n \n child.stderr?.on('data', (data) => {\n if (stderrCallback) {\n stderrCallback(data.toString());\n }\n });\n \n child.on('close', (code) => {\n if (closeCallback) {\n closeCallback(code);\n }\n });\n \n child.on('error', (error) => {\n if (errorCallback) {\n errorCallback(error);\n }\n });\n \n return {\n pid: child.pid,\n kill: async () => {\n child.kill();\n },\n write: async (data: string) => {\n return new Promise((resolve, reject) => {\n if (child.stdin) {\n child.stdin.write(data, (err) => {\n if (err) reject(err);\n else resolve();\n });\n } else {\n reject(new Error('stdin not available'));\n }\n });\n },\n onStdout: (callback) => {\n stdoutCallback = callback;\n },\n onStderr: (callback) => {\n stderrCallback = callback;\n },\n onClose: (callback) => {\n closeCallback = callback;\n },\n onError: (callback) => {\n errorCallback = callback;\n },\n };\n }\n \n throw new Error('spawn is not supported in this environment');\n}\n\n// ============================================================================\n// Sync Operations (Node.js only)\n// ============================================================================\n\n/**\n * Execute a shell command synchronously (Node.js only)\n * \n * @param command - Command to execute\n * @param options - Execution options\n * @returns Command output\n */\nexport function execSync(command: string, options: ExecOptions = {}): ExecResult {\n assertRuntime('execSync', ['node']);\n \n if (nodeChildProcess) {\n try {\n const stdout = nodeChildProcess.execSync(command, {\n cwd: options.cwd,\n env: options.env ? { ...process.env, ...options.env } : undefined,\n timeout: options.timeout,\n maxBuffer: options.maxBuffer || 50 * 1024 * 1024,\n encoding: options.encoding || 'utf-8',\n stdio: ['pipe', 'pipe', 'pipe'],\n });\n \n return {\n stdout: stdout?.toString() || '',\n stderr: '',\n code: 0,\n };\n } catch (error: any) {\n return {\n stdout: error.stdout?.toString() || '',\n stderr: error.stderr?.toString() || error.message,\n code: error.status || 1,\n };\n }\n }\n \n throw new Error('execSync is not supported in this environment');\n}\n\n/**\n * Spawn a process synchronously (Node.js only)\n * \n * @param program - Program to run\n * @param args - Arguments to pass\n * @param options - Spawn options\n * @returns Exit code and output\n */\nexport function spawnSync(\n program: string,\n args: string[] = [],\n options: SpawnOptions = {}\n): ExecResult {\n assertRuntime('spawnSync', ['node']);\n \n if (nodeChildProcess) {\n const result = nodeChildProcess.spawnSync(program, args, {\n cwd: options.cwd,\n env: options.env ? { ...process.env, ...options.env } : undefined,\n encoding: 'utf-8',\n });\n \n return {\n stdout: result.stdout || '',\n stderr: result.stderr || '',\n code: result.status,\n };\n }\n \n throw new Error('spawnSync is not supported in this environment');\n}\n\n// ============================================================================\n// Utility Functions\n// ============================================================================\n\n/**\n * Promisified exec with async/await syntax\n * Alias for exec() for compatibility\n */\nexport const execAsync = exec;\n\n/**\n * Create a promisified version of exec (Node.js compatible API)\n */\nexport function promisifyExec(): (command: string, options?: ExecOptions) => Promise<{ stdout: string; stderr: string }> {\n return async (command: string, options?: ExecOptions) => {\n const result = await exec(command, options);\n if (result.code !== 0) {\n const error = new Error(`Command failed: ${command}`);\n (error as any).stdout = result.stdout;\n (error as any).stderr = result.stderr;\n (error as any).code = result.code;\n throw error;\n }\n return { stdout: result.stdout, stderr: result.stderr };\n };\n}\n\n// ============================================================================\n// Node.js Native Access (Node.js only)\n// ============================================================================\n\nexport interface NodeSpawnOptions {\n cwd?: string;\n env?: NodeJS.ProcessEnv;\n stdio?: 'pipe' | 'inherit' | 'ignore' | Array<'pipe' | 'inherit' | 'ignore' | 'ipc'>;\n detached?: boolean;\n shell?: boolean | string;\n}\n\n/**\n * Direct access to Node.js child_process.spawn (Node.js only)\n * \n * Use this when you need the full Node.js ChildProcess API with event emitters.\n * Returns the native ChildProcess object.\n * \n * @param command - Command to execute\n * @param args - Arguments to pass\n * @param options - Node.js spawn options\n * @returns Native Node.js ChildProcess\n */\nexport function nodeSpawn(\n command: string,\n args: string[] = [],\n options: NodeSpawnOptions = {}\n): import('child_process').ChildProcess {\n assertRuntime('nodeSpawn', ['node']);\n \n if (nodeChildProcess) {\n return nodeChildProcess.spawn(command, args, options as any);\n }\n \n throw new Error('nodeSpawn is not supported in this environment');\n}\n\n// Default export\nexport default {\n exec,\n execAsync,\n execSync,\n spawn,\n spawnSync,\n promisifyExec,\n nodeSpawn,\n};\n", "/**\n * Habits Logger - Type Definitions\n * \n * A multilevel logging system with hierarchical config resolution:\n * .env (highest) > stack.yaml > habit.yaml > defaults (lowest)\n */\n\n/**\n * Log levels ordered by severity (trace=0 is most verbose, fatal=5 is most severe)\n */\nexport type LogLevel = 'trace' | 'debug' | 'info' | 'warn' | 'error' | 'fatal' | 'none';\n\n/**\n * Priority map for log level comparison\n * Lower number = more verbose, higher number = more severe\n */\nexport const LOG_LEVEL_PRIORITY: Record<LogLevel, number> = {\n trace: 0,\n debug: 1,\n info: 2,\n warn: 3,\n error: 4,\n fatal: 5,\n none: 6, // Disables all logging\n};\n\n/**\n * A single log entry with all metadata\n */\nexport interface LogEntry {\n /** When the log was created */\n timestamp: Date;\n /** Severity level */\n level: LogLevel;\n /** The log message */\n message: string;\n /** Contextual information about where this log originated */\n context: LogContext;\n /** Optional structured data to include with the log */\n data?: Record<string, unknown>;\n}\n\n/**\n * Context information attached to each log entry\n * Enables filtering and tracing across workflows and bits\n */\nexport interface LogContext {\n /** ID of the workflow being executed */\n workflowId?: string;\n /** ID of the current node in the workflow */\n nodeId?: string;\n /** Name of the bit (e.g., 'bit-http', 'bit-openai') */\n bitName?: string;\n /** Name of the action within the bit */\n actionName?: string;\n /** Unique ID for this execution instance */\n executionId?: string;\n}\n\n/**\n * Configuration for console output\n */\nexport interface ConsoleOutputConfig {\n type: 'console';\n /** Enable ANSI colors in output (auto-detected if not specified) */\n colorize?: boolean;\n /** Output format */\n format?: 'text' | 'json';\n}\n\n/**\n * Configuration for file output with rotation support\n */\nexport interface FileOutputConfig {\n type: 'file';\n /** Path to the log file */\n path: string;\n /** Maximum file size before rotation (e.g., '10mb', '1gb') */\n maxSize?: string;\n /** Maximum number of rotated files to keep */\n maxFiles?: number;\n /** Output format */\n format?: 'text' | 'json';\n}\n\n/**\n * Configuration for JSON output (NDJSON format)\n */\nexport interface JsonOutputConfig {\n type: 'json';\n /** Custom writable stream (defaults to stdout) */\n stream?: NodeJS.WritableStream;\n}\n\n/**\n * Union type for all output configurations\n */\nexport type OutputConfig = ConsoleOutputConfig | FileOutputConfig | JsonOutputConfig;\n\n/**\n * Complete logger configuration\n */\nexport interface LoggerConfig {\n /** Default log level for all loggers */\n level: LogLevel;\n /** Output destinations */\n outputs: OutputConfig[];\n /** Per-bit log level overrides (e.g., { 'bit-http': 'debug' }) */\n bitOverrides?: Record<string, LogLevel>;\n}\n\n/**\n * Logger interface that all logger implementations must satisfy\n */\nexport interface ILogger {\n /** Alias for info() - for console.log compatibility */\n log(message: string, data?: Record<string, unknown>): void;\n /** Log at trace level (most verbose, for detailed debugging) */\n trace(message: string, data?: Record<string, unknown>): void;\n /** Log at debug level (debugging information) */\n debug(message: string, data?: Record<string, unknown>): void;\n /** Log at info level (general information) */\n info(message: string, data?: Record<string, unknown>): void;\n /** Log at warn level (warnings, potential issues) */\n warn(message: string, data?: Record<string, unknown>): void;\n /** Log at error level (errors, failures) */\n error(message: string, data?: Record<string, unknown>): void;\n /** Log at fatal level (critical errors, system failures) */\n fatal(message: string, data?: Record<string, unknown>): void;\n \n /** Create a child logger with additional context */\n child(context: Partial<LogContext>): ILogger;\n \n /** Dynamically change the log level */\n setLevel(level: LogLevel): void;\n /** Get the current log level */\n getLevel(): LogLevel;\n}\n\n/**\n * Logging configuration as it appears in habit.yaml\n */\nexport interface HabitLoggingConfig {\n level?: LogLevel;\n outputs?: ('console' | 'file' | 'json')[];\n bitOverrides?: Record<string, LogLevel>;\n}\n\n/**\n * Logging configuration as it appears in stack.yaml\n * Extends habit config with additional server-level options\n */\nexport interface StackLoggingConfig extends HabitLoggingConfig {\n file?: {\n path?: string;\n maxSize?: string;\n maxFiles?: number;\n };\n format?: 'text' | 'json';\n colorize?: boolean;\n}\n\n/**\n * Environment variable names for logging configuration\n */\nexport const LOG_ENV_VARS = {\n /** Global log level override */\n LEVEL: 'HABITS_LOG_LEVEL',\n /** Comma-separated output types (console,file,json) */\n OUTPUT: 'HABITS_LOG_OUTPUT',\n /** File output path */\n FILE_PATH: 'HABITS_LOG_FILE_PATH',\n /** File max size */\n FILE_MAX_SIZE: 'HABITS_LOG_FILE_MAX_SIZE',\n /** File max rotation count */\n FILE_MAX_FILES: 'HABITS_LOG_FILE_MAX_FILES',\n /** Enable/disable colors */\n COLORIZE: 'HABITS_LOG_COLORIZE',\n /** Output format */\n FORMAT: 'HABITS_LOG_FORMAT',\n /** Pattern for per-bit level overrides: HABITS_LOG_BIT_{BITNAME}_LEVEL */\n BIT_LEVEL_PATTERN: /^HABITS_LOG_BIT_(.+)_LEVEL$/,\n} as const;\n", "/**\n * Logger - Main logger class\n * \n * A hierarchical, OOP-based logger with support for:\n * - 6 log levels (trace, debug, info, warn, error, fatal)\n * - Multiple transports (console, file, JSON)\n * - Per-bit log level overrides\n * - Child loggers with inherited configuration\n */\n\nimport { \n ILogger, \n LogLevel, \n LogEntry, \n LogContext, \n LoggerConfig,\n LOG_LEVEL_PRIORITY \n} from './types';\nimport { Transport } from './transports/Transport';\n\nexport interface LoggerOptions {\n /** Logger configuration */\n config: LoggerConfig;\n /** Transports to output to */\n transports: Transport[];\n /** Initial context */\n context?: LogContext;\n}\n\nexport class Logger implements ILogger {\n private level: LogLevel;\n private context: LogContext;\n private transports: Transport[];\n private bitOverrides: Record<string, LogLevel>;\n private closed: boolean = false;\n\n constructor(options: LoggerOptions) {\n this.level = options.config.level;\n this.transports = options.transports;\n this.context = options.context || {};\n this.bitOverrides = options.config.bitOverrides || {};\n }\n\n /**\n * Determine if a message at the given level should be logged\n */\n private shouldLog(level: LogLevel): boolean {\n if (this.closed) return false;\n const effectiveLevel = this.getEffectiveLevel();\n return LOG_LEVEL_PRIORITY[level] >= LOG_LEVEL_PRIORITY[effectiveLevel];\n }\n\n /**\n * Get the effective log level, accounting for bit-specific overrides\n */\n private getEffectiveLevel(): LogLevel {\n // Check for bit-specific override\n if (this.context.bitName) {\n const override = this.bitOverrides[this.context.bitName];\n if (override) return override;\n }\n return this.level;\n }\n\n /**\n * Core logging method - routes to all transports\n */\n private logInternal(level: LogLevel, message: string, data?: Record<string, unknown>): void {\n if (!this.shouldLog(level)) return;\n\n const entry: LogEntry = {\n timestamp: new Date(),\n level,\n message,\n context: { ...this.context },\n data,\n };\n\n for (const transport of this.transports) {\n try {\n transport.log(entry);\n } catch (err) {\n // Don't let transport errors break the application\n console.error(`[Logger] Transport error: ${err}`);\n }\n }\n }\n\n // ---------- Public logging methods ----------\n\n /** Alias for info() - for console.log compatibility */\n log(message: string, data?: Record<string, unknown>): void {\n this.logInternal('info', message, data);\n }\n\n trace(message: string, data?: Record<string, unknown>): void {\n this.logInternal('trace', message, data);\n }\n\n debug(message: string, data?: Record<string, unknown>): void {\n this.logInternal('debug', message, data);\n }\n\n info(message: string, data?: Record<string, unknown>): void {\n this.logInternal('info', message, data);\n }\n\n warn(message: string, data?: Record<string, unknown>): void {\n this.logInternal('warn', message, data);\n }\n\n error(message: string, data?: Record<string, unknown>): void {\n this.logInternal('error', message, data);\n }\n\n fatal(message: string, data?: Record<string, unknown>): void {\n this.logInternal('fatal', message, data);\n }\n\n // ---------- Configuration methods ----------\n\n /**\n * Create a child logger that inherits this logger's configuration\n * but with additional context fields\n */\n child(additionalContext: Partial<LogContext>): ILogger {\n return new Logger({\n config: {\n level: this.level,\n outputs: [],\n bitOverrides: this.bitOverrides,\n },\n transports: this.transports, // Share transports with parent\n context: { ...this.context, ...additionalContext },\n });\n }\n\n /**\n * Dynamically change the log level\n */\n setLevel(level: LogLevel): void {\n this.level = level;\n }\n\n /**\n * Get the current log level\n */\n getLevel(): LogLevel {\n return this.level;\n }\n\n /**\n * Get the current context\n */\n getContext(): LogContext {\n return { ...this.context };\n }\n\n /**\n * Update context fields\n */\n setContext(context: Partial<LogContext>): void {\n this.context = { ...this.context, ...context };\n }\n\n /**\n * Set a bit-specific log level override\n */\n setBitOverride(bitName: string, level: LogLevel): void {\n this.bitOverrides[bitName] = level;\n }\n\n /**\n * Remove a bit-specific log level override\n */\n removeBitOverride(bitName: string): void {\n delete this.bitOverrides[bitName];\n }\n\n /**\n * Get all bit overrides\n */\n getBitOverrides(): Record<string, LogLevel> {\n return { ...this.bitOverrides };\n }\n\n // ---------- Lifecycle methods ----------\n\n /**\n * Flush all transports\n */\n async flush(): Promise<void> {\n await Promise.all(this.transports.map(t => t.flush()));\n }\n\n /**\n * Close all transports and prevent further logging\n */\n async close(): Promise<void> {\n this.closed = true;\n await Promise.all(this.transports.map(t => t.close()));\n }\n\n /**\n * Check if the logger is closed\n */\n isClosed(): boolean {\n return this.closed;\n }\n}\n\n/**\n * No-op logger that discards all log messages\n * Useful for testing or when logging should be disabled\n */\nexport class NullLogger implements ILogger {\n log(_message: string, _data?: Record<string, unknown>): void {}\n trace(_message: string, _data?: Record<string, unknown>): void {}\n debug(_message: string, _data?: Record<string, unknown>): void {}\n info(_message: string, _data?: Record<string, unknown>): void {}\n warn(_message: string, _data?: Record<string, unknown>): void {}\n error(_message: string, _data?: Record<string, unknown>): void {}\n fatal(_message: string, _data?: Record<string, unknown>): void {}\n child(_context: Partial<LogContext>): ILogger { return this; }\n setLevel(_level: LogLevel): void {}\n getLevel(): LogLevel { return 'none'; }\n}\n", "/**\n * ConfigResolver - Resolves logger configuration from multiple sources\n * \n * Priority (highest to lowest):\n * 1. Environment variables (.env)\n * 2. Stack configuration (stack.yaml)\n * 3. Habit configuration (habit.yaml)\n * 4. Default values\n */\n\nimport { \n LoggerConfig, \n LogLevel, \n OutputConfig,\n HabitLoggingConfig,\n StackLoggingConfig,\n LOG_ENV_VARS,\n LOG_LEVEL_PRIORITY\n} from './types';\n\n/**\n * Default logger configuration\n */\nconst DEFAULT_CONFIG: LoggerConfig = {\n level: 'info',\n outputs: [{ type: 'console', colorize: true, format: 'text' }],\n bitOverrides: {},\n};\n\n/**\n * Valid log levels for validation\n */\nconst VALID_LOG_LEVELS = new Set<LogLevel>(Object.keys(LOG_LEVEL_PRIORITY) as LogLevel[]);\n\nexport class ConfigResolver {\n /**\n * Resolve logger configuration from all sources\n * \n * @param habitConfig - Configuration from habit.yaml (lowest priority)\n * @param stackConfig - Configuration from stack.yaml\n * @param env - Environment variables (highest priority)\n * @returns Merged LoggerConfig\n */\n static resolve(\n habitConfig?: HabitLoggingConfig,\n stackConfig?: StackLoggingConfig,\n env: Record<string, string | undefined> = process.env\n ): LoggerConfig {\n // Start with defaults\n let config: LoggerConfig = this.deepClone(DEFAULT_CONFIG);\n\n // Layer 1: Apply habit.yaml config\n if (habitConfig) {\n config = this.mergeHabitConfig(config, habitConfig);\n }\n\n // Layer 2: Apply stack.yaml config (overrides habit)\n if (stackConfig) {\n config = this.mergeStackConfig(config, stackConfig);\n }\n\n // Layer 3: Apply environment variables (highest priority)\n config = this.applyEnvOverrides(config, env);\n\n return config;\n }\n\n /**\n * Merge habit-level config into base config\n */\n private static mergeHabitConfig(\n base: LoggerConfig,\n habit: HabitLoggingConfig\n ): LoggerConfig {\n const result = this.deepClone(base);\n\n if (habit.level && this.isValidLogLevel(habit.level)) {\n result.level = habit.level;\n }\n\n if (habit.outputs && Array.isArray(habit.outputs)) {\n result.outputs = habit.outputs\n .filter(o => ['console', 'file', 'json'].includes(o))\n .map(o => this.createOutputConfig(o));\n }\n\n if (habit.bitOverrides) {\n result.bitOverrides = {\n ...result.bitOverrides,\n ...this.filterValidBitOverrides(habit.bitOverrides),\n };\n }\n\n return result;\n }\n\n /**\n * Merge stack-level config into base config\n */\n private static mergeStackConfig(\n base: LoggerConfig,\n stack: StackLoggingConfig\n ): LoggerConfig {\n let result = this.mergeHabitConfig(base, stack);\n\n // Handle file configuration\n if (stack.file?.path) {\n const fileOutput: OutputConfig = {\n type: 'file',\n path: stack.file.path,\n maxSize: stack.file.maxSize,\n maxFiles: stack.file.maxFiles,\n format: stack.format,\n };\n\n // Add file output if not already present\n const hasFileOutput = result.outputs.some(o => o.type === 'file');\n if (!hasFileOutput) {\n result.outputs.push(fileOutput);\n } else {\n // Update existing file output\n result.outputs = result.outputs.map(o =>\n o.type === 'file' ? fileOutput : o\n );\n }\n }\n\n // Apply format to console outputs\n if (stack.format) {\n result.outputs = result.outputs.map(o =>\n o.type === 'console' ? { ...o, format: stack.format } : o\n );\n }\n\n // Apply colorize to console outputs\n if (stack.colorize !== undefined) {\n result.outputs = result.outputs.map(o =>\n o.type === 'console' ? { ...o, colorize: stack.colorize } : o\n );\n }\n\n return result;\n }\n\n /**\n * Apply environment variable overrides\n */\n private static applyEnvOverrides(\n config: LoggerConfig,\n env: Record<string, string | undefined>\n ): LoggerConfig {\n const result = this.deepClone(config);\n\n // HABITS_LOG_LEVEL\n const levelEnv = env[LOG_ENV_VARS.LEVEL];\n if (levelEnv && this.isValidLogLevel(levelEnv as LogLevel)) {\n result.level = levelEnv as LogLevel;\n }\n\n // HABITS_LOG_OUTPUT (comma-separated: console,file,json)\n const outputEnv = env[LOG_ENV_VARS.OUTPUT];\n if (outputEnv) {\n const outputs = outputEnv.split(',').map(o => o.trim().toLowerCase());\n result.outputs = outputs\n .filter(o => ['console', 'file', 'json'].includes(o))\n .map(type => this.createOutputConfigFromEnv(type, env));\n }\n\n // HABITS_LOG_FILE_PATH\n const filePathEnv = env[LOG_ENV_VARS.FILE_PATH];\n if (filePathEnv) {\n const existingFile = result.outputs.find(o => o.type === 'file');\n if (existingFile && existingFile.type === 'file') {\n existingFile.path = filePathEnv;\n } else {\n result.outputs.push(this.createOutputConfigFromEnv('file', env));\n }\n }\n\n // HABITS_LOG_COLORIZE\n const colorizeEnv = env[LOG_ENV_VARS.COLORIZE];\n if (colorizeEnv !== undefined) {\n const colorize = colorizeEnv.toLowerCase() !== 'false';\n result.outputs = result.outputs.map(o =>\n o.type === 'console' ? { ...o, colorize } : o\n );\n }\n\n // HABITS_LOG_FORMAT\n const formatEnv = env[LOG_ENV_VARS.FORMAT];\n if (formatEnv && ['text', 'json'].includes(formatEnv.toLowerCase())) {\n const format = formatEnv.toLowerCase() as 'text' | 'json';\n result.outputs = result.outputs.map(o =>\n o.type === 'console' || o.type === 'file' ? { ...o, format } : o\n );\n }\n\n // Per-bit level overrides: HABITS_LOG_BIT_{BITNAME}_LEVEL\n for (const [key, value] of Object.entries(env)) {\n const match = key.match(LOG_ENV_VARS.BIT_LEVEL_PATTERN);\n if (match && value && this.isValidLogLevel(value as LogLevel)) {\n // Convert BITNAME to bit-name format (e.g., HTTP -> bit-http)\n const bitName = `bit-${match[1].toLowerCase().replace(/_/g, '-')}`;\n result.bitOverrides![bitName] = value as LogLevel;\n }\n }\n\n return result;\n }\n\n /**\n * Create a basic output config from type string\n */\n private static createOutputConfig(type: string): OutputConfig {\n switch (type) {\n case 'file':\n return { type: 'file', path: './logs/habits.log' };\n case 'json':\n return { type: 'json' };\n case 'console':\n default:\n return { type: 'console', colorize: true, format: 'text' };\n }\n }\n\n /**\n * Create output config from env vars\n */\n private static createOutputConfigFromEnv(\n type: string,\n env: Record<string, string | undefined>\n ): OutputConfig {\n switch (type) {\n case 'file':\n const maxFilesEnv = env[LOG_ENV_VARS.FILE_MAX_FILES];\n return {\n type: 'file',\n path: env[LOG_ENV_VARS.FILE_PATH] || './logs/habits.log',\n maxSize: env[LOG_ENV_VARS.FILE_MAX_SIZE],\n maxFiles: maxFilesEnv ? parseInt(maxFilesEnv, 10) : undefined,\n };\n case 'json':\n return { type: 'json' };\n case 'console':\n default:\n return {\n type: 'console',\n colorize: env[LOG_ENV_VARS.COLORIZE]?.toLowerCase() !== 'false',\n format: (env[LOG_ENV_VARS.FORMAT] as 'text' | 'json') || 'text',\n };\n }\n }\n\n /**\n * Filter and validate bit overrides\n */\n private static filterValidBitOverrides(\n overrides: Record<string, LogLevel>\n ): Record<string, LogLevel> {\n const result: Record<string, LogLevel> = {};\n for (const [bit, level] of Object.entries(overrides)) {\n if (this.isValidLogLevel(level)) {\n result[bit] = level;\n }\n }\n return result;\n }\n\n /**\n * Check if a value is a valid log level\n */\n private static isValidLogLevel(level: string): level is LogLevel {\n return VALID_LOG_LEVELS.has(level as LogLevel);\n }\n\n /**\n * Deep clone an object\n */\n private static deepClone<T>(obj: T): T {\n return JSON.parse(JSON.stringify(obj));\n }\n\n /**\n * Parse size string to bytes (e.g., \"10mb\" -> 10485760)\n */\n static parseSize(size?: string): number | undefined {\n if (!size) return undefined;\n\n const match = size.toLowerCase().match(/^(\\d+(?:\\.\\d+)?)\\s*(b|kb|mb|gb)?$/);\n if (!match) return undefined;\n\n const value = parseFloat(match[1]);\n const unit = match[2] || 'b';\n\n const multipliers: Record<string, number> = {\n b: 1,\n kb: 1024,\n mb: 1024 * 1024,\n gb: 1024 * 1024 * 1024,\n };\n\n return Math.floor(value * multipliers[unit]);\n }\n}\n", "/**\n * Abstract base class for log transports\n * Transports are responsible for delivering formatted log entries to their destination\n */\n\nimport { LogEntry } from '../types';\nimport { Formatter } from '../formatters/Formatter';\n\nexport abstract class Transport {\n protected formatter: Formatter;\n\n constructor(formatter: Formatter) {\n this.formatter = formatter;\n }\n\n /**\n * Log an entry to this transport's destination\n * @param entry The log entry to write\n */\n abstract log(entry: LogEntry): void;\n\n /**\n * Flush any buffered output\n * @returns Promise that resolves when flush is complete\n */\n abstract flush(): Promise<void>;\n\n /**\n * Close the transport and release resources\n * @returns Promise that resolves when closed\n */\n abstract close(): Promise<void>;\n\n /**\n * Replace the formatter used by this transport\n * @param formatter New formatter to use\n */\n setFormatter(formatter: Formatter): void {\n this.formatter = formatter;\n }\n\n /**\n * Get the current formatter\n */\n getFormatter(): Formatter {\n return this.formatter;\n }\n}\n", "/**\n * Console transport - writes logs to stdout/stderr with optional colors\n */\n\nimport { Transport } from './Transport';\nimport { LogEntry, LogLevel } from '../types';\nimport { Formatter } from '../formatters/Formatter';\n\n/**\n * ANSI color codes for each log level\n */\nconst LEVEL_COLORS: Record<LogLevel, string> = {\n trace: '\\x1b[90m', // Gray\n debug: '\\x1b[36m', // Cyan\n info: '\\x1b[32m', // Green\n warn: '\\x1b[33m', // Yellow\n error: '\\x1b[31m', // Red\n fatal: '\\x1b[35m', // Magenta (bold)\n none: '',\n};\n\nconst RESET = '\\x1b[0m';\nconst BOLD = '\\x1b[1m';\n\nexport interface ConsoleTransportOptions {\n /** Enable ANSI color codes. Auto-detected from TTY if not specified */\n colorize?: boolean;\n /** Use stderr for error and fatal levels. Default: true */\n useStderr?: boolean;\n}\n\nexport class ConsoleTransport extends Transport {\n private colorize: boolean;\n private useStderr: boolean;\n\n constructor(formatter: Formatter, options: ConsoleTransportOptions = {}) {\n super(formatter);\n // Auto-detect TTY for colorize if not explicitly set\n this.colorize = options.colorize ?? (process.stdout.isTTY ?? false);\n this.useStderr = options.useStderr ?? true;\n }\n\n log(entry: LogEntry): void {\n const formatted = this.formatter.format(entry);\n let output: string;\n\n if (this.colorize) {\n const color = LEVEL_COLORS[entry.level];\n const bold = entry.level === 'fatal' ? BOLD : '';\n output = `${bold}${color}${formatted}${RESET}`;\n } else {\n output = formatted;\n }\n\n // Route error/fatal to stderr\n const stream = this.useStderr && (entry.level === 'error' || entry.level === 'fatal')\n ? process.stderr\n : process.stdout;\n\n stream.write(output + '\\n');\n }\n\n async flush(): Promise<void> {\n // Console is synchronous, but we handle any pending writes\n return new Promise((resolve) => {\n if (process.stdout.writableLength === 0 && process.stderr.writableLength === 0) {\n resolve();\n } else {\n // Wait for drain event\n const checkDrain = () => {\n if (process.stdout.writableLength === 0 && process.stderr.writableLength === 0) {\n resolve();\n } else {\n setImmediate(checkDrain);\n }\n };\n checkDrain();\n }\n });\n }\n\n async close(): Promise<void> {\n await this.flush();\n // Nothing to close for console\n }\n\n /**\n * Enable or disable colorization at runtime\n */\n setColorize(enabled: boolean): void {\n this.colorize = enabled;\n }\n\n /**\n * Check if colorization is enabled\n */\n isColorized(): boolean {\n return this.colorize;\n }\n}\n", "/**\n * File transport - writes logs to a file with rotation support\n */\n\nimport * as fs from 'fs';\nimport * as path from 'path';\nimport { Transport } from './Transport';\nimport { LogEntry } from '../types';\nimport { Formatter } from '../formatters/Formatter';\n\nexport interface FileTransportOptions {\n /** Path to the log file */\n path: string;\n /** Maximum file size in bytes before rotation. Default: 10MB */\n maxSize?: number;\n /** Maximum number of rotated files to keep. Default: 5 */\n maxFiles?: number;\n /** File mode (permissions). Default: 0o644 */\n mode?: number;\n}\n\nexport class FileTransport extends Transport {\n private filePath: string;\n private maxSize: number;\n private maxFiles: number;\n private mode: number;\n private stream: fs.WriteStream | null = null;\n private currentSize: number = 0;\n private writeQueue: Promise<void> = Promise.resolve();\n\n constructor(formatter: Formatter, options: FileTransportOptions) {\n super(formatter);\n this.filePath = path.resolve(options.path);\n this.maxSize = options.maxSize || 10 * 1024 * 1024; // 10MB default\n this.maxFiles = options.maxFiles || 5;\n this.mode = options.mode || 0o644;\n this.initStream();\n }\n\n private initStream(): void {\n // Ensure directory exists\n const dir = path.dirname(this.filePath);\n if (!fs.existsSync(dir)) {\n fs.mkdirSync(dir, { recursive: true });\n }\n\n // Get current file size if file exists\n if (fs.existsSync(this.filePath)) {\n try {\n this.currentSize = fs.statSync(this.filePath).size;\n } catch {\n this.currentSize = 0;\n }\n }\n\n // Create write stream in append mode\n this.stream = fs.createWriteStream(this.filePath, {\n flags: 'a',\n mode: this.mode,\n encoding: 'utf8',\n });\n\n // Handle stream errors\n this.stream.on('error', (err) => {\n console.error(`[Logger] File transport error: ${err.message}`);\n });\n }\n\n private async rotate(): Promise<void> {\n if (!this.stream) return;\n\n // Close current stream\n await new Promise<void>((resolve) => {\n this.stream?.end(() => resolve());\n });\n this.stream = null;\n\n // Rotate existing files: .log.4 -> .log.5, .log.3 -> .log.4, etc.\n for (let i = this.maxFiles - 1; i >= 1; i--) {\n const oldPath = `${this.filePath}.${i}`;\n const newPath = `${this.filePath}.${i + 1}`;\n\n if (fs.existsSync(oldPath)) {\n if (i === this.maxFiles - 1) {\n // Delete oldest file\n try {\n fs.unlinkSync(oldPath);\n } catch {\n // Ignore deletion errors\n }\n } else {\n // Rename to next number\n try {\n fs.renameSync(oldPath, newPath);\n } catch {\n // Ignore rename errors\n }\n }\n }\n }\n\n // Rename current file to .1\n try {\n fs.renameSync(this.filePath, `${this.filePath}.1`);\n } catch {\n // If rename fails, we'll just append to the file\n }\n\n // Reset size and create new stream\n this.currentSize = 0;\n this.initStream();\n }\n\n log(entry: LogEntry): void {\n const formatted = this.formatter.format(entry) + '\\n';\n const bytes = Buffer.byteLength(formatted, 'utf8');\n\n // Queue the write to ensure sequential execution\n this.writeQueue = this.writeQueue.then(async () => {\n // Check if rotation needed\n if (this.currentSize + bytes > this.maxSize) {\n await this.rotate();\n }\n\n // Write to stream\n if (this.stream && !this.stream.destroyed) {\n this.stream.write(formatted);\n this.currentSize += bytes;\n }\n });\n }\n\n async flush(): Promise<void> {\n // Wait for write queue to complete\n await this.writeQueue;\n\n // Ensure stream is drained\n return new Promise((resolve) => {\n if (!this.stream || this.stream.writableLength === 0) {\n resolve();\n } else {\n this.stream.once('drain', () => resolve());\n }\n });\n }\n\n async close(): Promise<void> {\n await this.flush();\n \n return new Promise((resolve) => {\n if (!this.stream) {\n resolve();\n return;\n }\n\n this.stream.end(() => {\n this.stream = null;\n resolve();\n });\n });\n }\n\n /**\n * Get the current log file path\n */\n getFilePath(): string {\n return this.filePath;\n }\n\n /**\n * Get the current file size\n */\n getCurrentSize(): number {\n return this.currentSize;\n }\n}\n", "/**\n * Abstract base class for log formatters\n * Formatters transform LogEntry objects into string representations\n */\n\nimport { LogEntry } from '../types';\n\nexport abstract class Formatter {\n /**\n * Format a log entry into a string\n * @param entry The log entry to format\n * @returns Formatted string representation\n */\n abstract format(entry: LogEntry): string;\n}\n", "/**\n * JSON formatter for structured log output\n * Outputs NDJSON (newline-delimited JSON) format suitable for log aggregation\n */\n\nimport { Formatter } from './Formatter';\nimport { LogEntry } from '../types';\n\nexport interface JsonFormatterOptions {\n /** Include stack trace for error objects in data */\n includeStackTrace?: boolean;\n /** Pretty print JSON (adds indentation) - not recommended for production */\n prettyPrint?: boolean;\n}\n\nexport class JsonFormatter extends Formatter {\n private includeStackTrace: boolean;\n private prettyPrint: boolean;\n\n constructor(options: JsonFormatterOptions = {}) {\n super();\n this.includeStackTrace = options.includeStackTrace ?? true;\n this.prettyPrint = options.prettyPrint ?? false;\n }\n\n format(entry: LogEntry): string {\n const output: Record<string, unknown> = {\n timestamp: entry.timestamp.toISOString(),\n level: entry.level,\n message: entry.message,\n };\n\n // Add context fields if present\n if (entry.context.workflowId) output.workflowId = entry.context.workflowId;\n if (entry.context.nodeId) output.nodeId = entry.context.nodeId;\n if (entry.context.bitName) output.bitName = entry.context.bitName;\n if (entry.context.actionName) output.actionName = entry.context.actionName;\n if (entry.context.executionId) output.executionId = entry.context.executionId;\n\n // Add data if present, handling Error objects specially\n if (entry.data && Object.keys(entry.data).length > 0) {\n output.data = this.serializeData(entry.data);\n }\n\n return this.prettyPrint \n ? JSON.stringify(output, null, 2) \n : JSON.stringify(output);\n }\n\n private serializeData(data: Record<string, unknown>): Record<string, unknown> {\n const result: Record<string, unknown> = {};\n \n for (const [key, value] of Object.entries(data)) {\n if (value instanceof Error) {\n result[key] = {\n name: value.name,\n message: value.message,\n ...(this.includeStackTrace && value.stack ? { stack: value.stack } : {}),\n };\n } else if (value !== undefined) {\n result[key] = value;\n }\n }\n \n return result;\n }\n}\n", "/**\n * JSON transport - writes NDJSON (newline-delimited JSON) to a stream\n * Useful for log aggregation systems like ELK, Datadog, etc.\n */\n\nimport { Transport } from './Transport';\nimport { LogEntry } from '../types';\nimport { JsonFormatter } from '../formatters/JsonFormatter';\n\nexport interface JsonTransportOptions {\n /** Writable stream to output to. Default: process.stdout */\n stream?: NodeJS.WritableStream;\n}\n\nexport class JsonTransport extends Transport {\n private stream: NodeJS.WritableStream;\n\n constructor(options: JsonTransportOptions = {}) {\n // Always use JsonFormatter for this transport\n super(new JsonFormatter());\n this.stream = options.stream || process.stdout;\n }\n\n log(entry: LogEntry): void {\n const formatted = this.formatter.format(entry);\n this.stream.write(formatted + '\\n');\n }\n\n async flush(): Promise<void> {\n return new Promise((resolve) => {\n const writable = this.stream as NodeJS.WriteStream;\n if (writable.writableLength === 0) {\n resolve();\n } else {\n writable.once('drain', () => resolve());\n }\n });\n }\n\n async close(): Promise<void> {\n await this.flush();\n // Don't close process.stdout/stderr\n if (this.stream !== process.stdout && this.stream !== process.stderr) {\n return new Promise((resolve) => {\n (this.stream as any).end?.(() => resolve()) || resolve();\n });\n }\n }\n\n /**\n * Get the output stream\n */\n getStream(): NodeJS.WritableStream {\n return this.stream;\n }\n}\n", "/**\n * Text formatter for human-readable log output\n * \n * Output format: [timestamp] [LEVEL] [context] message {data}\n * Example: [2026-02-15T10:30:00.123Z] [INFO ] [wf:my-workflow/bit-http] Request completed {\"status\":200}\n */\n\nimport { Formatter } from './Formatter';\nimport { LogEntry, LogContext } from '../types';\n\nexport interface TextFormatterOptions {\n /** Timestamp format: 'iso' (full), 'unix' (milliseconds), 'short' (time only) */\n timestampFormat?: 'iso' | 'unix' | 'short';\n /** Include milliseconds in short format */\n includeMs?: boolean;\n}\n\nexport class TextFormatter extends Formatter {\n private timestampFormat: 'iso' | 'unix' | 'short';\n private includeMs: boolean;\n\n constructor(options: TextFormatterOptions = {}) {\n super();\n this.timestampFormat = options.timestampFormat || 'iso';\n this.includeMs = options.includeMs ?? true;\n }\n\n format(entry: LogEntry): string {\n const ts = this.formatTimestamp(entry.timestamp);\n const level = entry.level.toUpperCase().padEnd(5);\n const ctx = this.formatContext(entry.context);\n const data = entry.data && Object.keys(entry.data).length > 0 \n ? ` ${JSON.stringify(entry.data)}` \n : '';\n \n return `[${ts}] [${level}]${ctx} ${entry.message}${data}`;\n }\n\n private formatTimestamp(date: Date): string {\n switch (this.timestampFormat) {\n case 'unix':\n return String(date.getTime());\n case 'short':\n // HH:MM:SS.mmm or HH:MM:SS\n const time = date.toISOString().slice(11, this.includeMs ? 23 : 19);\n return time;\n case 'iso':\n default:\n return date.toISOString();\n }\n }\n\n private formatContext(ctx: LogContext): string {\n const parts: string[] = [];\n \n if (ctx.workflowId) {\n parts.push(`wf:${ctx.workflowId}`);\n }\n if (ctx.nodeId) {\n parts.push(`node:${ctx.nodeId}`);\n }\n if (ctx.bitName) {\n parts.push(ctx.bitName);\n }\n if (ctx.actionName) {\n parts.push(ctx.actionName);\n }\n if (ctx.executionId) {\n parts.push(`exec:${ctx.executionId.slice(0, 8)}`);\n }\n \n return parts.length > 0 ? ` [${parts.join('/')}]` : '';\n }\n}\n", "/**\n * LoggerFactory - Factory for creating configured logger instances\n * \n * Handles:\n * - Creating loggers from merged configuration sources\n * - Managing the root logger singleton\n * - Creating child loggers for specific bits/workflows\n * - Building appropriate transports based on configuration\n */\n\nimport { Logger, NullLogger } from './Logger';\nimport { \n LoggerConfig, \n OutputConfig, \n LogContext, \n ILogger,\n HabitLoggingConfig,\n StackLoggingConfig \n} from './types';\nimport { ConfigResolver } from './ConfigResolver';\nimport { Transport } from './transports/Transport';\nimport { ConsoleTransport } from './transports/ConsoleTransport';\nimport { FileTransport } from './transports/FileTransport';\nimport { JsonTransport } from './transports/JsonTransport';\nimport { TextFormatter } from './formatters/TextFormatter';\nimport { JsonFormatter } from './formatters/JsonFormatter';\nimport { Formatter } from './formatters/Formatter';\n\n/**\n * Global root logger instance\n */\nlet rootLogger: Logger | null = null;\n\nexport class LoggerFactory {\n /**\n * Create a new logger from configuration sources\n * \n * @param habitConfig - Per-workflow logging config from habit.yaml\n * @param stackConfig - Stack-level logging config from stack.yaml\n * @param context - Initial context for this logger\n * @returns Configured logger instance\n */\n static create(\n habitConfig?: HabitLoggingConfig,\n stackConfig?: StackLoggingConfig,\n context?: LogContext\n ): ILogger {\n const config = ConfigResolver.resolve(\n habitConfig,\n stackConfig,\n process.env\n );\n\n const transports = this.createTransports(config);\n \n return new Logger({\n config,\n transports,\n context,\n });\n }\n\n /**\n * Create a logger directly from a LoggerConfig\n */\n static createFromConfig(config: LoggerConfig, context?: LogContext): ILogger {\n const transports = this.createTransports(config);\n return new Logger({ config, transports, context });\n }\n\n /**\n * Initialize the root logger (called once at server startup)\n * \n * @param stackConfig - Stack-level logging configuration\n * @returns The root logger instance\n */\n static initRoot(stackConfig?: StackLoggingConfig): ILogger {\n if (rootLogger) {\n // Close existing root logger\n rootLogger.close().catch(() => {});\n }\n\n rootLogger = this.create(undefined, stackConfig) as Logger;\n return rootLogger;\n }\n\n /**\n * Get the current root logger, or create a default one\n */\n static getRoot(): ILogger {\n if (!rootLogger) {\n rootLogger = this.create() as Logger;\n }\n return rootLogger;\n }\n\n /**\n * Create a child logger for a specific bit execution\n * Inherits from the root logger with bit-specific context\n * \n * @param bitName - Name of the bit (e.g., 'bit-http')\n * @param actionName - Name of the action being executed\n * @param workflowId - ID of the workflow\n * @param nodeId - ID of the current node\n * @param executionId - Unique execution ID\n */\n static forBit(\n bitName: string,\n actionName: string,\n workflowId?: string,\n nodeId?: string,\n executionId?: string\n ): ILogger {\n const root = this.getRoot();\n \n return root.child({\n bitName,\n actionName,\n workflowId,\n nodeId,\n executionId,\n });\n }\n\n /**\n * Create a child logger for workflow execution\n */\n static forWorkflow(workflowId: string, executionId?: string): ILogger {\n const root = this.getRoot();\n \n return root.child({\n workflowId,\n executionId,\n });\n }\n\n /**\n * Create a null logger that discards all messages\n * Useful for testing or when logging should be disabled\n */\n static createNull(): ILogger {\n return new NullLogger();\n }\n\n /**\n * Shutdown the root logger and release resources\n */\n static async shutdown(): Promise<void> {\n if (rootLogger) {\n await rootLogger.close();\n rootLogger = null;\n }\n }\n\n // ---------- Internal methods ----------\n\n /**\n * Create transports based on configuration\n */\n private static createTransports(config: LoggerConfig): Transport[] {\n return config.outputs.map(output => this.createTransport(output));\n }\n\n /**\n * Create a single transport from output configuration\n */\n private static createTransport(output: OutputConfig): Transport {\n switch (output.type) {\n case 'file':\n return new FileTransport(\n this.createFormatter(output.format || 'text'),\n {\n path: output.path,\n maxSize: ConfigResolver.parseSize(output.maxSize),\n maxFiles: output.maxFiles,\n }\n );\n\n case 'json':\n return new JsonTransport({\n stream: output.stream,\n });\n\n case 'console':\n default:\n return new ConsoleTransport(\n this.createFormatter(output.format || 'text'),\n { colorize: output.colorize }\n );\n }\n }\n\n /**\n * Create a formatter based on format type\n */\n private static createFormatter(format: 'text' | 'json'): Formatter {\n return format === 'json' \n ? new JsonFormatter() \n : new TextFormatter();\n }\n}\n", "import * as fs from '@ha-bits/bindings/fs';\nimport * as path from '@ha-bits/bindings/path';\nimport { exec as execAsync } from '@ha-bits/bindings/shell';\nimport { LoggerFactory } from '@ha-bits/core/logger';\n\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// npm Install Utilities\n// ============================================================================\n\n/**\n * Options for npm install commands\n */\nexport interface NpmInstallOptions {\n cwd?: string;\n timeout?: number;\n legacyPeerDeps?: boolean;\n includePeer?: boolean;\n production?: boolean;\n noSave?: boolean;\n prefix?: string;\n saveOptional?: boolean;\n global?: boolean;\n /** Custom npm registry URL */\n registry?: string;\n}\n\n/**\n * Builds the npm install command with the given options\n */\nfunction buildNpmInstallCommand(packageSpec?: string, options: NpmInstallOptions = {}): string {\n const parts = ['npm', 'install'];\n \n // Always ignore engine requirements to allow n8n modules that require newer Node versions\n parts.push('--engine-strict=false');\n // Ignore scripts to reduce memory usage and speed up installs\n parts.push('--ignore-scripts');\n\n if (packageSpec) {\n parts.push(packageSpec);\n }\n \n if (options.global) {\n parts.push('-g');\n }\n if (options.legacyPeerDeps) {\n parts.push('--legacy-peer-deps');\n }\n if (options.includePeer) {\n parts.push('--include=peer');\n }\n if (options.production) {\n parts.push('--omit=dev');\n }\n if (options.noSave) {\n // parts.push('--no-save');\n }\n if (options.prefix) {\n parts.push(`--prefix ${options.prefix}`);\n }\n if (options.saveOptional) {\n parts.push('--save-optional');\n }\n if (options.registry) {\n parts.push(`--registry ${options.registry}`);\n }\n \n return parts.join(' ');\n}\n\n/**\n * Run package install asynchronously with the given options\n * Uses npm with increased memory for heavy packages\n */\nexport async function npmInstall(packageSpec?: string, options: NpmInstallOptions = {}): Promise<{ stdout: string; stderr: string }> {\n const command = buildNpmInstallCommand(packageSpec, options);\n \n const execOptions: { cwd?: string; timeout?: number; env?: NodeJS.ProcessEnv; maxBuffer?: number } = {\n // Increase max buffer for large outputs\n maxBuffer: 500 * 1024 * 1024, // 500MB\n // Set NODE_OPTIONS to increase heap memory and optimize GC for heavy installs\n env: {\n ...process.env,\n NODE_OPTIONS: '--max-old-space-size=16384',\n },\n };\n if (options.cwd) {\n execOptions.cwd = options.cwd;\n }\n if (options.timeout) {\n execOptions.timeout = options.timeout;\n }\n\n // Check if package is already installed, skip if yes\n if (packageSpec) {\n // Parse package name (handle @scope/name@version format)\n const packageName = packageSpec.replace(/@[\\d.]+(-[\\w.]+)?$/, ''); // Remove version suffix\n const nodeModulesBase = options.prefix || options.cwd || process.cwd();\n const packagePath = path.join(nodeModulesBase, 'node_modules', packageName);\n \n if (fs.existsSync(packagePath)) {\n logger.log(`Package ${packageName} already installed at ${packagePath}, skipping install`);\n return { stdout: `Skipped: ${packageName} already installed`, stderr: '' };\n }\n }\n\n logger.log(`Executing npm install command: ${command}`);\n return execAsync(command, execOptions);\n}\n\n// ============================================================================\n// Path Utilities\n// ============================================================================\n\n/**\n * Environment variable name for the nodes base path without the /nodes suffix\n */\nconst NODES_BASE_PATH_ENV = 'HABITS_NODES_PATH';\n\n/**\n * Environment variable name for local nodes directory in the workspace\n */\nconst LOCAL_NODES_PATH_ENV = 'HABITS_LOCAL_NODES_PATH';\n\n/**\n * Default base path for nodes when not specified in environment\n */\nconst DEFAULT_NODES_BASE_PATH = '/tmp/habits-nodes';\n\n/**\n * Cache the base path to avoid repeated file reads\n */\nlet cachedNodesBasePath: string | null = null;\n\n/**\n * Get the base path for nodes from environment variable or .env file.\n * Falls back to /tmp/habits-nodes if not specified.\n * \n * Priority:\n * 1. Environment variable HABITS_NODES_PATH\n * 2. .env file in current working directory\n * 3. Default: /tmp/habits-nodes\n * \n * @returns The base path for nodes\n */\nexport function getNodesBasePath(): string {\n if (cachedNodesBasePath !== null) {\n return cachedNodesBasePath;\n }\n\n // First, check environment variable\n if (process.env[NODES_BASE_PATH_ENV]) {\n cachedNodesBasePath = process.env[NODES_BASE_PATH_ENV];\n return cachedNodesBasePath;\n }\n\n // Default to /tmp/habits-nodes\n cachedNodesBasePath = DEFAULT_NODES_BASE_PATH;\n return cachedNodesBasePath;\n}\n\n/**\n * Get the full path to the nodes directory for a specific framework.\n * \n * @param framework - The framework name (e.g., 'activepieces', 'n8n', 'script')\n * @returns The full path to the framework's nodes directory\n */\nexport function getNodesPath(framework: string): string {\n return path.join(getNodesBasePath(), 'node_modules');\n}\n\n/**\n * Get the full path to a specific module within a framework.\n * \n * @param framework - The framework name (e.g., 'activepieces', 'n8n', 'script')\n * @param moduleName - The module name (e.g., '@ha-bits/piece-intersect')\n * @returns The full path to the module\n */\nexport function getModuleFullPath(framework: string, moduleName: string): string {\n return path.join(getNodesBasePath(), 'node_modules', moduleName);\n}\n\n/**\n * Get the local nodes path from the workspace for local module sources.\n * This is where modules in the 'nodes/' directory of the workspace are located.\n * \n * Priority:\n * 1. Environment variable HABITS_LOCAL_NODES_PATH\n * 2. 'nodes' directory relative to process.cwd()\n * 3. Search up from __dirname for a 'nodes' directory\n * \n * @param framework - The framework name (e.g., 'activepieces', 'n8n')\n * @returns The path to local nodes, or null if not found\n */\nexport function getLocalModulePath(framework: string, moduleName: string): string | null {\n // For bits modules, strip @ha-bits/ prefix for path construction when path already includes @ha-bits\n const strippedModuleName = moduleName.startsWith('@ha-bits/') ? moduleName.slice('@ha-bits/'.length) : moduleName;\n const pathModuleName = moduleName;\n \n // Check environment variable first\n if (process.env[LOCAL_NODES_PATH_ENV]) {\n const localPath = path.join(process.env[LOCAL_NODES_PATH_ENV], framework, pathModuleName);\n if (fs.existsSync(localPath)) {\n return localPath;\n }\n // Also check @ha-bits subdirectory for bits framework\n if (framework === 'bits') {\n const haBitsPath = path.join(process.env[LOCAL_NODES_PATH_ENV], framework, '@ha-bits', strippedModuleName);\n if (fs.existsSync(haBitsPath)) {\n return haBitsPath;\n }\n }\n }\n \n // Try relative to cwd()\n const cwdNodesPath = path.join(process.cwd(), 'nodes', framework, pathModuleName);\n if (fs.existsSync(cwdNodesPath)) {\n return cwdNodesPath;\n }\n \n // For bits framework, also check nodes/bits/@ha-bits/ path\n if (framework === 'bits') { // Try relative to cwd()\n const bitsCreatorPath = path.join(process.cwd(), 'nodes', 'bits', '@ha-bits', strippedModuleName);\n \n if (fs.existsSync(bitsCreatorPath)) {\n return bitsCreatorPath;\n }\n // Search up from __dirname path\n let currentDir = __dirname;\n for (let i = 0; i < 10; i++) { \n const bitsPath = path.join(currentDir, 'nodes', 'bits', '@ha-bits', strippedModuleName);\n if (fs.existsSync(bitsPath)) {\n return bitsPath;\n }\n const parent = path.dirname(currentDir);\n if (parent === currentDir) break;\n currentDir = parent;\n }\n }\n \n // Search up from __dirname\n let currentDir = __dirname;\n for (let i = 0; i < 10; i++) {\n const nodesPath = path.join(currentDir, 'nodes', framework, pathModuleName);\n if (fs.existsSync(nodesPath)) {\n return nodesPath;\n }\n const parent = path.dirname(currentDir);\n if (parent === currentDir) break;\n currentDir = parent;\n }\n \n return null;\n}\n\n/**\n * Clear the cached nodes base path.\n * Useful for testing or when the environment changes.\n */\nexport function clearNodesBasePathCache(): void {\n cachedNodesBasePath = null;\n}\n", "import Module, { createRequire } from 'module';\nimport path from 'path';\nimport * as fs from 'fs';\n\n// ============================================================================\n// Cortex Module Registration\n// ============================================================================\n\n/**\n * Path to the cortex package root (where package.json is).\n * This is determined at module load time.\n */\nlet cortexPackagePath: string | null = null;\n\n/**\n * Flag to track if the cortex module hook is already installed.\n */\nlet cortexModuleHookInstalled = false;\n\n/**\n * Get the path to the cortex package root.\n * Searches up from the current file to find the package.json with name \"@ha-bits/cortex\".\n */\nfunction getCortexPackagePath(): string {\n if (cortexPackagePath) {\n return cortexPackagePath;\n }\n \n // Start from this file's directory and search up for package.json\n let dir = __dirname;\n for (let i = 0; i < 10; i++) {\n const pkgPath = path.join(dir, 'package.json');\n if (fs.existsSync(pkgPath)) {\n try {\n const pkg = JSON.parse(fs.readFileSync(pkgPath, 'utf-8'));\n if (pkg.name === '@ha-bits/cortex') {\n cortexPackagePath = dir;\n return dir;\n }\n } catch (e) {\n // Continue searching\n }\n }\n const parent = path.dirname(dir);\n if (parent === dir) break;\n dir = parent;\n }\n \n // Fallback: assume we're 2 levels deep in src/utils\n cortexPackagePath = path.resolve(__dirname, '..', '..');\n return cortexPackagePath;\n}\n\n/**\n * Register @ha-bits/cortex in Node's module resolution system.\n * This allows bits modules to `require('@ha-bits/cortex')` without needing\n * symlinks or the package to be installed in node_modules.\n * \n * The hook intercepts resolution requests for '@ha-bits/cortex' and redirects\n * them to the current cortex package.\n */\nexport function registerCortexModule(): void {\n if (cortexModuleHookInstalled) {\n return; // Already installed\n }\n \n const cortexPath = getCortexPackagePath();\n console.log(`\uD83D\uDD17 Registering @ha-bits/cortex module resolution hook (path: ${cortexPath})`);\n \n // IMPORTANT: Capture the current _resolveFilename NOW, not at module load time.\n // This ensures we wrap around tsx's version (or any other loader's version) \n // rather than the original Node.js version.\n const currentResolveFilename = (Module as any)._resolveFilename;\n \n // Patch Module._resolveFilename to intercept @ha-bits/cortex requests\n (Module as any)._resolveFilename = function(request: string, parent: NodeModule, isMain: boolean, options?: any) {\n // Intercept requests for @ha-bits/cortex\n if (request === '@ha-bits/cortex' || request.startsWith('@ha-bits/cortex/')) {\n // For the main package, resolve to the package's main entry\n if (request === '@ha-bits/cortex') {\n const mainPath = path.join(cortexPath, 'src', 'index.ts');\n // When running from dist/pack, use the compiled entry\n if (fs.existsSync(mainPath)) {\n return mainPath;\n }\n const distPath = path.join(cortexPath, 'pack', 'index.cjs');\n if (fs.existsSync(distPath)) {\n return distPath;\n }\n // Fallback to index.js\n const jsPath = path.join(cortexPath, 'index.js');\n if (fs.existsSync(jsPath)) {\n return jsPath;\n }\n }\n \n // For subpath imports like '@ha-bits/cortex/bits/framework'\n const subPath = request.replace('@ha-bits/cortex/', '');\n const possiblePaths = [\n path.join(cortexPath, 'src', subPath + '.ts'),\n path.join(cortexPath, 'src', subPath, 'index.ts'),\n path.join(cortexPath, 'pack', subPath + '.cjs'),\n path.join(cortexPath, subPath + '.js'),\n path.join(cortexPath, subPath, 'index.js'),\n ];\n \n for (const p of possiblePaths) {\n if (fs.existsSync(p)) {\n return p;\n }\n }\n }\n \n // Fall through to the previous resolver (could be tsx's or Node's original)\n return currentResolveFilename.call(this, request, parent, isMain, options);\n };\n \n cortexModuleHookInstalled = true;\n console.log(`\u2713 @ha-bits/cortex module resolution hook installed`);\n}\n\n// ============================================================================\n// Patched Require Functions\n// ============================================================================\n\n/**\n * Creates a patched require function that includes additional search paths for module resolution.\n * This is used to load n8n/activepieces modules with their actual runtime dependencies.\n */\nexport function createPatchedRequire(basePath: string, additionalPaths: string[]): NodeRequire {\n const baseRequire = createRequire(path.join(basePath, 'package.json'));\n \n const originalResolvePaths = (Module as any)._resolveLookupPaths;\n\n console.log(`[customRequire] Creating patched require with paths:`, additionalPaths);\n \n return function patchedRequire(id: string): any {\n (Module as any)._resolveLookupPaths = function(request: string, parent: NodeModule) {\n const result = originalResolvePaths.call(this, request, parent);\n if (result && Array.isArray(result)) {\n for (const p of [...additionalPaths].reverse()) {\n if (!result.includes(p)) result.unshift(p);\n }\n }\n return result;\n };\n \n try {\n delete baseRequire.cache[id];\n return baseRequire(id);\n } finally {\n (Module as any)._resolveLookupPaths = originalResolvePaths;\n }\n } as NodeRequire;\n}\n\n\n/**\n * Require code from `pathToCode` while resolving dependencies from `searchPaths`.\n * Uses the actual n8n/activepieces runtime dependencies from node_modules.\n */\nexport function patchedRequire(pathToCode: string, searchPaths: string[]): unknown {\n const originalResolvePaths = (Module as any)._resolveLookupPaths;\n \n // Patch to inject our search paths\n (Module as any)._resolveLookupPaths = function(request: string, parent: NodeModule) {\n const result = originalResolvePaths.call(this, request, parent);\n if (result && Array.isArray(result)) {\n for (const p of [...searchPaths].reverse()) {\n if (!result.includes(p)) result.unshift(p);\n }\n }\n return result;\n };\n\n try {\n // Create require from the first search path\n const customRequire = createRequire(path.join(searchPaths[0], 'package.json'));\n delete customRequire.cache[pathToCode];\n return customRequire(pathToCode);\n } finally {\n // Restore\n (Module as any)._resolveLookupPaths = originalResolvePaths;\n }\n}\n\n\n/**\n * Simple require using createRequire from a specific search path.\n * Creates require from the module's directory so it can resolve its dependencies.\n */\nexport function simpleRequire(pathToCode: string, searchPath: string) {\n const dynamicRequire = createRequire(path.join(searchPath, \"package.json\"));\n delete dynamicRequire.cache[pathToCode];\n const nodeModule = dynamicRequire(pathToCode);\n return nodeModule;\n}\n\n/**\n * Custom require that loads modules from a specific search path.\n * Uses createRequire to create a require function rooted at the module's directory,\n * ensuring all dependencies resolve consistently from a single location.\n * \n * This avoids patching global Module._resolveLookupPaths which can cause issues\n * when the same dependency (e.g., semver) gets required from different paths\n * during the module loading chain.\n */\nexport function customRequire(pathToCode: string, searchPath: string) {\n console.log(`Custom requiring ${pathToCode} with search path ${searchPath}`);\n const flatMethod = true;\n // Use createRequire rooted at the search path - this ensures all dependencies\n // resolve relative to the module's location without patching global resolution\n if(flatMethod){\n const dynamicRequire = createRequire(path.join(searchPath, 'package.json'));\n \n // Clear cache to ensure fresh load\n delete dynamicRequire.cache[pathToCode];\n \n // Also clear any cached versions of the module by full path\n const resolvedPath = dynamicRequire.resolve(pathToCode);\n delete dynamicRequire.cache[resolvedPath];\n \n return dynamicRequire(pathToCode);\n }\n\n else {\n // Build list of search paths:\n // 1. The provided searchPath (e.g., module's src directory)\n // 2. The parent node_modules directory for resolving peer dependencies\n const searchPaths = [searchPath];\n \n // Find node_modules in the path hierarchy\n let currentPath = searchPath;\n while (currentPath && currentPath !== path.dirname(currentPath)) {\n const nodeModulesPath = path.join(currentPath, 'node_modules');\n if (fs.existsSync(nodeModulesPath)) {\n searchPaths.push(nodeModulesPath);\n }\n // Also check if currentPath itself is within node_modules\n if (path.basename(path.dirname(currentPath)) === 'node_modules' || \n path.basename(path.dirname(path.dirname(currentPath))) === 'node_modules') {\n // Find the root node_modules\n let nmPath = currentPath;\n while (nmPath && !nmPath.endsWith('/node_modules') && !nmPath.endsWith('\\\\node_modules')) {\n nmPath = path.dirname(nmPath);\n }\n if (nmPath && nmPath.endsWith('node_modules')) {\n if (!searchPaths.includes(nmPath)) {\n searchPaths.push(nmPath);\n }\n }\n }\n currentPath = path.dirname(currentPath);\n }\n \n const patchedReq = createPatchedRequire(pathToCode, searchPaths);\n return patchedReq(pathToCode);\n}\n}\n", "import * as fs from '@ha-bits/bindings/fs';\nimport * as path from '@ha-bits/bindings/path';\nimport { exec as execAsync } from '@ha-bits/bindings/shell';\nimport { getModuleName } from './moduleLoader';\nimport { getNodesPath, getModuleFullPath, getNodesBasePath, getLocalModulePath, npmInstall } from './utils';\nimport { registerCortexModule } from './customRequire';\n\n// ============================================================================\n// ActivePieces Dependency Linking\n// ============================================================================\n\n/**\n * ActivePieces peer dependencies that should be linked from cortex's node_modules.\n * These packages are already bundled in cortex and should be shared with pieces.\n */\nconst ACTIVEPIECES_PEER_DEPS = [\n '@activepieces/pieces-common',\n '@activepieces/pieces-framework',\n '@activepieces/shared'\n];\n\n/**\n * n8n peer dependencies that should be linked from the base node_modules.\n * These packages are required by n8n community nodes.\n */\nconst N8N_PEER_DEPS = [\n 'n8n-workflow',\n 'n8n-core',\n 'moment-timezone', // Often required by community nodes\n // Note: n8n-nodes-base is too large (300+ nodes, crashes npm with OOM)\n // Individual nodes should be installed separately if needed\n //'n8n-nodes-base'\n];\n\n/**\n * Get the path to base node_modules where ActivePieces packages should be installed.\n */\nfunction getActivepiecesPackagesPath(): string | null {\n const basePath = path.join(getNodesBasePath(), 'node_modules');\n const testPath = path.join(basePath, '@activepieces', 'pieces-framework');\n if (fs.existsSync(testPath)) {\n return basePath;\n }\n return null;\n}\n\n/**\n * Ensure ActivePieces peer dependencies are installed in the base node_modules.\n * Similar to ensureN8nDepsInstalled but for ActivePieces packages.\n */\nasync function ensureActivepiecesDepsInstalled(): Promise<string | null> {\n const basePath = getNodesBasePath();\n const baseNodeModules = path.join(basePath, 'node_modules');\n \n // Check if @activepieces/pieces-framework is already installed\n const piecesFrameworkPath = path.join(baseNodeModules, '@activepieces', 'pieces-framework');\n if (fs.existsSync(piecesFrameworkPath)) {\n console.log(`\u2713 @activepieces/pieces-framework already installed at ${baseNodeModules}`);\n return baseNodeModules;\n }\n \n console.log(`\uD83D\uDCE6 Installing ActivePieces peer dependencies to ${basePath}...`);\n \n // ============================================================================\n // \u2139\uFE0F LICENSE INFO - ActivePieces has mixed licensing!\n // ============================================================================\n // ActivePieces framework (@activepieces/pieces-framework, etc.) is MIT licensed.\n // However, some pieces may have different licenses:\n // \n // \u2705 OPEN SOURCE (MIT) - Safe to use and redistribute:\n // - Community pieces in @activepieces/piece-* packages\n // - Most integrations (OpenAI, Slack, Google, etc.)\n // \n // \u26A0\uFE0F CLOSED SOURCE / PREMIUM - Check before using:\n // - Some enterprise pieces may have restricted licenses\n // - Pieces marked as \"premium\" in the ActivePieces platform\n // - Custom pieces from third parties\n // \n // Always verify the license of each piece you use:\n // - Check the piece's package.json for license field\n // - Review https://github.com/activepieces/activepieces\n // ============================================================================\n console.log(`\\n${'='.repeat(80)}`);\n console.log(`\u2139\uFE0F LICENSE INFO: ActivePieces has MIXED licensing!`);\n console.log(`${'='.repeat(80)}`);\n console.log(`ActivePieces framework (@activepieces/pieces-framework) is MIT licensed.`);\n console.log(`However, SOME PIECES may have DIFFERENT or RESTRICTED licenses!`);\n console.log(``);\n console.log(`\u2705 OPEN SOURCE (MIT) - Safe to redistribute:`);\n console.log(` - Community pieces in @activepieces/piece-* packages`);\n console.log(` - Most integrations (OpenAI, Slack, Google, etc.)`);\n console.log(``);\n console.log(`\u26A0\uFE0F CLOSED SOURCE / PREMIUM / EE - Check before using:`);\n console.log(` - Some enterprise pieces have restricted licenses`);\n console.log(` - Pieces marked as \"premium\" in ActivePieces platform`);\n console.log(` - Custom pieces from third parties`);\n console.log(``);\n console.log(`Always verify the license of EACH piece before redistribution!`);\n console.log(`${'='.repeat(80)}\\n`);\n\n try {\n // Install all activepieces peer deps to the base path\n // Using specific versions for compatibility\n const depsToInstall = [\n '@activepieces/pieces-common@^0.11.0',\n '@activepieces/pieces-framework@^0.23.0',\n '@activepieces/shared@^0.30.4'\n ].join(' ');\n \n await npmInstall(depsToInstall, { \n prefix: basePath, \n legacyPeerDeps: true, \n production: true,\n timeout: 300000\n });\n console.log(`\u2713 ActivePieces peer dependencies installed`);\n return baseNodeModules;\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Failed to install ActivePieces peer dependencies: ${error.message}`);\n return null;\n }\n}\n\n/**\n * Link ActivePieces peer dependencies from base node_modules to a piece module.\n * This resolves the peer dependency issue where pieces need @activepieces/* packages.\n * \n * @param modulePath - Path to the module where peer deps should be linked\n * @param moduleName - Name of the module (for logging)\n */\nasync function linkActivepiecesDeps(modulePath: string, moduleName: string): Promise<void> {\n // First ensure ActivePieces deps are installed (like n8n pattern)\n const baseNodeModules = await ensureActivepiecesDepsInstalled();\n \n if (!baseNodeModules) {\n console.warn(`\u26A0\uFE0F Could not find or install ActivePieces peer dependencies`);\n return;\n }\n \n const cortexNodeModules = baseNodeModules;\n\n console.log(`\uD83D\uDD17 Linking ActivePieces peer dependencies for ${moduleName}...`);\n \n // Link at module's own node_modules level\n const moduleNodeModules = path.join(modulePath, 'node_modules');\n await linkDepsToDirectory(moduleNodeModules, cortexNodeModules, moduleName);\n \n // Also link at parent node_modules level (where npm hoists dependencies)\n // This handles the case where the module is in node_modules/@scope/package\n // and Node.js looks in the parent node_modules first\n const parentNodeModules = path.dirname(path.dirname(modulePath));\n if (parentNodeModules.endsWith('node_modules')) {\n console.log(`\uD83D\uDD17 Also linking at parent node_modules: ${parentNodeModules}`);\n await linkDepsToDirectory(parentNodeModules, cortexNodeModules, moduleName);\n }\n}\n\n\n// ============================================================================\n// Bits Dependency Resolution\n// ============================================================================\n\n/**\n * Ensure @ha-bits/cortex is resolvable by bits modules.\n * \n * Instead of creating symlinks, this uses Node's module resolution hook\n * to intercept requests for '@ha-bits/cortex' and resolve them to the\n * currently running cortex package. This is cleaner because:\n * - No filesystem operations needed\n * - Works immediately without race conditions\n * - No cleanup required\n * - Works regardless of where modules are installed\n * \n * @param modulePath - Path to the module (for logging only)\n * @param moduleName - Name of the module (for logging)\n */\nasync function linkBitsDeps(modulePath: string, moduleName: string): Promise<void> {\n // Register the cortex module resolution hook (idempotent - safe to call multiple times)\n registerCortexModule();\n console.log(`\u2713 Bits module ${moduleName} can now resolve @ha-bits/cortex`);\n}\n\n/**\n * Link ActivePieces peer dependencies to a specific node_modules directory.\n */\nasync function linkDepsToDirectory(targetNodeModules: string, sourceNodeModules: string, moduleName: string): Promise<void> {\n // Skip if source and target are the same (would create self-referencing symlinks)\n if (path.resolve(targetNodeModules) === path.resolve(sourceNodeModules)) {\n console.log(`\u2713 Source and target are same, no linking needed at ${targetNodeModules}`);\n return;\n }\n \n const activepiecesDir = path.join(targetNodeModules, '@activepieces');\n \n // Create node_modules/@activepieces directory if it doesn't exist\n if (!fs.existsSync(activepiecesDir)) {\n fs.mkdirSync(activepiecesDir, { recursive: true });\n }\n \n for (const dep of ACTIVEPIECES_PEER_DEPS) {\n const [scope, pkgName] = dep.split('/');\n const sourcePackagePath = path.join(sourceNodeModules, scope, pkgName);\n const targetPackagePath = path.join(targetNodeModules, scope, pkgName);\n \n if (!fs.existsSync(sourcePackagePath)) {\n console.warn(`\u26A0\uFE0F Source package not found: ${sourcePackagePath}`);\n continue;\n }\n \n // Check if source has actual content (not just node_modules folder)\n const sourcePackageJson = path.join(sourcePackagePath, 'package.json');\n if (!fs.existsSync(sourcePackageJson)) {\n console.warn(`\u26A0\uFE0F Source package incomplete (no package.json): ${sourcePackagePath}`);\n continue;\n }\n \n // Remove existing package if present (might be a symlink, incomplete install, or real install)\n if (fs.existsSync(targetPackagePath)) {\n try {\n const stats = fs.lstatSync(targetPackagePath);\n if (stats.isSymbolicLink()) {\n // Already linked, check if it points to correct location\n const linkTarget = fs.readlinkSync(targetPackagePath);\n if (linkTarget === sourcePackagePath || linkTarget.endsWith(path.join(scope, pkgName))) {\n console.log(`\u2713 ${dep} already linked at ${targetNodeModules}`);\n continue;\n }\n }\n // Check if it's an incomplete install (has node_modules but no package.json)\n const targetPackageJson = path.join(targetPackagePath, 'package.json');\n if (!fs.existsSync(targetPackageJson)) {\n console.log(`\uD83D\uDD04 Replacing incomplete ${dep} at ${targetPackagePath}`);\n }\n fs.rmSync(targetPackagePath, { recursive: true, force: true });\n } catch (e) {\n // Ignore errors when removing\n }\n }\n \n // Create symlink to the cortex node_modules package\n try {\n fs.symlinkSync(sourcePackagePath, targetPackagePath, 'dir');\n console.log(`\u2713 Linked ${dep} to ${targetNodeModules}`);\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Failed to link ${dep}: ${error.message}`);\n }\n }\n}\n\n/**\n * Ensures ActivePieces peer dependencies are linked after npm install.\n * This should be called AFTER npm install to override any installed peer deps.\n * \n * @param modulePath - Path to the module\n * @param moduleName - Name of the module (for logging)\n */\nasync function ensureActivepiecesDepsLinked(modulePath: string, moduleName: string): Promise<void> {\n await linkActivepiecesDeps(modulePath, moduleName);\n}\n\n// Bits\nasync function ensureBitsDepsLinked(modulePath: string, moduleName: string): Promise<void> {\n await linkBitsDeps(modulePath, moduleName);\n}\n\n\n\n/**\n * Public function to ensure ActivePieces dependencies are installed.\n * This should be called before dynamically importing @activepieces/* modules.\n */\nexport async function ensureActivepiecesReady(): Promise<string | null> {\n return await ensureActivepiecesDepsInstalled();\n}\n\n// ============================================================================\n// n8n Dependency Linking\n// ============================================================================\n\n/**\n * Get the path to base node_modules where n8n packages should be installed.\n */\nfunction getN8nPackagesPath(): string | null {\n const basePath = path.join(getNodesBasePath(), 'node_modules');\n const testPath = path.join(basePath, 'n8n-workflow');\n if (fs.existsSync(testPath)) {\n return basePath;\n }\n return null;\n}\n\n/**\n * Ensure n8n peer dependencies are installed in the base node_modules.\n */\nasync function ensureN8nDepsInstalled(): Promise<string | null> {\n const basePath = getNodesBasePath();\n const baseNodeModules = path.join(basePath, 'node_modules');\n \n // Check if n8n-workflow is already installed\n const n8nWorkflowPath = path.join(baseNodeModules, 'n8n-workflow');\n if (fs.existsSync(n8nWorkflowPath)) {\n console.log(`\u2713 n8n-workflow already installed at ${baseNodeModules}`);\n return baseNodeModules;\n }\n \n console.log(`\uD83D\uDCE6 Installing n8n peer dependencies to ${basePath}...`);\n \n // ============================================================================\n // \u26A0\uFE0F LICENSE WARNING - n8n is NOT open source!\n // ============================================================================\n // n8n and its packages (n8n-workflow, n8n-core, n8n-nodes-base) are licensed\n // under the Sustainable Use License (SUL), which is NOT an open source license.\n // \n // You CANNOT:\n // - Redistribute n8n packages in commercial products without a license\n // - Offer n8n as a service without explicit permission\n // - Use n8n-nodes-base in production without proper licensing\n // \n // If you do not have a valid n8n license for your use case, you should:\n // 1. Use only Apache 2.0 / MIT licensed modules (ActivePieces pieces, Habits bits)\n // 2. Purchase an n8n license from https://n8n.io/pricing\n // 3. Remove n8n dependencies from your workflow\n // \n // See: https://github.com/n8n-io/n8n/blob/master/LICENSE.md\n // ============================================================================\n console.log(`\\n${'='.repeat(80)}`);\n console.log(`\u26A0\uFE0F LICENSE WARNING: n8n is NOT open source!`);\n console.log(`${'='.repeat(80)}`);\n console.log(`n8n packages are licensed under the Sustainable Use License (SUL).`);\n console.log(`You CANNOT redistribute or use n8n commercially without a license.`);\n console.log(`If you don't have a valid n8n license, you can't use this habit for non-personal usage.`);\n console.log(`Use Apache 2.0/MIT licensed alternatives: ActivePieces pieces or Habits bits.`);\n console.log(`${'='.repeat(80)}\\n`);\n\n try {\n // Install n8n-workflow, n8n-core, and moment-timezone to the base path\n await npmInstall('n8n-workflow n8n-core moment-timezone', { \n prefix: basePath, \n legacyPeerDeps: true, \n production: true,\n timeout: 300000\n });\n console.log(`\u2713 n8n peer dependencies installed`);\n return baseNodeModules;\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Failed to install n8n peer dependencies: ${error.message}`);\n return null;\n }\n}\n\n/**\n * Link n8n peer dependencies from base node_modules to a module.\n */\nasync function linkN8nDeps(modulePath: string, moduleName: string): Promise<void> {\n // First ensure n8n deps are installed\n const baseNodeModules = await ensureN8nDepsInstalled();\n \n if (!baseNodeModules) {\n console.warn(`\u26A0\uFE0F Could not find or install n8n peer dependencies`);\n return;\n }\n\n console.log(`\uD83D\uDD17 Linking n8n peer dependencies for ${moduleName}...`);\n \n // Link at module's own node_modules level\n const moduleNodeModules = path.join(modulePath, 'node_modules');\n if (!fs.existsSync(moduleNodeModules)) {\n fs.mkdirSync(moduleNodeModules, { recursive: true });\n }\n \n for (const dep of N8N_PEER_DEPS) {\n const sourcePackagePath = path.join(baseNodeModules, dep);\n const targetPackagePath = path.join(moduleNodeModules, dep);\n \n if (!fs.existsSync(sourcePackagePath)) {\n console.warn(`\u26A0\uFE0F Source package not found: ${sourcePackagePath}`);\n continue;\n }\n \n // Check if already linked or exists\n if (fs.existsSync(targetPackagePath)) {\n try {\n const stats = fs.lstatSync(targetPackagePath);\n if (stats.isSymbolicLink()) {\n console.log(`\u2713 ${dep} already linked`);\n continue;\n }\n // Remove existing if not a symlink\n fs.rmSync(targetPackagePath, { recursive: true, force: true });\n } catch (e) {\n // Ignore\n }\n }\n \n // Create symlink\n try {\n fs.symlinkSync(sourcePackagePath, targetPackagePath, 'dir');\n console.log(`\u2713 Linked ${dep}`);\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Failed to link ${dep}: ${error.message}`);\n }\n }\n}\n\n/**\n * Ensures n8n peer dependencies are linked after npm install.\n */\nasync function ensureN8nDepsLinked(modulePath: string, moduleName: string): Promise<void> {\n await linkN8nDeps(modulePath, moduleName);\n}\n\n\nexport interface ModuleDefinition {\n framework: string;\n source: 'github' | 'npm' | 'local' | 'link';\n repository: string; // GitHub URL for 'github' source, package name for 'npm'/'link' source, module name for 'local' source\n /** \n * Optional custom npm registry URL for 'npm' source.\n * If not provided, uses HABITS_NPM_REGISTRY_URL environment variable,\n * or falls back to https://registry.npmjs.org\n */\n registry?: string;\n}\n\nexport async function cloneModule(\n moduleDefinition: ModuleDefinition,\n targetDir: string\n): Promise<string> {\n const { repository, source } = moduleDefinition;\n const name = getModuleName(moduleDefinition);\n\n if (source !== 'github') {\n throw new Error(`cloneModule only supports GitHub sources, got: ${source}`);\n }\n\n if (!repository) {\n throw new Error(`Module ${name} has no repository URL`);\n }\n\n const modulePath = path.join(targetDir, name);\n\n // Check if already cloned\n if (fs.existsSync(modulePath)) {\n console.log(`\u2713 Module ${name} already cloned at ${modulePath}`);\n return modulePath;\n }\n\n console.log(`\uD83D\uDCE6 Cloning ${name} from ${repository}...`);\n\n try {\n // Create target directory if it doesn't exist\n if (!fs.existsSync(targetDir)) {\n fs.mkdirSync(targetDir, { recursive: true });\n }\n\n // Clone the repository\n const { stdout, stderr } = await execAsync(\n `git clone ${repository} ${modulePath}`,\n { cwd: targetDir }\n );\n\n if (stderr && !stderr.includes('Cloning into')) {\n console.warn(`Clone warnings: ${stderr}`);\n }\n\n console.log(`\u2713 Successfully cloned ${name}`);\n\n // Install dependencies if package.json exists\n if (fs.existsSync(path.join(modulePath, 'package.json'))) {\n console.log(`\uD83D\uDCE6 Installing dependencies for ${name}...`);\n try {\n // To get around \"zod\" related version-issues in activepieces, legacy peer deps is used\n await npmInstall(undefined, { cwd: modulePath, legacyPeerDeps: true, includePeer: true, timeout: 180000 });\n console.log(`\u2713 Dependencies installed for ${name}`);\n \n // Link ActivePieces peer dependencies if this is an activepieces or bits module\n if (moduleDefinition.framework === 'activepieces' ) {\n await ensureActivepiecesDepsLinked(modulePath, name);\n }\n if(moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(modulePath, name);\n }\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Warning: Failed to install dependencies for ${name}: ${error.message}`);\n // Don't fail the entire process, module might still work\n }\n }\n\n // Auto-detect subPath if needed (for activepieces modules)\n const subPath = await detectSubPath(modulePath, moduleDefinition.framework);\n const workingDir = subPath ? path.join(modulePath, subPath) : modulePath;\n\n return workingDir;\n } catch (error: any) {\n throw new Error(`Failed to clone ${name}: ${error.message}`);\n }\n}\n\nexport async function buildModule(\n moduleDefinition: ModuleDefinition,\n modulePath: string\n): Promise<void> {\n const name = getModuleName(moduleDefinition);\n\n // Run npm install --production\n console.log(`\uD83D\uDCE6 Installing production dependencies for ${name}...`)\n try {\n await npmInstall(undefined, { cwd: modulePath, legacyPeerDeps: true, includePeer: true, production: true, timeout: 120000 });\n \n // Link peer dependencies based on framework\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(modulePath, name);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(modulePath, name);\n }\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Warning: Failed to install production dependencies for ${name}: ${error.message}`);\n // Don't fail the entire process, module might still work\n }\n // Auto-detect build command\n const buildCommand = await detectBuildCommand(modulePath);\n \n if (!buildCommand) {\n console.log(`\u26A0\uFE0F No build command detected for ${name}, skipping build`);\n return;\n }\n\n // Check if already built by looking for common build outputs\n if (await isAlreadyBuilt(modulePath)) {\n console.log(`\u2713 Module ${name} already built`);\n return;\n }\n\n console.log(`\uD83D\uDD28 Building ${name} with command: ${buildCommand}`);\n\n try {\n const { stdout, stderr } = await execAsync(buildCommand, {\n cwd: modulePath,\n maxBuffer: 1024 * 1024 * 10, // 10MB buffer\n });\n\n if (stderr && !stderr.includes('npm warn')) {\n console.warn(`Build warnings for ${name}:`, stderr.substring(0, 500));\n }\n\n console.log(`\u2713 Successfully built ${name}`);\n } catch (error: any) {\n throw new Error(`Failed to build ${name}: ${error.message}`);\n }\n}\n\nexport async function ensureModuleReady(\n moduleDefinition: ModuleDefinition\n): Promise<string> {\n const moduleName = getModuleName(moduleDefinition);\n \n console.log(`\\n\uD83D\uDD0D ensureModuleReady called:`);\n console.log(` Module: ${moduleName}`);\n console.log(` Source: ${moduleDefinition.source}`);\n console.log(` Repository: ${moduleDefinition.repository}`);\n console.log(` Framework: ${moduleDefinition.framework}`);\n \n if (moduleDefinition.source === 'github') {\n console.log(`\\n\uD83D\uDCC2 Processing GitHub module: ${moduleName}`);\n // Clone the module from GitHub to framework directory\n const baseDir = getNodesPath(moduleDefinition.framework);\n const modulePath = path.join(baseDir, moduleName);\n console.log(` Base directory: ${baseDir}`);\n console.log(` Module path: ${modulePath}`);\n \n // Check if already exists\n if (fs.existsSync(modulePath)) {\n console.log(`\u2713 GitHub module ${moduleName} already exists at ${modulePath}`);\n // Still check if built\n if (!await isAlreadyBuilt(modulePath)) {\n await buildModule(moduleDefinition, modulePath);\n }\n return modulePath;\n }\n \n const clonedPath = await cloneModule(moduleDefinition, baseDir);\n \n // Build the module\n await buildModule(moduleDefinition, clonedPath);\n \n return clonedPath;\n } else if (moduleDefinition.source === 'npm') {\n console.log(`\\n\uD83D\uDCE6 Processing npm module: ${moduleName}`);\n // Install the module from npm to nodes/{framework} directory\n const baseDir = getNodesPath(moduleDefinition.framework);\n const modulePath = path.join(baseDir, moduleName);\n console.log(` Base directory: ${baseDir}`);\n console.log(` Module path: ${modulePath}`);\n \n // Check if already exists\n if (fs.existsSync(modulePath)) {\n console.log(`\u2713 npm module ${moduleName} already exists at ${modulePath}`);\n // Ensure peer dependencies are linked even for existing modules\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(modulePath, moduleName);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(modulePath, moduleName);\n } else if (moduleDefinition.framework === 'n8n') {\n await ensureN8nDepsLinked(modulePath, moduleName);\n }\n return modulePath;\n }\n \n const installedPath = await installNpmModule(moduleDefinition, baseDir);\n \n return installedPath;\n } else if (moduleDefinition.source === 'local') {\n // Local modules are in the workspace's nodes/{framework} directory\n // We need to find them and install them to the nodes base path\n const targetModulePath = getModuleFullPath(moduleDefinition.framework, moduleName);\n \n // Check if already installed in target location\n if (fs.existsSync(targetModulePath)) {\n console.log(`\u2713 Local module ${moduleName} already installed at ${targetModulePath}`);\n // Ensure peer dependencies are available even for existing modules\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(targetModulePath, moduleName);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(targetModulePath, moduleName);\n } else if (moduleDefinition.framework === 'n8n') {\n await ensureN8nDepsLinked(targetModulePath, moduleName);\n }\n return targetModulePath;\n }\n \n // Find the local module in the workspace\n const localSourcePath = getLocalModulePath(moduleDefinition.framework, moduleName);\n \n if (!localSourcePath) {\n throw new Error(\n `Local module not found: ${moduleName}. ` +\n `Searched in nodes/${moduleDefinition.framework}/ directory. ` +\n `You can also set HABITS_LOCAL_NODES_PATH environment variable.`\n );\n }\n \n console.log(`\\n\uD83D\uDCE6 Installing local module: ${moduleName}`);\n console.log(` Source: ${localSourcePath}`);\n console.log(` Target: ${targetModulePath}`);\n \n // Ensure target parent directory exists\n const targetParentDir = path.dirname(targetModulePath);\n if (!fs.existsSync(targetParentDir)) {\n fs.mkdirSync(targetParentDir, { recursive: true });\n }\n \n // Copy the local module to the target location\n fs.cpSync(localSourcePath, targetModulePath, { recursive: true });\n \n // Install dependencies for the module\n if (fs.existsSync(path.join(targetModulePath, 'package.json'))) {\n console.log(`\uD83D\uDCE6 Installing dependencies for ${moduleName}...`);\n try {\n await npmInstall(undefined, { cwd: targetModulePath, legacyPeerDeps: true, includePeer: true, timeout: 120000 });\n console.log(`\u2713 Dependencies installed for ${moduleName}`);\n \n // Link peer dependencies based on framework\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(targetModulePath, moduleName);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(targetModulePath, moduleName);\n }\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Warning: Failed to install dependencies for ${moduleName}: ${error.message}`);\n // Still try to link peer dependencies\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(targetModulePath, moduleName);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(targetModulePath, moduleName);\n }\n }\n } else {\n // No package.json, but still try to link peer deps\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(targetModulePath, moduleName);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(targetModulePath, moduleName);\n }\n }\n \n console.log(`\u2713 Local module ${moduleName} installed at ${targetModulePath}`);\n return targetModulePath;\n } else if (moduleDefinition.source === 'link') {\n console.log(`\\n\uD83D\uDD17 Processing linked module: ${moduleName}`);\n // Use npm link to use a globally linked package\n const baseDir = getNodesPath(moduleDefinition.framework);\n const modulePath = path.join(baseDir, moduleName);\n console.log(` Base directory: ${baseDir}`);\n console.log(` Module path: ${modulePath}`);\n \n // Check if already linked/exists\n if (fs.existsSync(modulePath)) {\n console.log(`\u2713 Linked module ${moduleName} already exists at ${modulePath}`);\n // Ensure peer dependencies are linked even for existing modules\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(modulePath, moduleName);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(modulePath, moduleName);\n } else if (moduleDefinition.framework === 'n8n') {\n await ensureN8nDepsLinked(modulePath, moduleName);\n }\n return modulePath;\n }\n \n const linkedPath = await linkNpmModule(moduleDefinition, baseDir);\n \n return linkedPath;\n } else {\n throw new Error(`Unknown source type: ${moduleDefinition.source}`);\n }\n}\n\n// Helper function to detect subPath for frameworks like activepieces\nasync function detectSubPath(modulePath: string, framework: string): Promise<string | null> {\n if (framework === 'activepieces' || framework === 'bits') {\n // Check for common activepieces structure\n const possibleSubPaths = [\n 'packages/pieces/community',\n 'packages/pieces',\n 'pieces/community',\n 'pieces'\n ];\n \n for (const subPath of possibleSubPaths) {\n const fullPath = path.join(modulePath, subPath);\n if (fs.existsSync(fullPath)) {\n // Check if there are piece folders in this path\n try {\n const items = fs.readdirSync(fullPath);\n if (items.length > 0) {\n return subPath;\n }\n } catch (error) {\n continue;\n }\n }\n }\n }\n return null;\n}\n\n// Helper function to detect build command from package.json\nasync function detectBuildCommand(modulePath: string): Promise<string | null> {\n const packageJsonPath = path.join(modulePath, 'package.json');\n \n if (!fs.existsSync(packageJsonPath)) {\n return null;\n }\n\n try {\n const packageJson = JSON.parse(fs.readFileSync(packageJsonPath, 'utf-8'));\n const scripts = packageJson.scripts || {};\n\n // Try common build script names in order of preference\n const buildScriptNames = ['build', 'compile', 'tsc', 'webpack', 'rollup'];\n \n for (const scriptName of buildScriptNames) {\n if (scripts[scriptName]) {\n return `npm run ${scriptName}`;\n }\n }\n\n // Fallback: if no build script, run install only\n return 'npm install';\n } catch (error) {\n return 'npm install';\n }\n}\n\n// Helper function to check if module is already built\nasync function isAlreadyBuilt(modulePath: string): Promise<boolean> {\n const commonBuildDirs = ['dist', 'build', 'lib', 'out'];\n const commonMainFiles = [\n 'dist/index.js',\n 'dist/main.js', \n 'dist/nodes',\n 'build/index.js',\n 'lib/index.js',\n 'out/index.js'\n ];\n\n // Check for build directories with content\n for (const buildDir of commonBuildDirs) {\n const buildDirPath = path.join(modulePath, buildDir);\n if (fs.existsSync(buildDirPath)) {\n try {\n const items = fs.readdirSync(buildDirPath);\n if (items.length > 0) {\n return true;\n }\n } catch (error) {\n continue;\n }\n }\n }\n\n // Check for main files\n for (const mainFile of commonMainFiles) {\n const mainFilePath = path.join(modulePath, mainFile);\n if (fs.existsSync(mainFilePath)) {\n return true;\n }\n }\n\n return false;\n}\n\n/**\n * Fix package.json main entry if it points to .ts but .js exists.\n * This handles packages that were incorrectly published with TypeScript as main entry.\n */\nasync function fixPackageJsonMainEntry(modulePath: string): Promise<void> {\n const packageJsonPath = path.join(modulePath, 'package.json');\n if (!fs.existsSync(packageJsonPath)) {\n return;\n }\n \n try {\n const packageJson = JSON.parse(fs.readFileSync(packageJsonPath, 'utf-8'));\n const mainEntry = packageJson.main;\n \n if (mainEntry && mainEntry.endsWith('.ts')) {\n const tsPath = path.join(modulePath, mainEntry);\n const jsPath = tsPath.replace(/\\.ts$/, '.js');\n \n // If .ts doesn't exist but .js does, fix the main entry\n if (!fs.existsSync(tsPath) && fs.existsSync(jsPath)) {\n const newMain = mainEntry.replace(/\\.ts$/, '.js');\n packageJson.main = newMain;\n if (packageJson.types && packageJson.types.endsWith('.ts')) {\n packageJson.types = packageJson.types.replace(/\\.ts$/, '.d.ts');\n }\n fs.writeFileSync(packageJsonPath, JSON.stringify(packageJson, null, 2));\n console.log(`\uD83D\uDD27 Fixed package.json main entry: ${mainEntry} -> ${newMain}`);\n }\n }\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Failed to fix package.json main entry: ${error.message}`);\n }\n}\n\n// Install npm module to local directory\nasync function installNpmModule(\n moduleDefinition: ModuleDefinition,\n targetDir: string\n): Promise<string> {\n const { repository: packageName, registry: definedRegistry } = moduleDefinition;\n const name = getModuleName(moduleDefinition);\n \n // Determine registry URL: module definition > environment variable > default (npmjs)\n const registry = definedRegistry || process.env.HABITS_NPM_REGISTRY_URL || undefined;\n \n console.log(`\\n\uD83D\uDCE6 installNpmModule called:`);\n console.log(` Package name: ${packageName}`);\n console.log(` Module name: ${name}`);\n console.log(` Target dir: ${targetDir}`);\n console.log(` Registry: ${registry || 'https://registry.npmjs.org (default)'}`);\n \n if (!packageName) {\n throw new Error(`Module ${name} has no package name`);\n }\n \n // Validate that this is not a GitHub URL being passed as npm package\n if (packageName.includes('github.com') || packageName.startsWith('git@') || packageName.startsWith('https://')) {\n throw new Error(`Invalid npm package name: ${packageName}. This looks like a GitHub URL. Use source: 'github' instead.`);\n }\n\n const modulePath = path.join(targetDir, name);\n console.log(` Full module path: ${modulePath}`);\n\n // Check if already installed\n if (fs.existsSync(modulePath)) {\n console.log(`\u2713 Module ${name} already installed at ${modulePath}`);\n return modulePath;\n }\n const prefix = getNodesBasePath();\n console.log(`\uD83D\uDCE6 Installing ${name} from npm registry (${packageName}) to ${prefix}...`);\n\n try {\n // Create target directory if it doesn't exist\n if (!fs.existsSync(targetDir)) {\n fs.mkdirSync(targetDir, { recursive: true });\n }\n\n // Ensure prefix directory has a package.json (required for npm install)\n const prefixPackageJson = path.join(prefix, 'package.json');\n if (!fs.existsSync(prefixPackageJson)) {\n fs.mkdirSync(prefix, { recursive: true });\n fs.writeFileSync(prefixPackageJson, JSON.stringify({ \n name: 'habits-nodes', \n version: '1.0.0', \n private: true\n }, null, 2));\n }\n\n // Install directly to prefix with legacyPeerDeps and production mode to minimize dependencies\n const { stdout, stderr } = await npmInstall(packageName, { \n prefix, \n legacyPeerDeps: true, \n production: true,\n timeout: 300000, // 5 minute timeout\n registry // Use custom registry if provided\n });\n\n if (stderr && !stderr.includes('npm warn')) {\n console.warn(`Install warnings: ${stderr}`);\n }\n\n // Package is now installed directly at prefix/node_modules/package-name\n // Verify installation\n if (!fs.existsSync(modulePath)) {\n throw new Error(`Package ${packageName} was not installed correctly at ${modulePath}`);\n }\n\n // Fix package.json if main entry points to .ts but .js exists\n await fixPackageJsonMainEntry(modulePath);\n\n // Link peer dependencies based on framework\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(modulePath, name);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(modulePath, name);\n } else if (moduleDefinition.framework === 'n8n') {\n await ensureN8nDepsLinked(modulePath, name);\n }\n\n console.log(`\u2713 Successfully installed ${name} from npm at ${modulePath}`);\n return modulePath;\n } catch (error: any) {\n throw new Error(`Failed to install ${name}: ${error.message}`);\n }\n}\n\n// Link a globally linked npm module to local directory\nasync function linkNpmModule(\n moduleDefinition: ModuleDefinition,\n targetDir: string\n): Promise<string> {\n const { repository: packageName } = moduleDefinition;\n const name = getModuleName(moduleDefinition);\n \n console.log(`\\n\uD83D\uDD17 linkNpmModule called:`);\n console.log(` Package name: ${packageName}`);\n console.log(` Module name: ${name}`);\n console.log(` Target dir: ${targetDir}`);\n \n if (!packageName) {\n throw new Error(`Module ${name} has no package name`);\n }\n\n const modulePath = path.join(targetDir, name);\n console.log(` Full module path: ${modulePath}`);\n\n // Check if already linked\n if (fs.existsSync(modulePath)) {\n console.log(`\u2713 Module ${name} already linked at ${modulePath}`);\n return modulePath;\n }\n\n const prefix = getNodesBasePath();\n console.log(`\uD83D\uDD17 Linking ${name} from global npm link (${packageName}) to ${prefix}...`);\n\n try {\n // Create target directory if it doesn't exist\n if (!fs.existsSync(targetDir)) {\n fs.mkdirSync(targetDir, { recursive: true });\n }\n\n // Ensure prefix directory has a package.json (required for npm link)\n const prefixPackageJson = path.join(prefix, 'package.json');\n if (!fs.existsSync(prefixPackageJson)) {\n fs.mkdirSync(prefix, { recursive: true });\n fs.writeFileSync(prefixPackageJson, JSON.stringify({ \n name: 'habits-nodes', \n version: '1.0.0', \n private: true\n }, null, 2));\n }\n\n // Use npm link to link the globally linked package\n const linkCommand = `npm link ${packageName}`;\n console.log(`Executing link command: ${linkCommand}`);\n \n const { stdout, stderr } = await execAsync(linkCommand, {\n cwd: prefix,\n timeout: 60000 // 1 minute timeout\n });\n\n if (stderr && !stderr.includes('npm warn') && !stderr.includes('added')) {\n console.warn(`Link warnings: ${stderr}`);\n }\n\n // Verify the link was created\n if (!fs.existsSync(modulePath)) {\n throw new Error(`Package ${packageName} was not linked correctly at ${modulePath}`);\n }\n\n // Fix package.json if main entry points to .ts but .js exists\n await fixPackageJsonMainEntry(modulePath);\n\n // Link peer dependencies based on framework\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(modulePath, name);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(modulePath, name);\n } else if (moduleDefinition.framework === 'n8n') {\n await ensureN8nDepsLinked(modulePath, name);\n }\n\n console.log(`\u2713 Successfully linked ${name} at ${modulePath}`);\n return modulePath;\n } catch (error: any) {\n throw new Error(`Failed to link ${name}: ${error.message}`);\n }\n}\n\nexport function getModulePath(moduleDefinition: ModuleDefinition): string {\n // Return the correct path based on source type\n const moduleName = getModuleName(moduleDefinition);\n \n // Get the target path (where modules are installed)\n const targetPath = getModuleFullPath(moduleDefinition.framework, moduleName);\n \n // For local or link source, if target doesn't exist, return the source path\n if ((moduleDefinition.source === 'local' || moduleDefinition.source === 'link') && !fs.existsSync(targetPath)) {\n const localPath = getLocalModulePath(moduleDefinition.framework, moduleName);\n if (localPath && fs.existsSync(localPath)) {\n return localPath;\n }\n }\n \n // Check if package.json exists at the target path\n // If not, this might be a content-addressable store structure where the actual package\n // is in a hidden directory like .piece-name-hash\n const packageJsonPath = path.join(targetPath, 'package.json');\n if (!fs.existsSync(packageJsonPath) && fs.existsSync(targetPath)) {\n const pnpmStorePath = findPnpmStorePath(targetPath, moduleName);\n if (pnpmStorePath) {\n return pnpmStorePath;\n }\n }\n \n return targetPath;\n}\n\n/**\n * Find the actual module path in a content-addressable store.\n * Some package managers create hidden directories like `.piece-name-hash` that contain the actual package.\n * \n * @param expectedPath - The expected module path (e.g., /tmp/habits-nodes/node_modules/@activepieces/piece-openai)\n * @param moduleName - The module name (e.g., @activepieces/piece-openai)\n * @returns The actual path with package.json, or null if not found\n */\nfunction findPnpmStorePath(expectedPath: string, moduleName: string): string | null {\n const parentDir = path.dirname(expectedPath);\n \n if (!fs.existsSync(parentDir)) {\n return null;\n }\n \n // Extract the base package name without scope\n // e.g., \"@activepieces/piece-openai\" -> \"piece-openai\"\n const baseName = moduleName.includes('/') ? moduleName.split('/').pop()! : moduleName;\n \n try {\n const entries = fs.readdirSync(parentDir, { withFileTypes: true });\n \n // Look for hidden directories that start with the package name\n // Some package managers create directories like \".piece-openai-kB47Gs6C\"\n for (const entry of entries) {\n if (entry.isDirectory() && entry.name.startsWith(`.${baseName}`)) {\n const candidatePath = path.join(parentDir, entry.name);\n const candidatePackageJson = path.join(candidatePath, 'package.json');\n \n if (fs.existsSync(candidatePackageJson)) {\n console.log(`\uD83D\uDCE6 Found store path for ${moduleName}: ${candidatePath}`);\n return candidatePath;\n }\n }\n }\n } catch (error) {\n // Ignore errors reading directory\n }\n \n return null;\n}\n\nexport function getModuleMainFile(\n moduleDefinition: ModuleDefinition\n): string | null {\n const modulePath = getModulePath(moduleDefinition);\n\n // First, try to read the main entry from package.json\n const packageJsonPath = path.join(modulePath, 'package.json');\n if (fs.existsSync(packageJsonPath)) {\n try {\n const packageJson = JSON.parse(fs.readFileSync(packageJsonPath, 'utf-8'));\n \n // Try \"main\" field first, then \"module\", then \"exports\"\n let mainEntry = packageJson.main || packageJson.module;\n \n // Handle exports field (common in modern packages)\n if (!mainEntry && packageJson.exports) {\n if (typeof packageJson.exports === 'string') {\n mainEntry = packageJson.exports;\n } else if (packageJson.exports['.']) {\n const dotExport = packageJson.exports['.'];\n if (typeof dotExport === 'string') {\n mainEntry = dotExport;\n } else if (dotExport.require) {\n mainEntry = dotExport.require;\n } else if (dotExport.import) {\n mainEntry = dotExport.import;\n } else if (dotExport.default) {\n mainEntry = dotExport.default;\n }\n }\n }\n \n if (mainEntry) {\n // Remove leading ./ if present\n mainEntry = mainEntry.replace(/^\\.\\//, '');\n let mainPath = path.join(modulePath, mainEntry);\n \n // If main entry is a .ts file but .js exists, use .js instead\n // (handles packages with incorrect main entry pointing to TypeScript)\n if (mainEntry.endsWith('.ts') && !fs.existsSync(mainPath)) {\n const jsPath = mainPath.replace(/\\.ts$/, '.js');\n if (fs.existsSync(jsPath)) {\n console.log(`\u26A0\uFE0F Package.json main points to .ts but .js exists, using .js: ${jsPath}`);\n mainPath = jsPath;\n }\n }\n \n if (fs.existsSync(mainPath)) {\n console.log(`\u2713 Found main file from package.json for module: ${moduleDefinition.repository} at path: ${mainPath}`);\n return mainPath;\n }\n }\n } catch (error) {\n console.warn(`\u26A0\uFE0F Failed to parse package.json for ${moduleDefinition.repository}`);\n }\n }\n\n // Fallback: Try common patterns (including TypeScript sources for ts-node/tsx execution)\n const commonPaths = [\n 'dist/index.js',\n 'dist/main.js',\n 'dist/nodes',\n 'build/index.js',\n 'lib/index.js',\n 'out/index.js',\n // That's where activepieces modules are usually stored\n 'src/index.js',\n 'index.js',\n 'main.js',\n ];\n\n for (const commonPath of commonPaths) {\n const fullPath = path.join(modulePath, commonPath);\n if (fs.existsSync(fullPath)) {\n console.log(`\u2713 Detected main file for module: ${moduleDefinition.repository} at path: ${fullPath}`);\n return fullPath;\n }\n }\n console.log(`\u26A0\uFE0F Could not determine main file for module: ${moduleDefinition.repository} at path: ${modulePath}`);\n return null;\n}\n", "import * as fs from '@ha-bits/bindings/fs';\nimport * as path from '@ha-bits/bindings/path';\nimport { ensureModuleReady, getModuleMainFile, getModulePath } from './moduleCloner';\nimport { npmInstall, getLocalModulePath } from './utils';\nimport { LoggerFactory } from '@ha-bits/core/logger';\n\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// Bundled Modules Registry\n// ============================================================================\n\n/**\n * Registry for pre-bundled modules.\n * In browser/IIFE bundles, modules are bundled at build time and registered here\n * so ensureModuleInstalled can skip filesystem operations.\n */\nconst bundledModulesRegistry: Map<string, any> = new Map();\n\n/**\n * Register a pre-bundled module.\n * Call this at bundle initialization to register modules that are already\n * included in the bundle and don't need to be installed.\n * \n * @param moduleName The module name (e.g., '@ha-bits/bit-intersect')\n * @param moduleExports The module's exports object\n */\nexport function registerBundledModule(moduleName: string, moduleExports: any): void {\n bundledModulesRegistry.set(moduleName, moduleExports);\n console.log(`\uD83D\uDCE6 Registered bundled module: ${moduleName}`);\n}\n\n/**\n * Check if a module is registered as bundled.\n * @param moduleName The module name to check\n * @returns The module exports if bundled, undefined otherwise\n */\nexport function getBundledModule(moduleName: string): any | undefined {\n return bundledModulesRegistry.get(moduleName);\n}\n\n/**\n * Check if a module is available as a bundled module.\n * @param moduleName The module name to check\n */\nexport function isBundledModule(moduleName: string): boolean {\n return bundledModulesRegistry.has(moduleName);\n}\n\ninterface ModuleDefinition {\n framework: string;\n source: 'github' | 'npm' | 'local' | 'link';\n repository: string; // GitHub URL for 'github' source, package name for 'npm'/'link' source, module name for 'local' source\n}\n\ninterface ModulesConfig {\n modules: ModuleDefinition[];\n}\n\n/**\n * Infers the module name from the repository URL or npm package name.\n * For GitHub: extracts the last part of the URL (e.g., https://github.com/user/repo.git -> repo)\n * For npm: uses the whole package name as the ID/Name\n */\nexport function getModuleName(moduleDefinition: ModuleDefinition): string {\n if (moduleDefinition.source === 'github') {\n // Extract repository name from GitHub URL\n // Handle formats like:\n // - https://github.com/user/repo.git\n // - https://github.com/user/repo\n // - git@github.com:user/repo.git\n const url = moduleDefinition.repository;\n \n // Remove .git suffix if present\n let repoName = url.replace(/\\.git$/, '');\n \n // Extract the last part after the last slash\n const parts = repoName.split('/');\n repoName = parts[parts.length - 1];\n \n return repoName;\n } else if (moduleDefinition.source === 'npm' || moduleDefinition.source === 'link') {\n // For npm and link, use the whole package name as the ID/Name\n return moduleDefinition.repository;\n } else if (moduleDefinition.source === 'local') {\n // For local, use the module name as-is\n return moduleDefinition.repository;\n } else {\n throw new Error(`Unknown source type: ${moduleDefinition.source}`);\n }\n}\n\nconst MODULES_CONFIG_PATH = path.join(process.cwd(), 'modules.json');\n\n/**\n * Modules operation mode:\n * - 'restricted': Only allows using modules already defined in modules.json\n * - 'open': Allows adding any module and appends it to modules.json if it doesn't exist\n */\nexport type ModulesMode = 'restricted' | 'open';\n\n/**\n * Get the current modules mode from environment variable.\n * Default is 'restricted' for security.\n * Set HABITS_MODULES_MODE=open to allow adding new modules.\n */\nexport function getModulesMode(): ModulesMode {\n const mode = process.env.HABITS_MODULES_MODE?.toLowerCase();\n if (mode === 'open') {\n return 'open';\n }\n return 'restricted';\n}\n\n/**\n * Check if a module exists in modules.json\n */\nexport function moduleExists(moduleDefinition: ModuleDefinition): boolean {\n const config = loadModulesConfig();\n const moduleName = getModuleName(moduleDefinition);\n \n return config.modules.some(\n m => m.framework === moduleDefinition.framework && getModuleName(m) === moduleName\n );\n}\n\n/**\n * Get a module from modules.json by framework and name\n */\nexport function getModuleFromConfig(framework: string, moduleName: string): ModuleDefinition | undefined {\n const config = loadModulesConfig();\n return config.modules.find(\n m => m.framework === framework && getModuleName(m) === moduleName\n );\n}\n\nexport function loadModulesConfig(): ModulesConfig {\n try {\n const configData = fs.readFileSync(MODULES_CONFIG_PATH, 'utf-8');\n return JSON.parse(configData);\n } catch (error: any) {\n throw new Error(`Failed to load modules.json: ${error.message}`);\n }\n}\n\nexport function saveModulesConfig(config: ModulesConfig): void {\n try {\n const configData = JSON.stringify(config, null, 2);\n fs.writeFileSync(MODULES_CONFIG_PATH, configData, 'utf-8');\n } catch (error: any) {\n throw new Error(`Failed to save modules.json: ${error.message}`);\n }\n}\n\nexport interface AddModuleOptions {\n /** Override the mode check - allows forcing addition even in restricted mode */\n force?: boolean;\n /** Skip saving to modules.json (useful for temporary modules) */\n skipSave?: boolean;\n}\n\n/**\n * Add a module to modules.json.\n * \n * Behavior depends on the modules mode (HABITS_MODULES_MODE env var):\n * - 'restricted' (default): Will throw an error. Modules must be pre-defined in modules.json.\n * - 'open': Will add the module to modules.json if it doesn't exist.\n * \n * @param moduleDefinition - The module definition to add\n * @param options - Optional settings for the add operation\n * @throws Error if in restricted mode and force is not set\n * @throws Error if module already exists\n */\nexport function addModule(moduleDefinition: ModuleDefinition, options: AddModuleOptions = {}): void {\n const mode = getModulesMode();\n const moduleName = getModuleName(moduleDefinition);\n \n // Check mode restrictions\n if (mode === 'restricted' && !options.force) {\n throw new Error(\n `Cannot add module '${moduleName}' in restricted mode. ` +\n `Either add it manually to modules.json or set HABITS_MODULES_MODE=open`\n );\n }\n \n const config = loadModulesConfig();\n \n // Check if module already exists (by repository to prevent duplicates)\n const existingModule = config.modules.find(\n m => m.repository === moduleDefinition.repository\n );\n \n if (existingModule) {\n logger.log(`\u23ED\uFE0F Module '${moduleName}' already exists in modules.json, skipping`);\n return;\n }\n \n // Validate source type\n if (!['github', 'npm', 'local'].includes(moduleDefinition.source)) {\n throw new Error(`Invalid source type: ${moduleDefinition.source}. Must be 'github', 'npm', or 'local'`);\n }\n \n if (!options.skipSave) {\n config.modules.push(moduleDefinition);\n saveModulesConfig(config);\n logger.log(`\u2705 Module '${moduleName}' added to modules.json`);\n }\n}\n\n/**\n * Ensure a module is available for use.\n * In restricted mode: module must already exist in modules.json\n * In open mode: adds the module to modules.json if it doesn't exist\n * \n * @param moduleDefinition - The module definition to ensure\n * @returns The module definition (either existing or newly added)\n */\nexport function ensureModuleInConfig(moduleDefinition: ModuleDefinition): ModuleDefinition {\n const mode = getModulesMode();\n const moduleName = getModuleName(moduleDefinition);\n \n // Check if module exists\n const existingModule = getModuleFromConfig(moduleDefinition.framework, moduleName);\n \n if (existingModule) {\n return existingModule;\n }\n \n // Module doesn't exist\n if (mode === 'restricted') {\n throw new Error(\n `Module '${moduleName}' not found in modules.json. ` +\n `In restricted mode, only pre-defined modules can be used. ` +\n `Add it to modules.json or set HABITS_MODULES_MODE=open`\n );\n }\n \n // Open mode: add the module\n addModule(moduleDefinition);\n return moduleDefinition;\n}\n\nexport function getModuleByPath(modulePath: string): ModuleDefinition | undefined {\n const config = loadModulesConfig();\n const [framework, ...nameParts] = modulePath.split('/');\n const name = nameParts.join('/');\n\n return config.modules.find(\n (m) => m.framework === framework && getModuleName(m) === name\n );\n}\n\nexport function isModuleCloned(moduleDefinition: ModuleDefinition): boolean {\n const modulePath = getModulePath(moduleDefinition);\n \n // Check if installed in target location\n if (fs.existsSync(modulePath)) {\n return true;\n }\n \n // For local or link source, also check if it exists at the source location\n if (moduleDefinition.source === 'local' || moduleDefinition.source === 'link') {\n const moduleName = getModuleName(moduleDefinition);\n const localPath = getLocalModulePath(moduleDefinition.framework, moduleName);\n if (localPath && fs.existsSync(localPath)) {\n return true;\n }\n }\n \n return false;\n}\n\nexport function isModuleBuilt(moduleDefinition: ModuleDefinition): boolean {\n // Determine which path to check\n let modulePath = getModulePath(moduleDefinition);\n \n // For local or link source, check source location if target doesn't exist\n if ((moduleDefinition.source === 'local' || moduleDefinition.source === 'link') && !fs.existsSync(modulePath)) {\n const moduleName = getModuleName(moduleDefinition);\n const localPath = getLocalModulePath(moduleDefinition.framework, moduleName);\n if (localPath) {\n modulePath = localPath;\n }\n }\n \n if (!fs.existsSync(modulePath)) {\n return false;\n }\n\n // Check for common build outputs\n const commonBuildDirs = ['dist', 'build', 'lib', 'out'];\n const commonMainFiles = [\n 'dist/index.js',\n 'dist/main.js', \n 'dist/nodes',\n 'build/index.js',\n 'lib/index.js',\n 'out/index.js',\n 'src/index.js',\n ];\n\n // Check for build directories with content\n for (const buildDir of commonBuildDirs) {\n const buildDirPath = path.join(modulePath, buildDir);\n const exists = fs.existsSync(buildDirPath);\n if (exists) {\n try {\n const items = fs.readdirSync(buildDirPath);\n if (items.length > 0) {\n return true;\n }\n } catch (error) {\n continue;\n }\n }\n }\n\n // Check for main files\n for (const mainFile of commonMainFiles) {\n const mainFilePath = path.join(modulePath, mainFile);\n if (fs.existsSync(mainFilePath)) {\n return true;\n }\n }\n\n return false;\n}\n\nexport async function ensureModuleInstalled(\n moduleDefinition: ModuleDefinition\n): Promise<string> {\n const moduleName = getModuleName(moduleDefinition);\n \n // Check bundled modules registry first (for browser/IIFE bundles)\n if (isBundledModule(moduleDefinition.repository)) {\n console.log(`\u2713 Module ${moduleName} is pre-bundled, skipping installation\\n`);\n return moduleDefinition.repository; // Return module name as \"path\" for bundled modules\n }\n \n // In Node.js environments, try require as fallback\n if (typeof require !== 'undefined') {\n try {\n require(moduleDefinition.repository);\n console.log(`\u2713 Module ${moduleName} already available via require\\n`);\n return moduleDefinition.repository;\n } catch {\n // Module not available via require, continue with installation\n }\n }\n\n console.log(`\\n\uD83D\uDD0D ensureModuleInstalled called:`);\n console.log(` Module name: ${moduleName}`);\n console.log(` Source: ${moduleDefinition.source}`);\n console.log(` Repository: ${moduleDefinition.repository}`);\n console.log(` Framework: ${moduleDefinition.framework}`);\n\n try {\n // Use the cloner to ensure module is ready\n const modulePath = await ensureModuleReady(moduleDefinition);\n console.log(`\u2713 Module ${moduleName} is ready at: ${modulePath}\\n`);\n return modulePath;\n } catch (error: any) {\n console.error(`\u2717 Failed to prepare module ${moduleName}: ${error.message}\\n`);\n throw error;\n }\n}\n\nexport async function installModule(packageName: string, version: string = 'latest'): Promise<void> {\n const packageSpec = version === 'latest' ? packageName : `${packageName}@${version}`;\n\n try {\n console.log(`Installing ${packageSpec} via npm...`);\n const { stdout, stderr } = await npmInstall(packageSpec, { saveOptional: true });\n\n if (stderr && !stderr.includes('npm warn')) {\n console.error(`Installation warnings: ${stderr}`);\n }\n\n console.log(`Successfully installed ${packageSpec}`);\n } catch (error: any) {\n throw new Error(`Failed to install ${packageSpec}: ${error.message}`);\n }\n}\n\nexport async function listAvailableModules(framework?: string): Promise<any[]> {\n const config = loadModulesConfig();\n let modules = config.modules;\n\n if (framework) {\n modules = modules.filter((m) => m.framework === framework);\n }\n\n return modules.map((m) => {\n const moduleName = getModuleName(m);\n return {\n framework: m.framework,\n name: moduleName,\n source: m.source,\n path: `${m.framework}/${moduleName}`,\n repository: m.repository,\n cloned: isModuleCloned(m),\n built: isModuleBuilt(m),\n installed: isModuleCloned(m) && isModuleBuilt(m),\n };\n });\n}\n", "/**\n * Execution Context Factory for n8n nodes\n * Creates the IExecuteFunctions context that n8n nodes expect\n */\n\nimport * as path from 'path';\nimport {\n INodeType,\n INodeExecutionData,\n IExecuteFunctions,\n IHttpRequestOptions,\n INode,\n IDataObject,\n ICredentialType,\n} from './types';\nimport { ModuleDefinition } from '../utils/moduleCloner';\nimport { httpRequest } from './httpRequest';\nimport { loadCredentialType, applyCredentialAuthentication, applyFallbackAuthentication } from './credentialLoader';\nimport { LoggerFactory } from '@ha-bits/core/logger';\n\nconst logger = LoggerFactory.getRoot();\n\nexport interface N8nNodeExecutionOptions {\n inputData?: INodeExecutionData[];\n credentials?: Record<string, any>;\n}\n\n/**\n * Create a real execution context for n8n nodes\n * This provides all the methods that nodes expect to have access to\n */\nexport function createExecutionContext(\n node: INodeType,\n params: Record<string, any>,\n options?: N8nNodeExecutionOptions\n): IExecuteFunctions {\n const inputData: INodeExecutionData[] = options?.inputData || params.inputData || [{ json: params }];\n const credentials = options?.credentials || params.credentials || {};\n\n // Create the node configuration object\n const version = node.description?.version;\n const typeVersion = Array.isArray(version) ? version[0] : (version || 1);\n \n const nodeConfig: INode = {\n id: params.nodeId || 'node-1',\n name: node.description?.name || 'unknown',\n type: node.description?.name || 'unknown',\n typeVersion,\n position: [0, 0],\n parameters: params,\n credentials: {},\n };\n\n // Build the execution context\n const context: IExecuteFunctions = {\n // Get input data from previous nodes\n getInputData: (inputIndex: number = 0): INodeExecutionData[] => {\n return inputData;\n },\n\n // Get node parameter value\n getNodeParameter: (\n parameterName: string,\n itemIndex: number = 0,\n fallbackValue?: any,\n options?: any\n ): any => {\n // Handle nested parameters like 'options.timeout'\n const parts = parameterName.split('.');\n let value: any = params;\n \n for (const part of parts) {\n if (value && typeof value === 'object' && part in value) {\n value = value[part];\n } else {\n value = undefined;\n break;\n }\n }\n\n if (value !== undefined) {\n return value;\n }\n\n if (fallbackValue !== undefined) {\n return fallbackValue;\n }\n\n // For some parameters, return sensible defaults\n const defaultValues: Record<string, any> = {\n 'options': {},\n 'authentication': 'none',\n 'sendHeaders': false,\n 'sendQuery': false,\n 'sendBody': false,\n 'specifyHeaders': 'keypair',\n 'specifyQuery': 'keypair',\n 'specifyBody': 'keypair',\n 'headerParameters': { parameters: [] },\n 'queryParameters': { parameters: [] },\n 'bodyParameters': { parameters: [] },\n };\n\n return defaultValues[parameterName] ?? null;\n },\n\n // Get the current node\n getNode: (): INode => nodeConfig,\n\n // Get workflow data\n getWorkflow: () => ({\n id: 'workflow-1',\n name: 'Habits Workflow',\n active: true,\n }),\n\n // Get execution mode\n getMode: () => 'manual' as any,\n\n // Get execution ID\n getExecutionId: () => `exec-${Date.now()}`,\n\n // Continue on fail check\n continueOnFail: () => false,\n\n // Get credentials\n getCredentials: async <T extends object = any>(type: string): Promise<T> => {\n const creds = credentials[type];\n if (!creds) {\n throw new Error(`No credentials found for type: ${type}`);\n }\n return creds as T;\n },\n\n // Helpers object with HTTP request and other utilities\n helpers: {\n // HTTP request function\n httpRequest: async (opts: IHttpRequestOptions): Promise<any> => {\n return await httpRequest(opts);\n },\n\n // HTTP request with authentication\n httpRequestWithAuthentication: async (\n credentialsType: string,\n requestOptions: IHttpRequestOptions,\n additionalCredentialOptions?: any\n ): Promise<any> => {\n // Get credentials\n const creds = credentials[credentialsType] || {};\n \n // Try to load credential type and apply authentication generically\n const credentialType = loadCredentialType(\n (params as any).__moduleDefinition,\n credentialsType\n );\n \n if (credentialType) {\n applyCredentialAuthentication(requestOptions, credentialType, creds);\n } else {\n // Fallback to common patterns\n applyFallbackAuthentication(\n requestOptions.headers as Record<string, string> || {},\n creds\n );\n }\n\n return await httpRequest(requestOptions);\n },\n\n // Convert JSON to array format\n returnJsonArray: (jsonData: any): INodeExecutionData[] => {\n const data = Array.isArray(jsonData) ? jsonData : [jsonData];\n return data.map(item => ({ json: item }));\n },\n\n // Copy input items\n copyInputItems: (items: INodeExecutionData[], properties: string[]): IDataObject[] => {\n return items.map(item => {\n const newItem: IDataObject = {};\n for (const property of properties) {\n if (item.json.hasOwnProperty(property)) {\n newItem[property] = item.json[property] as any;\n }\n }\n return newItem;\n });\n },\n\n // Normalize items\n normalizeItems: (items: INodeExecutionData[]): INodeExecutionData[] => {\n return items.map(item => ({\n json: item.json || {},\n binary: item.binary,\n pairedItem: item.pairedItem,\n }));\n },\n\n // Construct execution metadata\n constructExecutionMetaData: (\n items: INodeExecutionData[],\n options: { itemData: { item: number } }\n ): INodeExecutionData[] => {\n return items.map((item, index) => ({\n ...item,\n pairedItem: { item: options.itemData.item },\n }));\n },\n\n // Request function (legacy)\n request: async (uriOrObject: string | any, options?: any): Promise<any> => {\n let requestOpts: IHttpRequestOptions;\n \n if (typeof uriOrObject === 'string') {\n requestOpts = {\n url: uriOrObject,\n method: options?.method || 'GET',\n body: options?.body,\n qs: options?.qs,\n headers: options?.headers,\n };\n } else {\n requestOpts = {\n url: uriOrObject.uri || uriOrObject.url,\n method: uriOrObject.method || 'GET',\n body: uriOrObject.body,\n qs: uriOrObject.qs,\n headers: uriOrObject.headers,\n };\n }\n\n return await httpRequest(requestOpts);\n },\n\n // Request with authentication (legacy)\n requestWithAuthentication: async (\n credentialsType: string,\n requestOptions: any,\n additionalCredentialOptions?: any,\n itemIndex?: number\n ): Promise<any> => {\n const creds = credentials[credentialsType] || {};\n \n // Try to load credential type and apply authentication generically\n const credentialType = loadCredentialType(\n (params as any).__moduleDefinition,\n credentialsType\n );\n \n const httpOptions: IHttpRequestOptions = {\n url: requestOptions.uri || requestOptions.url,\n method: requestOptions.method || 'GET',\n body: requestOptions.body,\n qs: requestOptions.qs,\n headers: requestOptions.headers || {},\n };\n \n if (credentialType) {\n applyCredentialAuthentication(httpOptions, credentialType, creds);\n } else {\n applyFallbackAuthentication(\n httpOptions.headers as Record<string, string>,\n creds\n );\n }\n\n return await httpRequest(httpOptions);\n },\n\n // Binary data helpers (stub implementations)\n prepareBinaryData: async (binaryData: Buffer, filePath?: string, mimeType?: string) => {\n return {\n data: binaryData.toString('base64'),\n mimeType: mimeType || 'application/octet-stream',\n fileName: filePath ? path.basename(filePath) : 'file',\n };\n },\n\n assertBinaryData: (itemIndex: number, propertyName: string) => {\n const item = inputData[itemIndex];\n if (!item?.binary?.[propertyName]) {\n throw new Error(`No binary data found for property: ${propertyName}`);\n }\n return item.binary[propertyName];\n },\n\n getBinaryDataBuffer: async (itemIndex: number, propertyName: string): Promise<Buffer> => {\n const item = inputData[itemIndex];\n if (!item?.binary?.[propertyName]) {\n throw new Error(`No binary data found for property: ${propertyName}`);\n }\n return Buffer.from(item.binary[propertyName].data, 'base64');\n },\n\n // Convert binary data to string\n binaryToString: async (binaryData: Buffer, encoding: BufferEncoding = 'utf-8'): Promise<string> => {\n return binaryData.toString(encoding);\n },\n\n // Create deferred promise\n createDeferredPromise: <T>(): { promise: Promise<T>; resolve: (value: T) => void; reject: (error: Error) => void } => {\n let resolve!: (value: T) => void;\n let reject!: (error: Error) => void;\n const promise = new Promise<T>((res, rej) => {\n resolve = res;\n reject = rej;\n });\n return { promise, resolve, reject };\n },\n } as any,\n\n // Node helpers\n nodeHelpers: {\n copyBinaryFile: async (filePath: string, fileName: string, mimeType?: string) => {\n return {\n data: '',\n mimeType: mimeType || 'application/octet-stream',\n fileName,\n };\n },\n } as any,\n\n // Additional methods that nodes might use\n getWorkflowStaticData: (type: string) => ({}),\n getTimezone: () => 'UTC',\n getRestApiUrl: () => 'http://localhost:5678/api/v1',\n getInstanceBaseUrl: () => 'http://localhost:5678',\n getInstanceId: () => 'instance-1',\n\n // Logging\n logger: {\n info: (...args: any[]) => logger.log('[n8n]', ...args),\n warn: (...args: any[]) => logger.warn('[n8n]', ...args),\n error: (...args: any[]) => logger.error('[n8n]', ...args),\n debug: (...args: any[]) => logger.log('[n8n:debug]', ...args),\n } as any,\n\n // Send message to UI (no-op in headless execution)\n sendMessageToUI: (message: any) => {\n logger.log('[n8n:ui]', message);\n },\n\n // Put execution to wait (for wait nodes)\n putExecutionToWait: async (waitTill: Date) => {\n logger.log(`[n8n] Waiting until: ${waitTill.toISOString()}`);\n },\n\n // Send response (for webhook response nodes)\n sendResponse: (response: any) => {\n logger.log('[n8n] Sending response:', response);\n },\n\n // Prepare output data - transforms INodeExecutionData[] to INodeExecutionData[][]\n prepareOutputData: async (outputData: any[], outputIndex: number = 0): Promise<any[][]> => {\n // n8n expects output as array of arrays (one array per output)\n const returnData: any[][] = [];\n \n // Initialize arrays for all outputs up to outputIndex\n for (let i = 0; i <= outputIndex; i++) {\n returnData.push(i === outputIndex ? outputData : []);\n }\n \n return returnData;\n },\n } as IExecuteFunctions;\n\n return context;\n}\n", "/**\n * Fetch binding\n * \n * Provides cross-platform HTTP fetch that works in Node.js, browser, and Tauri.\n * In Node.js/Browser, uses the native fetch API.\n * In Tauri, uses @tauri-apps/plugin-http through globalThis.__TAURI__ (requires withGlobalTauri: true).\n */\n\nimport { isTauri, getTauriPlugin, type TauriHttpPlugin } from './runtime';\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport interface FetchOptions extends Omit<RequestInit, 'body'> {\n body?: BodyInit | Record<string, unknown> | null;\n /** Timeout in milliseconds (Tauri only) */\n timeout?: number;\n /** Maximum redirects to follow (Tauri only) */\n maxRedirections?: number;\n}\n\nexport interface FetchResponse {\n ok: boolean;\n status: number;\n statusText: string;\n headers: Headers;\n url: string;\n redirected: boolean;\n text: () => Promise<string>;\n json: <T = unknown>() => Promise<T>;\n arrayBuffer: () => Promise<ArrayBuffer>;\n blob: () => Promise<Blob>;\n}\n\n// ============================================================================\n// Helper Functions\n// ============================================================================\n\n/**\n * Get Tauri HTTP plugin from globalThis.__TAURI__\n */\nfunction getTauriHttp(): TauriHttpPlugin {\n return getTauriPlugin('http');\n}\n\n/**\n * Convert native Headers to a plain object for Tauri\n */\nfunction headersToObject(headers?: HeadersInit): Record<string, string> | undefined {\n if (!headers) return undefined;\n \n if (headers instanceof Headers) {\n const obj: Record<string, string> = {};\n headers.forEach((value, key) => {\n obj[key] = value;\n });\n return obj;\n }\n \n if (Array.isArray(headers)) {\n const obj: Record<string, string> = {};\n for (const [key, value] of headers) {\n obj[key] = value;\n }\n return obj;\n }\n \n return headers as Record<string, string>;\n}\n\n/**\n * Convert Tauri response to FetchResponse interface\n */\nfunction wrapTauriResponse(response: Awaited<ReturnType<TauriHttpPlugin['fetch']>>): FetchResponse {\n return {\n ok: response.ok,\n status: response.status,\n statusText: response.statusText || '',\n headers: response.headers,\n url: response.url,\n redirected: response.redirected || false,\n text: () => response.text(),\n json: <T = unknown>() => response.json() as Promise<T>,\n arrayBuffer: () => response.arrayBuffer(),\n blob: () => response.blob(),\n };\n}\n\n/**\n * Convert native Response to FetchResponse interface\n */\nfunction wrapNativeResponse(response: Response): FetchResponse {\n return {\n ok: response.ok,\n status: response.status,\n statusText: response.statusText,\n headers: response.headers,\n url: response.url,\n redirected: response.redirected,\n text: () => response.text(),\n json: <T = unknown>() => response.json() as Promise<T>,\n arrayBuffer: () => response.arrayBuffer(),\n blob: () => response.blob(),\n };\n}\n\n// ============================================================================\n// Primary Functions\n// ============================================================================\n\n/**\n * Fetch a resource from a URL\n * \n * Works in Node.js, browser, and Tauri environments.\n * In Node.js/browser, uses native fetch.\n * In Tauri, uses @tauri-apps/plugin-http which bypasses CORS restrictions.\n * \n * @param url - URL to fetch\n * @param options - Fetch options\n * @returns Response object\n * \n * @example\n * ```typescript\n * const response = await fetch('https://api.example.com/data');\n * const data = await response.json();\n * ```\n * \n * @example With options\n * ```typescript\n * const response = await fetch('https://api.example.com/data', {\n * method: 'POST',\n * headers: { 'Content-Type': 'application/json' },\n * body: JSON.stringify({ key: 'value' }),\n * timeout: 5000, // Tauri only\n * });\n * ```\n */\nexport async function fetch(url: string | URL, options: FetchOptions = {}): Promise<FetchResponse> {\n if (isTauri()) {\n return fetchTauri(url, options);\n }\n return fetchNative(url, options);\n}\n\n/**\n * Fetch using native browser/Node.js fetch\n */\nasync function fetchNative(url: string | URL, options: FetchOptions = {}): Promise<FetchResponse> {\n const { timeout, maxRedirections, body, ...nativeOptions } = options;\n \n // Handle body - if it's an object, stringify it\n let processedBody: BodyInit | null | undefined = undefined;\n if (body !== null && body !== undefined) {\n if (typeof body === 'object' && !(body instanceof ArrayBuffer) && !(body instanceof Blob) && \n !(body instanceof FormData) && !(body instanceof URLSearchParams) &&\n !(body instanceof ReadableStream) && !ArrayBuffer.isView(body)) {\n processedBody = JSON.stringify(body);\n } else {\n processedBody = body as BodyInit;\n }\n }\n \n // Create abort controller for timeout\n let controller: AbortController | undefined;\n let timeoutId: ReturnType<typeof setTimeout> | undefined;\n \n if (timeout) {\n controller = new AbortController();\n timeoutId = setTimeout(() => controller!.abort(), timeout);\n }\n \n try {\n const response = await globalThis.fetch(url, {\n ...nativeOptions,\n body: processedBody,\n signal: controller?.signal ?? options.signal,\n });\n \n return wrapNativeResponse(response);\n } finally {\n if (timeoutId) {\n clearTimeout(timeoutId);\n }\n }\n}\n\n/**\n * Fetch using Tauri HTTP plugin\n * \n * The Tauri HTTP plugin bypasses CORS restrictions and provides\n * additional options like timeout and max redirections.\n */\nasync function fetchTauri(url: string | URL, options: FetchOptions = {}): Promise<FetchResponse> {\n const http = getTauriHttp();\n const { timeout, maxRedirections, body, headers, ...restOptions } = options;\n \n // Handle body - if it's an object, stringify it\n let processedBody: BodyInit | undefined = undefined;\n if (body !== null && body !== undefined) {\n if (typeof body === 'object' && !(body instanceof ArrayBuffer) && !(body instanceof Blob) && \n !(body instanceof FormData) && !(body instanceof URLSearchParams) &&\n !(body instanceof ReadableStream) && !ArrayBuffer.isView(body)) {\n processedBody = JSON.stringify(body);\n } else {\n processedBody = body as BodyInit;\n }\n }\n \n // Build Tauri fetch options\n const tauriOptions: RequestInit & { \n timeout?: number; \n maxRedirections?: number;\n } = {\n ...restOptions,\n body: processedBody,\n headers: headersToObject(headers),\n };\n \n // Add Tauri-specific options if provided\n if (timeout !== undefined) {\n tauriOptions.timeout = timeout;\n }\n if (maxRedirections !== undefined) {\n tauriOptions.maxRedirections = maxRedirections;\n }\n\n const response = await http.fetch(url.toString(), tauriOptions);\n return wrapTauriResponse(response);\n}\n\n\n", "/**\n * HTTP Request utilities for n8n node execution\n */\n\nimport { fetch } from '@ha-bits/bindings';\nimport FormData from 'form-data';\nimport {\n IHttpRequestOptions,\n IN8nHttpFullResponse,\n IN8nHttpResponse,\n} from './types';\nimport { LoggerFactory } from '@ha-bits/core/logger';\n\nconst logger = LoggerFactory.getRoot();\n\n/**\n * Build URL with query parameters and base URL\n */\nfunction buildUrl(url: string, baseURL?: string, qs?: Record<string, any>): string {\n let fullUrl = url;\n \n // Resolve base URL\n if (baseURL && !url.startsWith('http://') && !url.startsWith('https://')) {\n fullUrl = baseURL.replace(/\\/$/, '') + '/' + url.replace(/^\\//, '');\n }\n \n // Add query parameters\n if (qs && Object.keys(qs).length > 0) {\n const params = new URLSearchParams();\n for (const [key, value] of Object.entries(qs)) {\n if (value !== undefined && value !== null) {\n params.append(key, String(value));\n }\n }\n fullUrl += (fullUrl.includes('?') ? '&' : '?') + params.toString();\n }\n \n return fullUrl;\n}\n\n/**\n * Prepare request body for fetch\n */\nfunction prepareBody(body: any, headers: Record<string, string>): BodyInit | undefined {\n if (!body) return undefined;\n \n if (body instanceof FormData) {\n // FormData - set headers from form-data package\n const formHeaders = body.getHeaders();\n Object.assign(headers, formHeaders);\n return body as any;\n }\n \n if (body instanceof URLSearchParams) {\n headers['Content-Type'] = 'application/x-www-form-urlencoded';\n return body.toString();\n }\n \n if (typeof body === 'object' && Object.keys(body).length > 0) {\n if (!headers['Content-Type']) {\n headers['Content-Type'] = 'application/json';\n }\n return JSON.stringify(body);\n }\n \n if (typeof body === 'string') {\n return body;\n }\n \n return undefined;\n}\n\n/**\n * Execute HTTP request\n */\nexport async function httpRequest(\n requestOptions: IHttpRequestOptions\n): Promise<IN8nHttpFullResponse | IN8nHttpResponse> {\n // Remove empty body for GET/HEAD/OPTIONS\n const noBodyMethods = ['GET', 'HEAD', 'OPTIONS'];\n const method = (requestOptions.method || 'GET').toUpperCase();\n if (noBodyMethods.includes(method) && requestOptions.body && Object.keys(requestOptions.body).length === 0) {\n delete requestOptions.body;\n }\n\n const headers: Record<string, string> = {\n ...(requestOptions.headers as Record<string, string>) ?? {},\n };\n \n // Add authentication\n if (requestOptions.auth) {\n const credentials = Buffer.from(\n `${requestOptions.auth.username || ''}:${requestOptions.auth.password || ''}`\n ).toString('base64');\n headers['Authorization'] = `Basic ${credentials}`;\n }\n \n // Add JSON accept header if requested\n if (requestOptions.json) {\n headers['Accept'] = 'application/json';\n }\n \n // Add User-Agent header\n if (!headers['User-Agent']) {\n headers['User-Agent'] = 'n8n-habits-executor';\n }\n \n // Build full URL\n const url = buildUrl(requestOptions.url, requestOptions.baseURL, requestOptions.qs);\n \n // Prepare body (skip for GET requests)\n let body: BodyInit | undefined;\n if (!noBodyMethods.includes(method)) {\n body = prepareBody(requestOptions.body, headers);\n }\n\n logger.log(`\uD83C\uDF10 Making HTTP request: ${method} ${url}`);\n \n try {\n const response = await fetch(url, {\n method,\n headers,\n body,\n redirect: requestOptions.disableFollowRedirect ? 'manual' : 'follow',\n });\n\n // Handle response based on encoding\n let responseData: any;\n const contentType = response.headers.get('content-type') || '';\n \n if (requestOptions.encoding === 'arraybuffer' || contentType.includes('application/octet-stream')) {\n responseData = await response.arrayBuffer();\n } else if (contentType.includes('application/json')) {\n responseData = await response.json();\n } else {\n responseData = await response.text();\n // Try to parse as JSON if it looks like JSON\n try {\n responseData = JSON.parse(responseData);\n } catch {\n // Keep as text\n }\n }\n\n // Check for HTTP errors unless ignoreHttpStatusErrors is set\n if (!response.ok && !requestOptions.ignoreHttpStatusErrors) {\n logger.error(`HTTP Error (${response.status}): ${JSON.stringify(responseData)}`);\n throw new Error(`HTTP Error (${response.status}): ${JSON.stringify(responseData)}`);\n }\n\n if (requestOptions.returnFullResponse) {\n const responseHeaders: Record<string, string> = {};\n response.headers.forEach((value, key) => {\n responseHeaders[key] = value;\n });\n \n return {\n body: responseData,\n headers: responseHeaders,\n statusCode: response.status,\n statusMessage: response.statusText,\n };\n }\n\n return responseData;\n } catch (error: any) {\n if (error.message?.startsWith('HTTP Error')) {\n throw error;\n }\n logger.error(`Request failed: ${error.message}`);\n throw error;\n }\n}\n\n/**\n * Legacy function - kept for compatibility but now builds fetch-compatible config\n * @deprecated Use httpRequest directly\n */\nexport function convertN8nRequestToAxios(requestOptions: IHttpRequestOptions): {\n method: string;\n url: string;\n headers: Record<string, string>;\n data?: any;\n params?: Record<string, any>;\n baseURL?: string;\n} {\n const { headers, method, auth, url, body, qs } = requestOptions;\n\n const config: {\n method: string;\n url: string;\n headers: Record<string, string>;\n data?: any;\n params?: Record<string, any>;\n baseURL?: string;\n } = {\n headers: (headers as Record<string, string>) ?? {},\n method: method || 'GET',\n url,\n };\n\n if (qs) {\n config.params = qs;\n }\n\n if (auth) {\n const credentials = Buffer.from(`${auth.username || ''}:${auth.password || ''}`).toString('base64');\n config.headers['Authorization'] = `Basic ${credentials}`;\n }\n\n if (requestOptions.baseURL) {\n config.baseURL = requestOptions.baseURL;\n }\n\n if (body) {\n if (typeof body === 'object' && Object.keys(body).length > 0) {\n config.data = body;\n } else if (typeof body === 'string') {\n config.data = body;\n }\n }\n\n if (requestOptions.json) {\n config.headers['Accept'] = 'application/json';\n }\n\n if (!config.headers['User-Agent']) {\n config.headers['User-Agent'] = 'n8n-habits-executor';\n }\n\n return config;\n}\n", "/**\n * Credential Type Loading and Authentication\n * Handles loading credential type definitions and applying authentication\n */\n\nimport * as path from '@ha-bits/bindings/path';\nimport * as fs from '@ha-bits/bindings/fs';\nimport { customRequire } from '../utils/customRequire';\nimport { getModulePath, ModuleDefinition } from '../utils/moduleCloner';\nimport {\n IHttpRequestOptions,\n ICredentialType,\n IAuthenticateGeneric,\n ICredentialDataDecryptedObject,\n} from './types';\nimport { LoggerFactory } from '@ha-bits/core/logger';\n\nconst logger = LoggerFactory.getRoot();\n\n// Cache for loaded credential types\nconst credentialTypeCache: Map<string, ICredentialType> = new Map();\n\n/**\n * Load credential type definition from a module\n * This looks for .credentials.ts files and loads the credential class\n */\nexport function loadCredentialType(\n moduleDefinition: ModuleDefinition,\n credentialTypeName: string\n): ICredentialType | null {\n // Check cache first\n if (credentialTypeCache.has(credentialTypeName)) {\n return credentialTypeCache.get(credentialTypeName)!;\n }\n\n if (!moduleDefinition) return null;\n\n try {\n const modulePath = getModulePath(moduleDefinition);\n if (!modulePath) return null;\n\n // Look for credentials directory\n const credentialsDir = path.join(modulePath, 'credentials');\n const distCredentialsDir = path.join(modulePath, 'dist', 'credentials');\n \n const dirsToCheck = [credentialsDir, distCredentialsDir];\n \n for (const dir of dirsToCheck) {\n if (!fs.existsSync(dir)) continue;\n \n const files = fs.readdirSync(dir);\n for (const file of files) {\n if (!file.endsWith('.js') && !file.endsWith('.ts')) continue;\n \n const filePath = path.join(dir, file);\n try {\n const module = customRequire(filePath, dir);\n \n for (const key of Object.keys(module)) {\n const exported = module[key];\n if (exported && typeof exported === 'function') {\n try {\n const instance = new exported();\n if (instance && instance.name === credentialTypeName) {\n credentialTypeCache.set(credentialTypeName, instance);\n logger.log(`\uD83D\uDCCB Loaded credential type: ${credentialTypeName}`);\n return instance;\n }\n } catch (e) {\n // Not a valid credential class, continue\n }\n }\n }\n } catch (e) {\n // Failed to load file, continue\n }\n }\n }\n } catch (error) {\n logger.warn(`Failed to load credential type ${credentialTypeName}: ${error}`);\n }\n \n return null;\n}\n\n/**\n * Resolve credential expression like ={{$credentials.xiApiKey}}\n */\nexport function resolveCredentialExpression(\n expression: string,\n credentials: ICredentialDataDecryptedObject\n): string {\n // Match patterns like ={{$credentials.propertyName}}\n const match = expression.match(/^=\\{\\{\\$credentials\\.([^}]+)\\}\\}$/);\n if (match) {\n const propName = match[1];\n const value = credentials[propName];\n return value !== undefined ? String(value) : '';\n }\n return expression;\n}\n\n/**\n * Apply authentication from credential type definition to request options\n * This reads the `authenticate` property from the credential type and applies it generically\n */\nexport function applyCredentialAuthentication(\n requestOptions: IHttpRequestOptions,\n credentialType: ICredentialType,\n credentials: ICredentialDataDecryptedObject\n): void {\n const auth = credentialType.authenticate;\n \n if (!auth) {\n logger.warn(`Credential type ${credentialType.name} has no authenticate property`);\n return;\n }\n\n // Handle IAuthenticateGeneric type\n if (typeof auth === 'object' && auth.type === 'generic') {\n const genericAuth = auth as IAuthenticateGeneric;\n const props = genericAuth.properties;\n \n // Apply headers\n if (props.headers) {\n const headers = requestOptions.headers as Record<string, string> || {};\n for (const [headerName, expression] of Object.entries(props.headers)) {\n const value = resolveCredentialExpression(String(expression), credentials);\n if (value) {\n headers[headerName] = value;\n }\n }\n requestOptions.headers = headers;\n }\n \n // Apply query parameters\n if (props.qs) {\n const qs = requestOptions.qs as Record<string, any> || {};\n for (const [paramName, expression] of Object.entries(props.qs)) {\n const value = resolveCredentialExpression(String(expression), credentials);\n if (value) {\n qs[paramName] = value;\n }\n }\n requestOptions.qs = qs;\n }\n \n // Apply body parameters\n if (props.body) {\n const body = requestOptions.body as Record<string, any> || {};\n for (const [bodyParam, expression] of Object.entries(props.body)) {\n const value = resolveCredentialExpression(String(expression), credentials);\n if (value) {\n body[bodyParam] = value;\n }\n }\n requestOptions.body = body;\n }\n \n // Apply basic auth\n if (props.auth) {\n const username = resolveCredentialExpression(\n String(props.auth.username || ''),\n credentials\n );\n const password = resolveCredentialExpression(\n String(props.auth.password || ''),\n credentials\n );\n requestOptions.auth = { username, password };\n }\n \n logger.log(`\u2705 Applied generic authentication from credential type: ${credentialType.name}`);\n } else if (typeof auth === 'function') {\n // Handle function-based authentication (advanced case)\n logger.warn(`Function-based authentication not yet supported for ${credentialType.name}`);\n }\n}\n\n/**\n * Apply credentials to request headers using credential type definitions\n * Falls back to common patterns if credential type is not found\n */\nexport function applyCredentialsToHeaders(\n headers: Record<string, string>,\n credentialTypeName: string,\n credentials: ICredentialDataDecryptedObject,\n moduleDefinition?: ModuleDefinition\n): void {\n // Try to load credential type definition\n let credentialType: ICredentialType | null = null;\n if (moduleDefinition) {\n credentialType = loadCredentialType(moduleDefinition, credentialTypeName);\n }\n \n if (credentialType) {\n // Use the authenticate property from the credential type\n const tempOptions: IHttpRequestOptions = { url: '', headers };\n applyCredentialAuthentication(tempOptions, credentialType, credentials);\n Object.assign(headers, tempOptions.headers);\n } else {\n // Fallback: Apply common authentication patterns\n logger.warn(`Credential type ${credentialTypeName} not found, using fallback patterns`);\n applyFallbackAuthentication(headers, credentials);\n }\n}\n\n/**\n * Fallback authentication for when credential type definition is not available\n * Supports common patterns like apiKey, Authorization, etc.\n */\nexport function applyFallbackAuthentication(\n headers: Record<string, string>,\n credentials: ICredentialDataDecryptedObject\n): void {\n // Check for common API key patterns\n if (credentials.apiKey) {\n headers['Authorization'] = `Bearer ${credentials.apiKey}`;\n }\n \n // Check for all credential properties that look like headers\n for (const [key, value] of Object.entries(credentials)) {\n if (typeof value !== 'string') continue;\n \n // Common header-like credential properties\n const headerMappings: Record<string, string> = {\n 'xiApiKey': 'xi-api-key',\n 'xApiKey': 'x-api-key',\n 'authToken': 'Authorization',\n 'bearerToken': 'Authorization',\n 'accessToken': 'Authorization',\n };\n \n if (headerMappings[key]) {\n const headerName = headerMappings[key];\n if (headerName === 'Authorization' && !value.startsWith('Bearer ')) {\n headers[headerName] = `Bearer ${value}`;\n } else {\n headers[headerName] = value;\n }\n }\n }\n}\n", "/**\n * Node Execution Functions\n * Contains executeGenericN8nNode and executeRoutingBasedNode\n */\n\nimport * as path from 'path';\nimport { fetch } from '@ha-bits/bindings';\nimport { customRequire } from '../utils/customRequire';\nimport { getModuleName } from '../utils/moduleLoader';\nimport { ModuleDefinition } from '../utils/moduleCloner';\nimport {\n INodeType,\n INodeExecutionData,\n IExecuteFunctions,\n IHttpRequestOptions,\n INodeTypeDescription,\n} from './types';\nimport { createExecutionContext, N8nNodeExecutionOptions } from './executionContext';\nimport { loadCredentialType, applyCredentialAuthentication, applyFallbackAuthentication } from './credentialLoader';\nimport { LoggerFactory } from '@ha-bits/core/logger';\n\nconst logger = LoggerFactory.getRoot();\n\n/**\n * Load a node from a module file\n */\nexport async function loadNodeFromModule(\n moduleDefinition: ModuleDefinition,\n mainFilePath: string\n): Promise<INodeType> {\n const moduleName = getModuleName(moduleDefinition);\n const originalCwd = process.cwd();\n const moduleDir = path.dirname(mainFilePath);\n\n try {\n process.chdir(moduleDir);\n // Use customRequire to bypass bundler's require and enable dynamic loading\n // n8n-workflow and n8n-core are resolved from the module's node_modules\n \n const module = customRequire(mainFilePath, moduleDir);\n\n // Find the node export - look for class that when instantiated has a description property\n let nodeInstance: INodeType | null = null;\n \n for (const key of Object.keys(module)) {\n const exported = module[key];\n if (exported && typeof exported === 'function') {\n try {\n // Try to instantiate and check for description property\n const instance = new exported();\n if (instance && typeof instance === 'object' && 'description' in instance) {\n nodeInstance = instance as INodeType;\n logger.debug(`Found n8n node class: ${key}`);\n break;\n }\n } catch (e) {\n // Not a valid node class, continue\n }\n }\n }\n\n if (!nodeInstance) {\n throw new Error(`No n8n node class found in module: ${moduleName}`);\n }\n \n process.chdir(originalCwd);\n return nodeInstance;\n } catch (error: any) {\n process.chdir(originalCwd);\n logger.error(error.stack);\n throw error;\n }\n}\n\n/**\n * Check if a node description has routing definitions\n */\nexport function hasRoutingInDescription(description: INodeTypeDescription): boolean {\n if (!description.properties) return false;\n \n for (const prop of description.properties) {\n if (prop.options) {\n for (const option of prop.options as any[]) {\n if (option.routing) {\n return true;\n }\n }\n }\n }\n return false;\n}\n\n/**\n * Execute a generic n8n node\n */\nexport async function executeGenericN8nNode(\n params: Record<string, any>,\n moduleDefinition: ModuleDefinition,\n mainFilePath: string\n): Promise<any> {\n try {\n const node = await loadNodeFromModule(moduleDefinition, mainFilePath);\n \n logger.log(`\uD83D\uDE80 Executing n8n node: ${node.description.displayName}`);\n \n const operation = params.operation;\n const resource = params.resource;\n \n logger.log(`Resource: ${resource || 'default'}, Operation: ${operation || 'default'}`);\n\n // Add moduleDefinition to params so it can be accessed in credential authentication\n const paramsWithModule = {\n ...params,\n __moduleDefinition: moduleDefinition,\n };\n\n // Create a real execution context for the node\n const context = createExecutionContext(node, paramsWithModule);\n\n // Execute the node\n let result: any = null;\n \n if (node.execute) {\n result = await node.execute.call(context);\n } else if (node.description.requestDefaults || hasRoutingInDescription(node.description)) {\n // Handle routing-based declarative nodes (like ElevenLabs)\n logger.log(`\uD83D\uDCE1 Using routing-based execution for declarative node`);\n result = await executeRoutingBasedNode(node, paramsWithModule, context);\n } else {\n throw new Error(`Node does not have an execute method and is not a routing-based node`);\n }\n\n logger.log(`\u2705 Successfully executed n8n node: ${node.description.displayName}`);\n\n // Extract the output from the result\n const output = result?.[0]?.map((item: any) => item.json) || result;\n\n return {\n success: true,\n module: moduleDefinition.repository,\n nodeLoaded: true,\n result: output,\n executedAt: new Date().toISOString(),\n data: {\n message: `Successfully executed n8n node: ${node.description.displayName}`,\n status: 'completed',\n output: result,\n rawOutput: output,\n },\n };\n } catch (error: any) {\n logger.error(`Failed to execute n8n node: ${error.message}`);\n logger.error(error.stack);\n throw error;\n }\n}\n\n/**\n * Execute a routing-based declarative n8n node\n * These nodes define HTTP routing in their operation descriptions instead of using execute()\n */\nexport async function executeRoutingBasedNode(\n node: INodeType,\n params: Record<string, any>,\n context: IExecuteFunctions\n): Promise<INodeExecutionData[][]> {\n const description = node.description;\n const resource = params.resource;\n const operation = params.operation;\n const credentials = params.credentials || {};\n \n // Find the operation definition with routing\n // n8n nodes can have routing at two levels:\n // 1. Property-level routing (on the 'operation' property itself) - contains request config\n // 2. Option-level routing (on individual operation options) - contains preSend/postReceive hooks\n let propertyRoutingConfig: any = null;\n let optionRoutingConfig: any = null;\n let operationDef: any = null;\n let operationProperty: any = null;\n \n for (const prop of description.properties || []) {\n if (prop.name === 'operation' && prop.options) {\n operationProperty = prop;\n // Check for property-level routing (has request.url template)\n if (prop.routing) {\n propertyRoutingConfig = prop.routing;\n }\n // Also check for option-level routing (has preSend hooks)\n for (const option of prop.options as any[]) {\n if (option.value === operation) {\n operationDef = option;\n if (option.routing) {\n optionRoutingConfig = option.routing;\n }\n break;\n }\n }\n }\n }\n \n // Merge routing configs: property-level provides request config, option-level provides hooks\n const routingConfig = {\n ...(propertyRoutingConfig || {}),\n ...(optionRoutingConfig || {}),\n request: {\n ...(propertyRoutingConfig?.request || {}),\n ...(optionRoutingConfig?.request || {}),\n },\n output: {\n ...(propertyRoutingConfig?.output || {}),\n ...(optionRoutingConfig?.output || {}),\n },\n send: {\n ...(propertyRoutingConfig?.send || {}),\n ...(optionRoutingConfig?.send || {}),\n },\n };\n \n if (!propertyRoutingConfig && !optionRoutingConfig) {\n throw new Error(`No routing configuration found for operation: ${operation}`);\n }\n \n logger.log(`\uD83D\uDCE1 Found routing config for operation: ${operation}`);\n \n // Build the request from routing config and requestDefaults\n const requestDefaults = description.requestDefaults || {};\n const requestConfig = routingConfig.request || {};\n \n // Resolve URL with parameter substitution\n let url = requestConfig.url || '';\n if (url.startsWith('=')) {\n // n8n expression format: ={{\"/text-to-speech/\"+$parameter[\"voice\"]}}\n url = resolveN8nExpression(url, params);\n }\n \n // Prepend baseURL if URL is relative\n const baseURL = requestDefaults.baseURL || '';\n if (url && !url.startsWith('http')) {\n url = baseURL + url;\n }\n \n // Build request body from field routing\n const body: Record<string, any> = {};\n const queryParams: Record<string, any> = {};\n \n for (const prop of description.properties || []) {\n // Skip meta fields\n if (['resource', 'operation', 'notice'].includes(prop.name)) {\n continue;\n }\n \n const paramValue = params[prop.name];\n \n // If property has explicit routing.send, use that\n if (prop.routing?.send) {\n const sendConfig = prop.routing.send;\n \n if (paramValue !== undefined && paramValue !== null && paramValue !== '') {\n if (sendConfig.type === 'body') {\n const propName = sendConfig.property || prop.name;\n body[propName] = resolveParamValue(paramValue);\n } else if (sendConfig.type === 'query') {\n const propName = sendConfig.property || prop.name;\n queryParams[propName] = resolveParamValue(paramValue);\n }\n }\n } else if ((prop as any).required && paramValue !== undefined && paramValue !== null && paramValue !== '') {\n // For required fields without explicit routing, add them to body by default\n // This handles cases where preSend hooks normally handle the parameter\n body[prop.name] = resolveParamValue(paramValue);\n } else if (paramValue !== undefined && paramValue !== null && paramValue !== '' && \n !prop.name.includes('_id') && prop.type === 'string') {\n // Also add string parameters that might be body content\n body[prop.name] = resolveParamValue(paramValue);\n }\n \n // Handle nested options (like additionalOptions)\n if (prop.type === 'collection' && prop.options && params[prop.name]) {\n const collectionValue = params[prop.name];\n for (const subProp of prop.options as any[]) {\n if (subProp.routing?.send && collectionValue[subProp.name] !== undefined) {\n const sendConfig = subProp.routing.send;\n const paramValue = collectionValue[subProp.name];\n \n if (paramValue !== undefined && paramValue !== null) {\n if (sendConfig.type === 'body') {\n const propName = sendConfig.property || subProp.name;\n body[propName] = resolveParamValue(paramValue);\n } else if (sendConfig.type === 'query') {\n const propName = sendConfig.property || subProp.name;\n queryParams[propName] = resolveParamValue(paramValue);\n }\n }\n }\n }\n }\n }\n \n // Determine HTTP method\n const method = (requestConfig.method || requestDefaults.method || 'POST').toUpperCase();\n \n // Build headers\n const headers: Record<string, string> = {\n ...(requestDefaults.headers || {}),\n ...(requestConfig.headers || {}),\n };\n \n // Apply credentials authentication using credential type definitions\n const credentialTypeName = description.credentials?.[0]?.name;\n if (credentialTypeName && credentials[credentialTypeName]) {\n const creds = credentials[credentialTypeName];\n const moduleDefinition = (params as any).__moduleDefinition;\n \n // Try to load credential type definition and apply authentication generically\n const credentialType = moduleDefinition \n ? loadCredentialType(moduleDefinition, credentialTypeName)\n : null;\n \n if (credentialType) {\n // Use the authenticate property from the credential type\n const tempOptions: IHttpRequestOptions = { url: '', headers };\n applyCredentialAuthentication(tempOptions, credentialType, creds);\n Object.assign(headers, tempOptions.headers);\n } else {\n // Fallback to common patterns\n applyFallbackAuthentication(headers, creds);\n }\n }\n \n logger.log(`\uD83C\uDF10 Making routing-based request: ${method} ${url}`);\n logger.log(`\uD83D\uDCE4 Request body:`, { body: body });\n \n // Build URL with query params\n let fullUrl = url;\n if (Object.keys(queryParams).length > 0) {\n const params = new URLSearchParams();\n for (const [key, value] of Object.entries(queryParams)) {\n if (value !== undefined && value !== null) {\n params.append(key, String(value));\n }\n }\n fullUrl += (fullUrl.includes('?') ? '&' : '?') + params.toString();\n }\n \n // Prepare request body\n const requestBody = Object.keys(body).length > 0 ? JSON.stringify(body) : undefined;\n if (requestBody && !headers['Content-Type']) {\n headers['Content-Type'] = 'application/json';\n }\n \n try {\n const response = await fetch(fullUrl, {\n method,\n headers,\n body: requestBody,\n });\n \n logger.log(`\u2705 Routing-based request successful: ${response.status}`);\n \n const contentType = response.headers.get('content-type') || '';\n \n // Handle binary response (audio data)\n if (requestConfig.encoding === 'arraybuffer' || contentType.includes('audio')) {\n const arrayBuffer = await response.arrayBuffer();\n const binaryData = Buffer.from(arrayBuffer);\n const base64Data = binaryData.toString('base64');\n const mimeType = contentType || 'audio/mpeg';\n \n return [[{\n json: {\n success: true,\n mimeType,\n dataSize: binaryData.length,\n base64: base64Data,\n },\n binary: {\n data: {\n data: base64Data,\n mimeType,\n fileName: `audio.${mimeType.split('/')[1] || 'mp3'}`,\n }\n }\n }]];\n }\n \n // Handle JSON response\n let responseData: any;\n if (contentType.includes('application/json')) {\n responseData = await response.json();\n } else {\n const text = await response.text();\n try {\n responseData = JSON.parse(text);\n } catch {\n responseData = text;\n }\n }\n \n // Check for HTTP errors\n if (!response.ok) {\n const errorMessage = typeof responseData === 'object' \n ? JSON.stringify(responseData) \n : String(responseData);\n logger.error(`HTTP Error (${response.status}): ${errorMessage}`);\n throw new Error(`HTTP Error (${response.status}): ${errorMessage}`);\n }\n \n return [[{ json: responseData }]];\n \n } catch (error: any) {\n if (error.message?.startsWith('HTTP Error')) {\n throw error;\n }\n logger.error(`Request failed: ${error.message}`);\n throw error;\n }\n}\n\n/**\n * Resolve n8n expression like ={{\"/text-to-speech/\"+$parameter[\"voice\"]}}\n */\nfunction resolveN8nExpression(expression: string, params: Record<string, any>): string {\n // Remove the leading = and {{ }} wrapper\n let expr = expression;\n if (expr.startsWith('=')) {\n expr = expr.substring(1);\n }\n if (expr.startsWith('{{') && expr.endsWith('}}')) {\n expr = expr.substring(2, expr.length - 2);\n }\n \n // Replace $parameter[\"paramName\"] with quoted placeholder values\n const paramValues: Record<string, string> = {};\n expr = expr.replace(/\\$parameter\\[\"([^\"]+)\"\\]/g, (match, paramName) => {\n const value = params[paramName];\n let resolved: string;\n if (typeof value === 'object' && value !== null) {\n // Handle resourceLocator type values\n resolved = value.value || value.id || JSON.stringify(value);\n } else {\n resolved = value !== undefined ? String(value) : '';\n }\n paramValues[paramName] = resolved;\n return `\"${resolved}\"`;\n });\n \n // Now evaluate the string concatenation expression\n // expr is now like: \"/text-to-speech/\"+\"21m00Tcm4TlvDq8ikWAM\"\n try {\n // Remove all quotes and plus signs to concatenate the parts\n // Match pattern: \"string1\"+\"string2\"+\"string3\" etc.\n const parts: string[] = [];\n const regex = /\"([^\"]*)\"/g;\n let match;\n while ((match = regex.exec(expr)) !== null) {\n parts.push(match[1]);\n }\n if (parts.length > 0) {\n return parts.join('');\n }\n // Fallback: just return the expression without quotes\n return expr.replace(/\"/g, '').replace(/\\+/g, '');\n } catch {\n return expr;\n }\n}\n\n/**\n * Resolve parameter value (handle resourceLocator and other complex types)\n */\nfunction resolveParamValue(value: any): any {\n if (typeof value === 'object' && value !== null) {\n // Handle resourceLocator type: { mode: 'list', value: 'actual_value' }\n if ('value' in value) {\n return value.value;\n }\n if ('id' in value) {\n return value.id;\n }\n }\n return value;\n}\n", "/**\n * n8n Module Executor\n * Main entry point for executing n8n nodes\n */\n\nimport { ensureModuleInstalled, getModuleName } from '../utils/moduleLoader';\nimport { getModuleMainFile, getModulePath, ModuleDefinition } from '../utils/moduleCloner';\nimport * as path from '@ha-bits/bindings/path';\nimport * as fs from '@ha-bits/bindings/fs';\n\n// Re-export types and functions from sub-modules\nexport { createExecutionContext, N8nNodeExecutionOptions } from './executionContext';\nexport { executeGenericN8nNode, executeRoutingBasedNode, loadNodeFromModule, hasRoutingInDescription } from './nodeExecution';\nexport { httpRequest, convertN8nRequestToAxios } from './httpRequest';\nexport { loadCredentialType, applyCredentialAuthentication, applyFallbackAuthentication, applyCredentialsToHeaders, resolveCredentialExpression } from './credentialLoader';\nimport { LoggerFactory } from '@ha-bits/core/logger';\n\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport interface N8nExecutionParams {\n source: string;\n framework: string;\n moduleName: string;\n params: Record<string, any>;\n}\n\n// ============================================================================\n// N8n Module Path Resolution\n// ============================================================================\n\n/**\n * Find the main node file for an n8n module\n * N8n modules specify their nodes in package.json under \"n8n.nodes\"\n */\nfunction getN8nNodeFile(moduleDefinition: ModuleDefinition): string | null {\n const modulePath = getModulePath(moduleDefinition);\n logger.log(`\\n\uD83D\uDD0D getN8nNodeFile looking for module at: ${modulePath}`);\n logger.log(` Source: ${moduleDefinition.source}`);\n \n const packageJsonPath = path.join(modulePath, 'package.json');\n\n if (!fs.existsSync(packageJsonPath)) {\n logger.error(`package.json not found at: ${packageJsonPath}`);\n return null;\n }\n \n logger.log(` Found package.json at: ${packageJsonPath}`);\n\n try {\n const packageJson = JSON.parse(fs.readFileSync(packageJsonPath, 'utf-8'));\n \n // N8n modules specify nodes in the \"n8n\" section\n if (packageJson.n8n?.nodes && packageJson.n8n.nodes.length > 0) {\n // Get the first node file\n const nodeFile = packageJson.n8n.nodes[0];\n const fullPath = path.join(modulePath, nodeFile);\n \n if (fs.existsSync(fullPath)) {\n logger.log(`\uD83D\uDD0D Found n8n node at: ${fullPath}`);\n return fullPath;\n }\n }\n\n // Fallback: Try to find .node.js files in common locations\n const fallbackPaths = [\n 'dist/nodes',\n 'nodes',\n 'dist',\n ];\n\n for (const fallbackPath of fallbackPaths) {\n const dir = path.join(modulePath, fallbackPath);\n if (fs.existsSync(dir) && fs.statSync(dir).isDirectory()) {\n const nodeFile = findNodeFileInDirectory(dir);\n if (nodeFile) {\n logger.log(`\uD83D\uDD0D Found n8n node via search at: ${nodeFile}`);\n return nodeFile;\n }\n }\n }\n\n return null;\n } catch (error: any) {\n logger.error(`Error reading package.json: ${error.message}`);\n return null;\n }\n}\n\n/**\n * Recursively search for .node.js files in a directory\n */\nfunction findNodeFileInDirectory(dir: string): string | null {\n const entries = fs.readdirSync(dir, { withFileTypes: true });\n \n for (const entry of entries) {\n const fullPath = path.join(dir, entry.name);\n \n if (entry.isFile() && entry.name.endsWith('.node.js')) {\n return fullPath;\n }\n \n if (entry.isDirectory()) {\n const found = findNodeFileInDirectory(fullPath);\n if (found) {\n return found;\n }\n }\n }\n \n return null;\n}\n\n// ============================================================================\n// Main Execution Function\n// ============================================================================\n\n// Import executeGenericN8nNode here to avoid circular dependency\nimport { executeGenericN8nNode } from './nodeExecution';\n\n/**\n * Execute an n8n module with real HTTP calls and proper execution context\n */\nexport async function executeN8nModule(\n params: N8nExecutionParams\n): Promise<any>;\nexport async function executeN8nModule(\n moduleName: string,\n params: Record<string, any>\n): Promise<any>;\nexport async function executeN8nModule(\n paramsOrModuleName: N8nExecutionParams | string,\n maybeParams?: Record<string, any>\n): Promise<any> {\n // Handle both function signatures\n let moduleDefinition: ModuleDefinition;\n let executionParams: Record<string, any>;\n\n if (typeof paramsOrModuleName === 'string') {\n // Called as executeN8nModule(moduleName, params)\n logger.log(`\\n\uD83D\uDCCB executeN8nModule called with string: ${paramsOrModuleName}`);\n moduleDefinition = {\n framework: 'n8n',\n source: 'npm',\n repository: paramsOrModuleName,\n };\n executionParams = maybeParams || {};\n } else {\n // Called as executeN8nModule(params: N8nExecutionParams)\n logger.log(`\\n\uD83D\uDCCB executeN8nModule called with params object:`);\n logger.log(` Framework: ${paramsOrModuleName.framework}`);\n logger.log(` Source: ${paramsOrModuleName.source}`);\n logger.log(` ModuleName: ${paramsOrModuleName.moduleName}`);\n moduleDefinition = {\n framework: paramsOrModuleName.framework,\n source: paramsOrModuleName.source as 'github' | 'npm' | 'local',\n repository: paramsOrModuleName.moduleName,\n };\n executionParams = paramsOrModuleName.params;\n }\n\n // Ensure module is installed\n const inferredModuleName = getModuleName(moduleDefinition);\n logger.log(`\\n\uD83D\uDD0D Ensuring n8n module is ready: ${inferredModuleName}`);\n await ensureModuleInstalled(moduleDefinition);\n\n // Get the n8n node file path using n8n-specific resolution\n let mainFilePath = getN8nNodeFile(moduleDefinition);\n \n // Fallback to generic resolution if n8n-specific fails\n if (!mainFilePath) {\n mainFilePath = getModuleMainFile(moduleDefinition);\n }\n \n if (!mainFilePath) {\n throw new Error(`Could not locate node file for n8n module: ${inferredModuleName}`);\n }\n\n logger.log(`\uD83D\uDCE6 n8n node file at: ${mainFilePath}`);\n\n try {\n return await executeGenericN8nNode(executionParams, moduleDefinition, mainFilePath);\n } catch (error: any) {\n throw new Error(`Failed to execute n8n module '${moduleDefinition.repository}': ${error.message}`);\n }\n}\n", "import { ensureModuleInstalled, getModuleName } from '../utils/moduleLoader';\nimport { getModuleMainFile, ModuleDefinition, ensureActivepiecesReady } from '../utils/moduleCloner';\nimport * as path from '@ha-bits/bindings/path';\nimport { simpleRequire } from '../utils/customRequire';\n\n// Lazy-loaded activepieces modules - will be loaded after ensureActivepiecesReady() is called\nlet extractPieceFromModule: any;\nlet TriggerStrategy: any;\nlet trimVersionFromAlias: any;\n\n/**\n * Ensures activepieces dependencies are installed and loads the required modules.\n * Must be called before using any activepieces functionality.\n */\nasync function ensureActivepiecesModulesLoaded(): Promise<void> {\n if (extractPieceFromModule) return; // Already loaded\n \n // Ensure deps are installed first\n await ensureActivepiecesReady();\n \n // Now dynamically import the modules\n const shared = await import('@activepieces/shared');\n \n extractPieceFromModule = shared.extractPieceFromModule;\n TriggerStrategy = shared.TriggerStrategy;\n trimVersionFromAlias = shared.trimVersionFromAlias;\n}\n\nimport { LoggerFactory } from '@ha-bits/core/logger';\nconst logger = LoggerFactory.getRoot();\n\n\n\nexport async function executeActivepiecesModule(\nparams: { source: string,\n framework: string,\n moduleName: string,\n params: Record<string, any>}\n): Promise<any> {\n // Ensure activepieces dependencies are installed and loaded\n await ensureActivepiecesModulesLoaded();\n\n // Get module definition from config\n const moduleDefinition: ModuleDefinition = {\n framework: params.framework,\n source: params.source as 'github' | 'npm',\n repository: params.moduleName,\n };\n \n\n\n\n \n if (!moduleDefinition) {\n throw new Error(`Activepieces module '${params.moduleName}' not found in modules.json`);\n }\n\n // Ensure module is cloned and built\n const inferredModuleName = getModuleName(moduleDefinition);\n console.log(`\\n\uD83D\uDD0D Ensuring module is ready: ${inferredModuleName}`);\n await ensureModuleInstalled(moduleDefinition);\n\n\n\n \n\n try {\n return await executeGenericActivepiecesPiece(params, moduleDefinition);\n\n } catch (error: any) {\n throw new Error(`Failed to load Activepieces module from '${moduleDefinition.repository}': ${error.message}`);\n }\n\n // Generic execution fallback\n}\nasync function pieceFromModule(\n moduleDefinition: ModuleDefinition\n): Promise<any> {\n const moduleName = getModuleName(moduleDefinition);\n\n\n // Get the main file path\n const mainFilePath = getModuleMainFile(moduleDefinition);\n if (!mainFilePath) {\n throw new Error(`Could not locate main file for module: ${moduleName}`);\n }\n\n console.log(`\uD83D\uDCE6 Module ready at: ${mainFilePath}`);\n\n // Import module using require for CommonJS compatibility \n // Save current working directory and change to module directory for proper resolution\n const originalCwd = process.cwd();\n const moduleDir = path.dirname(mainFilePath);\n \n // Find the node_modules directory containing the module\n // For /tmp/habits-nodes/node_modules/@activepieces/piece-openai/src/index.js\n // we want /tmp/habits-nodes/node_modules\n let nodeModulesDir = moduleDir;\n while (nodeModulesDir && !nodeModulesDir.endsWith('/node_modules') && nodeModulesDir !== path.dirname(nodeModulesDir)) {\n nodeModulesDir = path.dirname(nodeModulesDir);\n }\n \n try {\n process.chdir(moduleDir);\n // Use simpleRequire which creates require from the node_modules context\n // This avoids module resolution path manipulation that can cause circular dependency issues\n const loadedModule = simpleRequire(mainFilePath, nodeModulesDir);\n \n // Find the piece export in the module\n const pieceName = Object.keys(loadedModule).find(key => {\n const exported = loadedModule[key];\n return exported && typeof exported === 'object' && 'actions' in exported && 'triggers' in exported;\n });\n \n const piece = (extractPieceFromModule as any)({module: loadedModule, pieceName: pieceName!, pieceVersion: trimVersionFromAlias('2.0' )});\n process.chdir(originalCwd);\n return piece;\n } catch (error: any) {\n process.chdir(originalCwd);\n logger.error(error.stack);\n throw error;\n }\n\n\n}\nasync function hookTriggers(\n moduleDefinition: ModuleDefinition\n){\n // Ensure activepieces modules are loaded before using TriggerStrategy\n await ensureActivepiecesModulesLoaded();\n \n const piece = await pieceFromModule(moduleDefinition);\n\n const triggers = piece.triggers();\n for (const [triggerKey, trigger] of Object.entries(triggers)) {\n console.log(`\uD83D\uDD14 Hooking trigger: ${triggerKey}`);\n const triggerObj = trigger as any;\n\n // Check trigger type: polling, webhook, app-webhook\n if(triggerObj.type == TriggerStrategy.POLLING){\n // If Polling trigger, Check strategy either timebased or \n\n\n }\n\n if(triggerObj.type == TriggerStrategy.WEBHOOK){\n // If Webhook trigger\n // Here you would add logic to actually hook the trigger into your system\n // For example, setting up webhooks, polling mechanisms, etc.\n }\n if(triggerObj.type == TriggerStrategy.APP_WEBHOOK){\n // If App Webhook trigger\n // Here you would add logic to actually hook the trigger into your system\n // For example, setting up webhooks, polling mechanisms, etc.\n }\n}\n}\nasync function executeGenericActivepiecesPiece(\n params: Record<string, any>,\n moduleDefinition: ModuleDefinition\n): Promise<any> {\n\n try {\n\n \n const piece = await pieceFromModule(moduleDefinition);\n\n \n logger.log(`\uD83D\uDE80 Executing Activepieces piece: ${piece.displayName}`);\n const actionName = params.params.operation;\n const pieceActions = piece.actions();\n logger.log(`Available actions: ${Object.keys(pieceActions).join(', ')}`);\n logger.log(`Requested action: ${actionName}`);\n const action = piece.actions()[actionName] as any;\n \n // if action is not found, throw error with available actions\n if (!action) {\n throw new Error(`Action '${actionName}' not found in piece '${piece.displayName}'. Available actions: ${Object.keys(pieceActions).join(', ')}`);\n }\n // Extract auth from credentials if present\n // The piece expects auth to be passed separately from propsValue\n // Credentials are typically in params.params.credentials.<pieceName>\n let auth: any = undefined;\n const { credentials, ...actionProps } = params.params;\n if (credentials) {\n // Find the first credential object (e.g., credentials.intersect, credentials.openai, etc.)\n const credentialKeys = Object.keys(credentials);\n if (credentialKeys.length > 0) {\n // Pass auth data directly - pieces access auth properties directly (e.g., auth.host, auth.apiKey)\n // Some pieces may wrap in auth.props but most modern pieces access directly\n auth = credentials[credentialKeys[0]];\n logger.log(`\uD83D\uDD10 Using credentials for: ${credentialKeys[0]}`);\n }\n }\n \n const result = await action.run({\n auth,\n propsValue: {\n ...actionProps\n } as any\n } as any);\n logger.log(`\u2705 Successfully executed Activepieces piece action: ${actionName}`, result);\n \n \n return {\n success: true,\n module: moduleDefinition.repository,\n pieceLoaded: true,\n params,\n result,\n executedAt: new Date().toISOString(),\n data: {\n message: `Successfully executed Activepieces piece: ${piece.displayName}`,\n status: 'completed',\n pieceExports: Object.keys(module),\n },\n };\n \n } catch (error: any) {\n // Print stack\n logger.error(error.stack);\n throw error;\n }\n\n\n\n}\n", "import { inspect } from 'node:util';\nimport { getModuleName } from '../utils/moduleLoader';\nimport { getModuleMainFile, ModuleDefinition, ensureActivepiecesReady } from '../utils/moduleCloner';\nimport * as path from '@ha-bits/bindings/path';\n\n// Lazy-loaded activepieces modules - will be loaded after ensureActivepiecesReady() is called\nlet isNil: any;\nlet TriggerStrategy: any;\nlet extractPieceFromModule: any;\nlet trimVersionFromAlias: any;\n\n/**\n * Ensures activepieces dependencies are installed and loads the required modules.\n * Must be called before using any activepieces functionality.\n */\nasync function ensureActivepiecesModulesLoaded(): Promise<void> {\n if (extractPieceFromModule) return; // Already loaded\n \n // Ensure deps are installed first\n await ensureActivepiecesReady();\n \n // Now dynamically import the modules\n const shared = await import('@activepieces/shared');\n \n isNil = shared.isNil;\n TriggerStrategy = shared.TriggerStrategy;\n extractPieceFromModule = shared.extractPieceFromModule;\n trimVersionFromAlias = shared.trimVersionFromAlias;\n}\n\nimport { LoggerFactory } from '@ha-bits/core/logger';\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport enum TriggerHookType {\n ON_ENABLE = 'ON_ENABLE',\n ON_DISABLE = 'ON_DISABLE',\n RUN = 'RUN',\n TEST = 'TEST',\n HANDSHAKE = 'HANDSHAKE',\n}\n\nexport interface Listener {\n events: string[];\n identifierValue: string;\n identifierKey: string;\n}\n\nexport interface ScheduleOptions {\n cronExpression: string;\n timezone?: string;\n}\n\nexport interface TriggerExecutionParams {\n moduleDefinition: ModuleDefinition;\n triggerName: string;\n input: Record<string, any>;\n hookType: TriggerHookType;\n trigger?: any; // Lazy-loaded Trigger type from @activepieces/pieces-framework\n payload?: unknown;\n webhookUrl?: string;\n isTest?: boolean;\n store?: SimpleStore;\n}\n\nexport interface TriggerExecutionResult {\n success: boolean;\n output?: unknown[];\n message?: string;\n listeners?: Listener[];\n scheduleOptions?: ScheduleOptions;\n response?: unknown;\n}\n\nexport interface SimpleTriggerContext {\n auth?: any;\n propsValue: Record<string, any>;\n payload: unknown;\n webhookUrl?: string;\n store: SimpleStore;\n app: {\n createListeners: (listener: Listener) => void;\n };\n setSchedule: (options: ScheduleOptions) => void;\n}\n\nexport interface SimpleStore {\n get: <T>(key: string) => Promise<T | null>;\n put: <T>(key: string, value: T) => Promise<void>;\n delete: (key: string) => Promise<void>;\n}\n\n// ============================================================================\n// Simple In-Memory Store (can be replaced with persistent storage)\n// ============================================================================\n\nfunction createSimpleStore(prefix: string = ''): SimpleStore {\n const storage = new Map<string, unknown>();\n \n return {\n async get<T>(key: string): Promise<T | null> {\n const fullKey = `${prefix}:${key}`;\n return (storage.get(fullKey) as T) ?? null;\n },\n async put<T>(key: string, value: T): Promise<void> {\n const fullKey = `${prefix}:${key}`;\n storage.set(fullKey, value);\n },\n async delete(key: string): Promise<void> {\n const fullKey = `${prefix}:${key}`;\n storage.delete(fullKey);\n },\n };\n}\n\n// ============================================================================\n// Trigger Helper\n// ============================================================================\n\nexport const triggerHelper = {\n /**\n * Load a piece from module definition\n */\n async loadPieceFromModule(moduleDefinition: ModuleDefinition): Promise<any> {\n // Ensure activepieces dependencies are installed and loaded\n await ensureActivepiecesModulesLoaded();\n \n const moduleName = getModuleName(moduleDefinition);\n const mainFilePath = getModuleMainFile(moduleDefinition);\n \n if (!mainFilePath) {\n throw new Error(`Could not locate main file for module: ${moduleName}`);\n }\n\n logger.log(`\uD83D\uDCE6 Loading piece from: ${mainFilePath}`);\n\n const originalCwd = process.cwd();\n const moduleDir = path.dirname(mainFilePath);\n\n try {\n process.chdir(moduleDir);\n // Use customRequire to bypass bundler's require and enable dynamic loading\n const module = require(mainFilePath);\n\n // Find the piece export\n const pieceName = Object.keys(module).find(key => {\n const exported = module[key];\n return exported && typeof exported === 'object' && 'actions' in exported && 'triggers' in exported;\n });\n\n if (!pieceName) {\n throw new Error(`No piece found in module: ${moduleName}`);\n }\n\n const piece = (extractPieceFromModule as any)({\n module,\n pieceName,\n pieceVersion: trimVersionFromAlias('2.0'),\n });\n\n process.chdir(originalCwd);\n return piece;\n } catch (error: any) {\n process.chdir(originalCwd);\n logger.error(error.stack);\n throw error;\n }\n },\n\n /**\n * Get a specific trigger from a piece\n */\n async getTrigger(\n moduleDefinition: ModuleDefinition,\n triggerName: string\n ): Promise<{ piece: any; trigger: any }> {\n const piece = await this.loadPieceFromModule(moduleDefinition);\n const triggers = piece.triggers();\n const trigger = triggers[triggerName];\n\n if (!trigger) {\n const availableTriggers = Object.keys(triggers).join(', ');\n throw new Error(\n `Trigger '${triggerName}' not found. Available triggers: ${availableTriggers}`\n );\n }\n\n return { piece, trigger };\n },\n\n /**\n * Execute a trigger based on hook type\n */\n async executeTrigger(params: TriggerExecutionParams): Promise<TriggerExecutionResult> {\n const { moduleDefinition, triggerName, input, hookType,trigger, payload, webhookUrl, isTest, store } = params;\n\n if (isNil(triggerName)) {\n throw new Error('Trigger name is not set');\n }\n let pieceTrigger: any;\n if(trigger){\n pieceTrigger=trigger;\n }else{\n const { piece,trigger } = await this.getTrigger(moduleDefinition, triggerName);\n pieceTrigger=trigger;\n }\n logger.log(`\uD83D\uDD14 Executing trigger: ${triggerName} (${hookType})`);\n\n const appListeners: Listener[] = [];\n let scheduleOptions: ScheduleOptions | undefined;\n const storePrefix = isTest ? 'test' : triggerName;\n\n // Use provided store or create a new one\n // This ensures state persists between onEnable and run calls\n const triggerStore = store || createSimpleStore(storePrefix);\n\n // Extract auth from credentials if present (similar to actions)\n // The auth object needs to have a `props` property for pieces that use CustomAuth\n let auth: any = undefined;\n const { credentials, ...triggerProps } = input;\n if (credentials) {\n // Find the first credential object (e.g., credentials.imapAuth, credentials.gmail, etc.)\n const credentialKeys = Object.keys(credentials);\n if (credentialKeys.length > 0) {\n const credentialData = credentials[credentialKeys[0]];\n // Wrap in props structure as expected by CustomAuth pieces\n auth = {\n props: credentialData,\n ...credentialData, // Also spread at top level for pieces that access directly\n };\n logger.log(`\uD83D\uDD10 Using credentials for trigger: ${credentialKeys[0]}`);\n logger.log(` Auth props: ${JSON.stringify(Object.keys(credentialData))}`);\n }\n }\n\n // Build context for trigger execution\n const context: SimpleTriggerContext = {\n auth,\n propsValue: triggerProps,\n payload: payload ?? {},\n webhookUrl,\n store: triggerStore,\n app: {\n createListeners(listener: Listener): void {\n appListeners.push(listener);\n },\n },\n setSchedule(options: ScheduleOptions): void {\n scheduleOptions = {\n cronExpression: options.cronExpression,\n timezone: options.timezone ?? 'UTC',\n };\n },\n };\n\n try {\n switch (hookType) {\n case TriggerHookType.ON_ENABLE: {\n if (pieceTrigger.onEnable) {\n await pieceTrigger.onEnable(context as any);\n }\n return {\n success: true,\n listeners: appListeners,\n scheduleOptions: pieceTrigger.type === TriggerStrategy.POLLING ? scheduleOptions : undefined,\n };\n }\n\n case TriggerHookType.ON_DISABLE: {\n if (pieceTrigger.onDisable) {\n await pieceTrigger.onDisable(context as any);\n }\n return { success: true };\n }\n\n case TriggerHookType.HANDSHAKE: {\n if (pieceTrigger.onHandshake) {\n const response = await pieceTrigger.onHandshake(context as any);\n return {\n success: true,\n response,\n };\n }\n return {\n success: false,\n message: 'Trigger does not support handshake',\n };\n }\n\n case TriggerHookType.TEST: {\n if (pieceTrigger.test) {\n const testResult = await pieceTrigger.test(context as any);\n return {\n success: true,\n output: Array.isArray(testResult) ? testResult : [testResult],\n };\n }\n return {\n success: false,\n message: 'Trigger does not support test mode',\n output: [],\n };\n }\n\n case TriggerHookType.RUN: {\n if (pieceTrigger.run) {\n const runResult = await pieceTrigger.run(context as any);\n return {\n success: true,\n output: Array.isArray(runResult) ? runResult : [runResult],\n };\n }\n return {\n success: false,\n message: 'Trigger does not have a run method',\n output: [],\n };\n }\n\n default:\n return {\n success: false,\n message: `Unknown hook type: ${hookType}`,\n };\n }\n } catch (error: any) {\n logger.error(`Error executing trigger ${triggerName}:`, error);\n return {\n success: false,\n message: `Error executing trigger: ${inspect(error)}`,\n output: [],\n };\n }\n },\n\n /**\n * List all triggers from a piece\n */\n async listTriggers(moduleDefinition: ModuleDefinition): Promise<{\n triggers: Array<{\n name: string;\n displayName: string;\n description: string;\n type: any; // TriggerStrategy - lazy-loaded from @activepieces/shared\n }>;\n }> {\n const piece = await this.loadPieceFromModule(moduleDefinition);\n const triggers = piece.triggers();\n\n return {\n triggers: Object.entries(triggers).map(([name, trigger]) => {\n const t = trigger as any;\n return {\n name,\n displayName: t.displayName,\n description: t.description,\n type: t.type,\n };\n }),\n };\n },\n\n /**\n * Execute trigger with proper flow based on trigger type\n * For polling: calls onEnable first, then run\n * For webhooks: calls run directly\n */\n async executeActivepiecesTrigger(params: {\n moduleDefinition: ModuleDefinition;\n triggerName: string;\n input: Record<string, any>;\n payload?: unknown;\n webhookUrl?: string;\n store?: SimpleStore;\n }): Promise<TriggerExecutionResult> {\n const { moduleDefinition, triggerName, input, payload, webhookUrl, store } = params;\n\n // Get the trigger to determine its type\n const { piece, trigger } = await this.getTrigger(moduleDefinition, triggerName);\n \n\n const triggerStore = store || createSimpleStore(`trigger:${triggerName}`);\n\n switch (trigger.type) {\n case TriggerStrategy.POLLING: {\n logger.log(`Polling trigger flow: onEnable \u2192 run`);\n \n const onEnableResult = await this.executeTrigger({\n moduleDefinition,\n triggerName,\n input,\n hookType: TriggerHookType.ON_ENABLE,\n trigger,\n payload,\n webhookUrl,\n isTest: false,\n store: triggerStore,\n });\n\n if (!onEnableResult.success) {\n return onEnableResult;\n }\n\n logger.log(` \u2705 onEnable completed`);\n if (onEnableResult.scheduleOptions) {\n logger.log(` \uD83D\uDCC5 Schedule: ${onEnableResult.scheduleOptions.cronExpression} (${onEnableResult.scheduleOptions.timezone})`);\n }\n if (onEnableResult.listeners && onEnableResult.listeners.length > 0) {\n logger.log(` \uD83D\uDC42 Listeners: ${onEnableResult.listeners.length}`);\n }\n\n logger.log(` \u2192 Calling run to fetch items...`);\n const runResult = await this.executeTrigger({\n moduleDefinition,\n triggerName,\n input,\n hookType: TriggerHookType.RUN,\n trigger,\n payload,\n webhookUrl,\n isTest: false,\n store: triggerStore, \n });\n\n if (!runResult.success) {\n logger.warn(` \u26A0\uFE0F Run failed: ${runResult.message}`);\n } else {\n logger.log(` \u2705 Run completed, items found: ${runResult.output?.length || 0}`);\n }\n\n return runResult;\n }\n\n case TriggerStrategy.WEBHOOK: {\n logger.log(`webhook trigger`);\n \n return await this.executeTrigger({\n moduleDefinition,\n triggerName,\n input,\n hookType: TriggerHookType.RUN,\n payload,\n webhookUrl,\n isTest: false,\n });\n }\n\n default: {\n return {\n success: false,\n message: `Unsupported trigger type: ${trigger.type}`,\n output: [],\n };\n }\n }\n },\n\n /**\n * Hook triggers for a piece - sets up polling/webhooks based on trigger type\n * For polling triggers, automatically runs after a delay (default 3 seconds)\n */\n async hookTriggers(\n moduleDefinition: ModuleDefinition,\n options?: {\n webhookBaseUrl?: string;\n onPollingTrigger?: (triggerName: string, trigger: any) => void;\n onWebhookTrigger?: (triggerName: string, trigger: any) => void;\n onAppWebhookTrigger?: (triggerName: string, trigger: any) => void;\n onTriggerResult?: (triggerName: string, result: TriggerExecutionResult) => void;\n input?: Record<string, any>; // Input params for the trigger\n }\n ): Promise<void> {\n const piece = await this.loadPieceFromModule(moduleDefinition);\n const triggers = piece.triggers();\n\n for (const [triggerName, trigger] of Object.entries(triggers)) {\n const t = trigger as any;\n logger.log(`\uD83D\uDD14 Hooking trigger: ${triggerName} (type: ${t.type})`);\n\n switch (t.type) {\n case TriggerStrategy.POLLING:\n logger.log(` \u2192 Setting up polling trigger`);\n if (options?.onPollingTrigger) {\n options.onPollingTrigger(triggerName, t);\n }\n \n // Auto-run polling trigger immediately\n logger.log(` \uD83D\uDE80 Running polling trigger immediately...`);\n try {\n const result = await this.executeActivepiecesTrigger({\n moduleDefinition,\n triggerName,\n input: options?.input || {},\n });\n \n if (result.success) {\n logger.log(` \u2705 Trigger ${triggerName} executed successfully`);\n logger.log(` \uD83D\uDCE6 Output items: ${result.output?.length || 0}`);\n } else {\n logger.warn(` \u26A0\uFE0F Trigger ${triggerName} failed: ${result.message}`);\n }\n \n // Notify callback if provided\n if (options?.onTriggerResult) {\n options.onTriggerResult(triggerName, result);\n }\n } catch (error: any) {\n logger.error(` \u274C Error running trigger ${triggerName}:`, error.message);\n }\n break;\n\n case TriggerStrategy.WEBHOOK:\n logger.log(` \u2192 Setting up webhook trigger`);\n if (options?.onWebhookTrigger) {\n options.onWebhookTrigger(triggerName, t);\n }\n break;\n\n case TriggerStrategy.APP_WEBHOOK:\n logger.log(` \u2192 Setting up app webhook trigger`);\n if (options?.onAppWebhookTrigger) {\n options.onAppWebhookTrigger(triggerName, t);\n }\n break;\n\n default:\n logger.warn(` \u26A0\uFE0F Unknown trigger type: ${t.type}`);\n }\n }\n },\n\n /**\n * Validate cron expression (simple validation)\n */\n isValidCron(expression: string): boolean {\n // Simple validation - checks for 5 or 6 space-separated parts\n const parts = expression.trim().split(/\\s+/);\n return parts.length >= 5 && parts.length <= 6;\n },\n\n /**\n * Check if a node is an Activepieces trigger (polling or webhook)\n */\n isActivepiecesTrigger(node: any): boolean {\n return (\n node.data?.framework === 'activepieces' &&\n (node.data?.triggerType === 'polling' || node.data?.triggerType === 'webhook')\n );\n },\n\n /**\n * Check if a node is a webhook trigger\n */\n isWebhookTrigger(node: any): boolean {\n return (\n node.type === 'trigger' &&\n node.data?.framework === 'activepieces' &&\n (node.data?.triggerType === 'webhook' || \n node.data?.module === '@activepieces/piece-webhook' ||\n node.data?.operation === 'catch_webhook')\n );\n },\n\n /**\n * Extract webhook trigger configuration from a node\n */\n getWebhookConfig(node: any): {\n nodeId: string;\n path: string;\n authType: 'none' | 'header' | 'query_param';\n authFields: Record<string, any>;\n } {\n return {\n nodeId: node.id,\n path: `/webhook/${node.id}`,\n authType: node.data?.triggerSettings?.authType || 'none',\n authFields: node.data?.triggerSettings?.authFields || {},\n };\n },\n\n /**\n * Execute a webhook trigger with received payload\n */\n async executeWebhookTrigger(\n nodeId: string,\n payload: any,\n headers?: Record<string, string>,\n query?: Record<string, string>\n ): Promise<TriggerExecutionResult> {\n logger.log(`\uD83D\uDD14 Executing webhook trigger for node: ${nodeId}`);\n \n // For webhook triggers, we just pass through the payload\n // The actual processing is done by the downstream nodes\n return {\n success: true,\n output: [{\n body: payload,\n headers: headers || {},\n query: query || {},\n method: 'POST',\n timestamp: new Date().toISOString(),\n }],\n message: 'Webhook received successfully',\n };\n },\n};\n\n// ============================================================================\n// Utility Functions\n// ============================================================================\n\n/**\n * Try-catch wrapper that returns a result object\n */\nexport async function tryCatch<T>(\n fn: () => Promise<T>\n): Promise<{ data: T | null; error: Error | null }> {\n try {\n const data = await fn();\n return { data, error: null };\n } catch (error: any) {\n return { data: null, error };\n }\n}\n\nexport default triggerHelper;\n", "/**\n * Declarative API Executor\n * \n * This module handles the execution of declarative bits that define API\n * integrations through a description object with routing configuration,\n * similar to n8n's declarative node pattern - but without any n8n dependencies.\n * \n * Example declarative bit:\n * ```typescript\n * export class FriendGrid implements INodeType {\n * description: INodeTypeDescription = {\n * displayName: 'FriendGrid',\n * name: 'friendGrid',\n * requestDefaults: {\n * baseURL: 'https://api.sendgrid.com/v3/marketing'\n * },\n * properties: [\n * {\n * displayName: 'Operation',\n * name: 'operation',\n * type: 'options',\n * options: [\n * {\n * name: 'Create',\n * value: 'create',\n * routing: {\n * request: {\n * method: 'POST',\n * url: '/contacts'\n * }\n * }\n * }\n * ]\n * }\n * ]\n * }\n * }\n * ```\n */\n\nimport { fetch } from '@ha-bits/bindings';\n\n// ============================================================================\n// Types for HTTP Request Configuration\n// ============================================================================\n\n/**\n * HTTP Method type for routing\n */\ntype Method = 'GET' | 'POST' | 'PUT' | 'PATCH' | 'DELETE' | 'HEAD' | 'OPTIONS';\n\n/**\n * Request configuration (replaces AxiosRequestConfig)\n */\ninterface RequestConfig {\n method?: Method;\n url?: string;\n baseURL?: string;\n headers?: Record<string, string>;\n params?: Record<string, any>;\n data?: any;\n}\n\n// ============================================================================\n// Types for Declarative Node Definition\n// ============================================================================\n\n/**\n * HTTP methods supported in routing\n */\nexport type DeclarativeHttpMethod = 'GET' | 'POST' | 'PUT' | 'PATCH' | 'DELETE' | 'HEAD' | 'OPTIONS';\n\n/**\n * Expression resolver context - available variables in expressions\n */\nexport interface ExpressionContext {\n $parameter: Record<string, any>;\n $credentials: Record<string, any>;\n $response?: any;\n $input?: any;\n $json?: any;\n}\n\n/**\n * Send configuration for request body/query\n */\nexport interface RoutingSend {\n type: 'body' | 'query';\n property?: string;\n properties?: Record<string, any>;\n value?: any;\n preSend?: PreSendAction[];\n}\n\n/**\n * Pre-send action types\n */\nexport interface PreSendAction {\n type: 'setKeyValue' | 'json';\n properties?: Record<string, any>;\n}\n\n/**\n * Post-receive action types\n */\nexport interface PostReceiveAction {\n type: 'set' | 'setKeyValue' | 'filter' | 'rootProperty' | 'limit' | 'sort' | 'binaryData';\n properties?: {\n value?: string;\n key?: string;\n property?: string;\n enabled?: string | boolean;\n maxResults?: number;\n };\n}\n\n/**\n * Routing output configuration\n */\nexport interface RoutingOutput {\n postReceive?: PostReceiveAction[];\n}\n\n/**\n * Request routing configuration\n */\nexport interface RoutingRequest {\n method?: DeclarativeHttpMethod;\n url?: string;\n baseURL?: string;\n headers?: Record<string, string>;\n qs?: Record<string, any>;\n body?: Record<string, any> | any;\n send?: RoutingSend;\n ignoreHttpStatusErrors?: boolean;\n returnFullResponse?: boolean;\n skipOnEmpty?: string;\n}\n\n/**\n * Complete routing configuration for an operation\n */\nexport interface RoutingConfig {\n request?: RoutingRequest;\n send?: RoutingSend;\n output?: RoutingOutput;\n}\n\n/**\n * Option definition for dropdown/options type properties\n */\nexport interface PropertyOption {\n name: string;\n value: string | number | boolean;\n description?: string;\n action?: string;\n routing?: RoutingConfig;\n}\n\n/**\n * Display options for conditional visibility\n */\nexport interface DisplayOptions {\n show?: Record<string, any[]>;\n hide?: Record<string, any[]>;\n}\n\n/**\n * Property definition in declarative node\n */\nexport interface DeclarativeProperty {\n displayName: string;\n name: string;\n type: 'string' | 'number' | 'boolean' | 'options' | 'multiOptions' | 'collection' | 'fixedCollection' | 'json' | 'notice' | 'hidden';\n default?: any;\n required?: boolean;\n description?: string;\n placeholder?: string;\n noDataExpression?: boolean;\n displayOptions?: DisplayOptions;\n options?: PropertyOption[] | DeclarativeProperty[];\n typeOptions?: {\n multipleValues?: boolean;\n multipleValueButtonText?: string;\n minValue?: number;\n maxValue?: number;\n numberStepSize?: number;\n rows?: number;\n alwaysOpenEditWindow?: boolean;\n password?: boolean;\n loadOptionsMethod?: string;\n };\n routing?: RoutingConfig;\n}\n\n/**\n * Request defaults configuration\n */\nexport interface RequestDefaults {\n baseURL?: string;\n url?: string;\n headers?: Record<string, string>;\n method?: DeclarativeHttpMethod;\n qs?: Record<string, any>;\n body?: Record<string, any>;\n}\n\n/**\n * Credential definition for declarative nodes\n */\nexport interface CredentialDefinition {\n name: string;\n required?: boolean;\n displayOptions?: DisplayOptions;\n}\n\n/**\n * Complete declarative node type description\n */\nexport interface DeclarativeNodeDescription {\n displayName: string;\n name: string;\n icon?: string;\n group?: string[];\n version?: number | number[];\n subtitle?: string;\n description?: string;\n defaults?: {\n name?: string;\n color?: string;\n };\n inputs?: string[];\n outputs?: string[];\n credentials?: CredentialDefinition[];\n requestDefaults?: RequestDefaults;\n requestOperations?: {\n pagination?: any;\n };\n properties: DeclarativeProperty[];\n}\n\n/**\n * Declarative node type interface (the class structure)\n */\nexport interface IDeclarativeNodeType {\n description: DeclarativeNodeDescription;\n // Optional methods for advanced use cases\n methods?: {\n loadOptions?: Record<string, (this: any) => Promise<PropertyOption[]>>;\n credentialTest?: Record<string, (this: any, credentials: any) => Promise<{ status: string; message: string }>>;\n };\n}\n\n/**\n * Execution context for declarative nodes\n */\nexport interface DeclarativeExecutionContext {\n parameters: Record<string, any>;\n credentials?: Record<string, any>;\n input?: any;\n}\n\n/**\n * Execution result\n */\nexport interface DeclarativeExecutionResult {\n success: boolean;\n data: any;\n status?: number;\n headers?: Record<string, string>;\n}\n\n// ============================================================================\n// Expression Resolver\n// ============================================================================\n\n/**\n * Resolve expressions in strings like:\n * - \"={{$parameter['email']}}\"\n * - \"={{$parameter.email}}\" \n * - \"=/contacts/{{$parameter['id']}}\"\n * - Simple property reference without braces\n */\nexport function resolveExpression(expression: any, context: ExpressionContext): any {\n if (expression === null || expression === undefined) {\n return expression;\n }\n\n if (typeof expression !== 'string') {\n // If it's an object, recursively resolve\n if (typeof expression === 'object' && !Array.isArray(expression)) {\n const resolved: Record<string, any> = {};\n for (const [key, value] of Object.entries(expression)) {\n resolved[key] = resolveExpression(value, context);\n }\n return resolved;\n }\n if (Array.isArray(expression)) {\n return expression.map(item => resolveExpression(item, context));\n }\n return expression;\n }\n\n // Check if it's an expression (starts with = or contains {{ }})\n const trimmed = expression.trim();\n \n // Full expression: ={{...}}\n if (trimmed.startsWith('={{') && trimmed.endsWith('}}')) {\n const expr = trimmed.slice(3, -2);\n return evaluateExpression(expr, context);\n }\n\n // Path expression: =/path/{{...}}\n if (trimmed.startsWith('=') && trimmed.includes('{{')) {\n let result = trimmed.slice(1); // Remove leading =\n // Replace all {{...}} occurrences\n result = result.replace(/\\{\\{([^}]+)\\}\\}/g, (_, expr) => {\n const value = evaluateExpression(expr.trim(), context);\n return value !== undefined && value !== null ? String(value) : '';\n });\n return result;\n }\n\n // Simple expression: =$parameter.email\n if (trimmed.startsWith('=')) {\n const expr = trimmed.slice(1);\n return evaluateExpression(expr, context);\n }\n\n // Template literal style: ${...}\n if (trimmed.includes('${')) {\n let result = trimmed;\n result = result.replace(/\\$\\{([^}]+)\\}/g, (_, expr) => {\n const value = evaluateExpression(expr.trim(), context);\n return value !== undefined && value !== null ? String(value) : '';\n });\n return result;\n }\n\n // No expression, return as-is\n return expression;\n}\n\n/**\n * Evaluate an expression string against the context\n */\nfunction evaluateExpression(expr: string, context: ExpressionContext): any {\n try {\n // Handle $parameter['key'] or $parameter.key syntax\n if (expr.startsWith('$parameter')) {\n return resolvePropertyAccess(expr.slice(1), { parameter: context.$parameter });\n }\n \n // Handle $credentials['key'] or $credentials.key syntax\n if (expr.startsWith('$credentials')) {\n return resolvePropertyAccess(expr.slice(1), { credentials: context.$credentials });\n }\n \n // Handle $response\n if (expr.startsWith('$response')) {\n return resolvePropertyAccess(expr.slice(1), { response: context.$response });\n }\n\n // Handle $input or $json\n if (expr.startsWith('$input') || expr.startsWith('$json')) {\n const key = expr.startsWith('$input') ? 'input' : 'json';\n return resolvePropertyAccess(expr.slice(expr.indexOf('$') + key.length + 1), { [key]: context.$input || context.$json });\n }\n\n // Try to evaluate as a simple JS expression (for things like ternary, etc.)\n // Create a safe evaluation context\n const safeContext = {\n $parameter: context.$parameter || {},\n $credentials: context.$credentials || {},\n $response: context.$response,\n $input: context.$input,\n $json: context.$json,\n };\n\n // Use Function constructor for safe evaluation\n const fn = new Function(...Object.keys(safeContext), `return ${expr}`);\n return fn(...Object.values(safeContext));\n } catch (error) {\n console.warn(`Failed to evaluate expression: ${expr}`, error);\n return undefined;\n }\n}\n\n/**\n * Resolve property access like \"parameter['email']\" or \"parameter.email\"\n */\nfunction resolvePropertyAccess(path: string, obj: Record<string, any>): any {\n // Normalize different access patterns\n // parameter['key'] -> parameter.key\n // parameter[\"key\"] -> parameter.key\n const normalizedPath = path\n .replace(/\\[['\"]([^'\"]+)['\"]\\]/g, '.$1')\n .replace(/\\[(\\d+)\\]/g, '.$1')\n .replace(/^\\./, '');\n\n const parts = normalizedPath.split('.');\n let current: any = obj;\n\n for (const part of parts) {\n if (current === null || current === undefined) {\n return undefined;\n }\n current = current[part];\n }\n\n return current;\n}\n\n// ============================================================================\n// Request Builder\n// ============================================================================\n\n/**\n * Build the final request configuration by merging defaults, operation routing, and property routing\n */\nexport function buildRequest(\n description: DeclarativeNodeDescription,\n context: DeclarativeExecutionContext\n): RequestConfig {\n const expressionContext: ExpressionContext = {\n $parameter: context.parameters,\n $credentials: context.credentials || {},\n $input: context.input,\n };\n\n // Start with request defaults\n const defaults = description.requestDefaults || {};\n \n let config: RequestConfig = {\n baseURL: resolveExpression(defaults.baseURL, expressionContext),\n url: resolveExpression(defaults.url, expressionContext) || '',\n method: (defaults.method || 'GET') as Method,\n headers: { ...resolveExpression(defaults.headers, expressionContext) },\n params: { ...resolveExpression(defaults.qs, expressionContext) },\n data: defaults.body ? { ...resolveExpression(defaults.body, expressionContext) } : undefined,\n };\n\n // Find and apply routing from selected options\n const routingConfigs = collectRoutingConfigs(description.properties, context.parameters, expressionContext);\n\n // Merge all routing configs\n for (const routing of routingConfigs) {\n config = mergeRoutingIntoConfig(config, routing, expressionContext);\n }\n\n // Process all properties for their routing configurations\n for (const prop of description.properties) {\n if (shouldShowProperty(prop, context.parameters)) {\n const propRouting = getPropertyRouting(prop, context.parameters, expressionContext);\n if (propRouting) {\n config = mergeRoutingIntoConfig(config, propRouting, expressionContext);\n }\n }\n }\n\n // Clean up undefined values\n if (config.data && typeof config.data === 'object') {\n config.data = removeUndefinedValues(config.data);\n if (Object.keys(config.data).length === 0) {\n config.data = undefined;\n }\n }\n\n if (config.params && typeof config.params === 'object') {\n config.params = removeUndefinedValues(config.params);\n if (Object.keys(config.params).length === 0) {\n config.params = undefined;\n }\n }\n\n return config;\n}\n\n/**\n * Remove undefined values from an object\n */\nfunction removeUndefinedValues(obj: Record<string, any>): Record<string, any> {\n const result: Record<string, any> = {};\n for (const [key, value] of Object.entries(obj)) {\n if (value !== undefined) {\n result[key] = value;\n }\n }\n return result;\n}\n\n/**\n * Check if a property should be shown based on displayOptions\n */\nfunction shouldShowProperty(prop: DeclarativeProperty, parameters: Record<string, any>): boolean {\n if (!prop.displayOptions) {\n return true;\n }\n\n // Check show conditions\n if (prop.displayOptions.show) {\n for (const [key, values] of Object.entries(prop.displayOptions.show)) {\n const paramValue = parameters[key];\n if (!values.includes(paramValue)) {\n return false;\n }\n }\n }\n\n // Check hide conditions\n if (prop.displayOptions.hide) {\n for (const [key, values] of Object.entries(prop.displayOptions.hide)) {\n const paramValue = parameters[key];\n if (values.includes(paramValue)) {\n return false;\n }\n }\n }\n\n return true;\n}\n\n/**\n * Collect routing configurations from selected options in properties\n */\nfunction collectRoutingConfigs(\n properties: DeclarativeProperty[],\n parameters: Record<string, any>,\n expressionContext: ExpressionContext\n): RoutingConfig[] {\n const configs: RoutingConfig[] = [];\n\n for (const prop of properties) {\n if (!shouldShowProperty(prop, parameters)) {\n continue;\n }\n\n const paramValue = parameters[prop.name];\n\n // Handle options type - find selected option's routing\n if (prop.type === 'options' && prop.options && paramValue !== undefined) {\n const selectedOption = (prop.options as PropertyOption[]).find(\n opt => opt.value === paramValue\n );\n if (selectedOption?.routing) {\n configs.push(selectedOption.routing);\n }\n }\n\n // Handle multiOptions type\n if (prop.type === 'multiOptions' && prop.options && Array.isArray(paramValue)) {\n for (const val of paramValue) {\n const selectedOption = (prop.options as PropertyOption[]).find(\n opt => opt.value === val\n );\n if (selectedOption?.routing) {\n configs.push(selectedOption.routing);\n }\n }\n }\n\n // Handle collection/fixedCollection - recurse into sub-properties\n if ((prop.type === 'collection' || prop.type === 'fixedCollection') && prop.options) {\n const subProperties = prop.options as DeclarativeProperty[];\n const subParams = paramValue || {};\n \n // For fixedCollection, the value is nested under property names\n if (typeof subParams === 'object') {\n for (const subProp of subProperties) {\n const subValue = subParams[subProp.name];\n if (subValue !== undefined && subProp.routing) {\n configs.push(subProp.routing);\n }\n }\n }\n }\n }\n\n return configs;\n}\n\n/**\n * Get routing configuration from a property based on its value\n */\nfunction getPropertyRouting(\n prop: DeclarativeProperty,\n parameters: Record<string, any>,\n expressionContext: ExpressionContext\n): RoutingConfig | null {\n const value = parameters[prop.name];\n \n // If property has direct routing\n if (prop.routing && value !== undefined) {\n return prop.routing;\n }\n\n return null;\n}\n\n/**\n * Merge a routing config into the request config\n */\nfunction mergeRoutingIntoConfig(\n config: RequestConfig,\n routing: RoutingConfig,\n expressionContext: ExpressionContext\n): RequestConfig {\n const request = routing.request;\n \n if (!request) {\n return config;\n }\n\n // Update method if specified\n if (request.method) {\n config.method = request.method as Method;\n }\n\n // Update URL if specified\n if (request.url) {\n const resolvedUrl = resolveExpression(request.url, expressionContext);\n config.url = resolvedUrl;\n }\n\n // Update base URL if specified\n if (request.baseURL) {\n config.baseURL = resolveExpression(request.baseURL, expressionContext);\n }\n\n // Merge headers\n if (request.headers) {\n config.headers = {\n ...config.headers,\n ...resolveExpression(request.headers, expressionContext),\n };\n }\n\n // Merge query parameters\n if (request.qs) {\n config.params = {\n ...config.params,\n ...resolveExpression(request.qs, expressionContext),\n };\n }\n\n // Handle body\n if (request.body) {\n const resolvedBody = resolveExpression(request.body, expressionContext);\n if (typeof config.data === 'object' && typeof resolvedBody === 'object') {\n config.data = { ...config.data, ...resolvedBody };\n } else {\n config.data = resolvedBody;\n }\n }\n\n // Handle send configuration\n if (request.send || routing.send) {\n const send = request.send || routing.send!;\n const sendData = processSend(send, expressionContext);\n \n if (send.type === 'body') {\n if (send.property) {\n // Nest under a property\n config.data = {\n ...config.data,\n [send.property]: sendData,\n };\n } else {\n config.data = {\n ...config.data,\n ...sendData,\n };\n }\n } else if (send.type === 'query') {\n config.params = {\n ...config.params,\n ...sendData,\n };\n }\n }\n\n return config;\n}\n\n/**\n * Process send configuration to build data\n */\nfunction processSend(send: RoutingSend, expressionContext: ExpressionContext): Record<string, any> {\n const data: Record<string, any> = {};\n\n if (send.properties) {\n for (const [key, value] of Object.entries(send.properties)) {\n data[key] = resolveExpression(value, expressionContext);\n }\n }\n\n if (send.value !== undefined) {\n return resolveExpression(send.value, expressionContext);\n }\n\n return data;\n}\n\n// ============================================================================\n// Response Processor\n// ============================================================================\n\n/**\n * Process the response according to output configuration\n */\nexport function processResponse(\n response: any,\n routing: RoutingConfig | undefined,\n expressionContext: ExpressionContext\n): any {\n if (!routing?.output?.postReceive) {\n return response;\n }\n\n let result = response;\n const ctx = { ...expressionContext, $response: response };\n\n for (const action of routing.output.postReceive) {\n result = applyPostReceiveAction(result, action, ctx);\n }\n\n return result;\n}\n\n/**\n * Apply a single post-receive action\n */\nfunction applyPostReceiveAction(\n data: any,\n action: PostReceiveAction,\n context: ExpressionContext\n): any {\n switch (action.type) {\n case 'set':\n if (action.properties?.value) {\n return resolveExpression(action.properties.value, context);\n }\n return data;\n\n case 'setKeyValue':\n if (action.properties?.key) {\n const key = resolveExpression(action.properties.key, context);\n return { [key]: data };\n }\n return data;\n\n case 'rootProperty':\n if (action.properties?.property) {\n const prop = action.properties.property;\n return data?.[prop];\n }\n return data;\n\n case 'filter':\n if (action.properties?.enabled !== undefined) {\n const enabled = resolveExpression(action.properties.enabled, context);\n if (!enabled) {\n return [];\n }\n }\n return data;\n\n case 'limit':\n if (Array.isArray(data) && action.properties?.maxResults) {\n return data.slice(0, action.properties.maxResults);\n }\n return data;\n\n case 'sort':\n // Basic sort implementation\n if (Array.isArray(data)) {\n return [...data].sort();\n }\n return data;\n\n default:\n return data;\n }\n}\n\n// ============================================================================\n// Declarative Executor\n// ============================================================================\n\n/**\n * Execute a declarative node\n */\nexport async function executeDeclarativeNode(\n node: IDeclarativeNodeType,\n context: DeclarativeExecutionContext\n): Promise<DeclarativeExecutionResult> {\n const description = node.description;\n \n // Build the request configuration\n const requestConfig = buildRequest(description, context);\n \n // Add credentials to headers if needed\n if (context.credentials) {\n applyCredentials(requestConfig, context.credentials, description);\n }\n\n // Ensure we have a URL\n if (!requestConfig.url && !requestConfig.baseURL) {\n throw new Error('No URL specified in request configuration or defaults');\n }\n\n try {\n // Build full URL\n let fullUrl = requestConfig.url || '';\n if (requestConfig.baseURL && !fullUrl.startsWith('http://') && !fullUrl.startsWith('https://')) {\n fullUrl = requestConfig.baseURL.replace(/\\/$/, '') + '/' + fullUrl.replace(/^\\//, '');\n }\n \n // Add query params to URL\n if (requestConfig.params && Object.keys(requestConfig.params).length > 0) {\n const params = new URLSearchParams();\n for (const [key, value] of Object.entries(requestConfig.params)) {\n if (value !== undefined && value !== null) {\n params.append(key, String(value));\n }\n }\n fullUrl += (fullUrl.includes('?') ? '&' : '?') + params.toString();\n }\n \n // Prepare headers\n const headers: Record<string, string> = { ...requestConfig.headers };\n \n // Prepare body\n let body: string | undefined;\n if (requestConfig.data) {\n if (!headers['Content-Type']) {\n headers['Content-Type'] = 'application/json';\n }\n body = typeof requestConfig.data === 'string' ? requestConfig.data : JSON.stringify(requestConfig.data);\n }\n \n // Make the request\n const response = await fetch(fullUrl, {\n method: requestConfig.method || 'GET',\n headers,\n body,\n });\n \n // Parse response\n let responseData: any;\n const contentType = response.headers.get('content-type') || '';\n if (contentType.includes('application/json')) {\n responseData = await response.json();\n } else {\n const text = await response.text();\n try {\n responseData = JSON.parse(text);\n } catch {\n responseData = text;\n }\n }\n \n // Convert headers to object\n const responseHeaders: Record<string, string> = {};\n response.headers.forEach((value, key) => {\n responseHeaders[key] = value;\n });\n\n // Find the operation routing for response processing\n const operationRouting = findOperationRouting(description.properties, context.parameters);\n \n // Check for HTTP errors\n if (!response.ok) {\n if (operationRouting?.request?.ignoreHttpStatusErrors) {\n return {\n success: true,\n data: responseData,\n status: response.status,\n headers: responseHeaders,\n };\n }\n throw new Error(`HTTP Error (${response.status}): ${JSON.stringify(responseData)}`);\n }\n \n // Process the response\n const expressionContext: ExpressionContext = {\n $parameter: context.parameters,\n $credentials: context.credentials || {},\n $response: responseData,\n };\n \n const processedData = processResponse(responseData, operationRouting, expressionContext);\n\n return {\n success: true,\n data: processedData,\n status: response.status,\n headers: responseHeaders,\n };\n } catch (error: any) {\n throw new Error(`Request failed: ${error.message}`);\n }\n}\n\n/**\n * Find the routing configuration for the current operation\n */\nfunction findOperationRouting(\n properties: DeclarativeProperty[],\n parameters: Record<string, any>\n): RoutingConfig | undefined {\n for (const prop of properties) {\n if (prop.type === 'options' && prop.options) {\n const value = parameters[prop.name];\n const selectedOption = (prop.options as PropertyOption[]).find(\n opt => opt.value === value\n );\n if (selectedOption?.routing) {\n return selectedOption.routing;\n }\n }\n }\n return undefined;\n}\n\n/**\n * Apply credentials to the request configuration\n */\nfunction applyCredentials(\n config: RequestConfig,\n credentials: Record<string, any>,\n description: DeclarativeNodeDescription\n): void {\n // Common patterns for credential application\n \n // API Key in header\n if (credentials.apiKey) {\n const headerName = credentials.headerName || credentials.apiKeyHeader || 'Authorization';\n const headerPrefix = credentials.headerPrefix || credentials.apiKeyPrefix || '';\n \n config.headers = {\n ...config.headers,\n [headerName]: headerPrefix ? `${headerPrefix} ${credentials.apiKey}` : credentials.apiKey,\n };\n }\n\n // Bearer token\n if (credentials.accessToken || credentials.token || credentials.bearerToken) {\n const token = credentials.accessToken || credentials.token || credentials.bearerToken;\n config.headers = {\n ...config.headers,\n Authorization: `Bearer ${token}`,\n };\n }\n\n // Basic auth\n if (credentials.username && credentials.password) {\n const auth = Buffer.from(`${credentials.username}:${credentials.password}`).toString('base64');\n config.headers = {\n ...config.headers,\n Authorization: `Basic ${auth}`,\n };\n }\n\n // OAuth2 token\n if (credentials.oauthTokenData?.access_token) {\n config.headers = {\n ...config.headers,\n Authorization: `Bearer ${credentials.oauthTokenData.access_token}`,\n };\n }\n}\n\n// ============================================================================\n// Detection and Integration\n// ============================================================================\n\n/**\n * Check if a loaded module is a declarative node type\n */\nexport function isDeclarativeNode(module: any): boolean {\n // Check if it has the description property with the required fields\n if (!module) return false;\n \n // Could be a class instance or the class itself\n const target = module.description ? module : (module.prototype?.description ? new module() : null);\n \n if (!target?.description) return false;\n \n const desc = target.description;\n \n // Must have properties with routing or requestDefaults\n const hasRoutingProperties = desc.properties?.some((prop: DeclarativeProperty) => {\n if (prop.routing) return true;\n if (prop.type === 'options' && prop.options) {\n return (prop.options as PropertyOption[]).some(opt => opt.routing);\n }\n return false;\n });\n\n const hasRequestDefaults = !!desc.requestDefaults;\n \n return hasRoutingProperties || hasRequestDefaults;\n}\n\n/**\n * Extract declarative node from a loaded module\n */\nexport function extractDeclarativeNode(loadedModule: any): IDeclarativeNodeType | null {\n // Check direct export\n if (isDeclarativeNode(loadedModule)) {\n return loadedModule.description ? loadedModule : new loadedModule();\n }\n\n // Check named exports\n for (const key of Object.keys(loadedModule)) {\n const exported = loadedModule[key];\n if (isDeclarativeNode(exported)) {\n return exported.description ? exported : new exported();\n }\n }\n\n // Check default export\n if (loadedModule.default && isDeclarativeNode(loadedModule.default)) {\n return loadedModule.default.description \n ? loadedModule.default \n : new loadedModule.default();\n }\n\n return null;\n}\n\n/**\n * Convert declarative node to Bits action format for compatibility\n */\nexport function declarativeNodeToBitsAction(node: IDeclarativeNodeType): {\n name: string;\n displayName: string;\n description: string;\n props: Record<string, any>;\n run: (context: { auth?: any; propsValue: Record<string, any> }) => Promise<any>;\n} {\n const desc = node.description;\n\n // Convert declarative properties to bits properties\n const props: Record<string, any> = {};\n for (const prop of desc.properties) {\n props[prop.name] = convertDeclarativePropertyToBitsProp(prop);\n }\n\n return {\n name: desc.name,\n displayName: desc.displayName,\n description: desc.description || '',\n props,\n run: async (context) => {\n const result = await executeDeclarativeNode(node, {\n parameters: context.propsValue,\n credentials: context.auth,\n });\n return result.data;\n },\n };\n}\n\n/**\n * Convert a declarative property to bits property format\n */\nfunction convertDeclarativePropertyToBitsProp(prop: DeclarativeProperty): any {\n const base = {\n displayName: prop.displayName,\n description: prop.description,\n required: prop.required || false,\n defaultValue: prop.default,\n };\n\n switch (prop.type) {\n case 'string':\n return { ...base, type: 'SHORT_TEXT' };\n case 'number':\n return { ...base, type: 'NUMBER' };\n case 'boolean':\n return { ...base, type: 'CHECKBOX' };\n case 'options':\n return {\n ...base,\n type: 'STATIC_DROPDOWN',\n options: {\n options: (prop.options as PropertyOption[]).map(opt => ({\n label: opt.name,\n value: opt.value,\n })),\n },\n };\n case 'json':\n return { ...base, type: 'JSON' };\n case 'collection':\n case 'fixedCollection':\n return { ...base, type: 'OBJECT' };\n default:\n return { ...base, type: 'SHORT_TEXT' };\n }\n}\n\n// Alias for execute\nexport const execute = executeDeclarativeNode;\n", "/**\n * Polling Store\n * \n * SQLite-backed store for polling trigger deduplication.\n * Tracks seen items by ID, date, or both to prevent duplicate workflow executions.\n * \n * Uses @ha-bits/bit-database-sql driver functions internally.\n */\n\nimport { LoggerFactory } from '@ha-bits/core/logger';\n\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// Types\n// ============================================================================\n\n/**\n * Deduplication strategy for polling triggers\n */\nexport type DedupStrategy = 'id' | 'date' | 'both';\n\n/**\n * Record of a seen item in the polling store\n */\nexport interface SeenItemRecord {\n /** Unique identifier from the source (e.g., Stripe payment ID) */\n id: string;\n /** Timestamp when the item was created at the source */\n sourceDate: string;\n /** Timestamp when we first saw/processed this item */\n seenAt: string;\n /** Optional: Full item data for debugging/auditing */\n data?: any;\n}\n\n/**\n * Options for the polling store\n */\nexport interface PollingStoreOptions {\n /** Database file name (default: 'habits-polling.db') */\n database?: string;\n /** Collection/table prefix for this trigger (default: 'polling') */\n collection?: string;\n /** Deduplication strategy (default: 'id') */\n dedupStrategy?: DedupStrategy;\n /** Time-to-live in days for seen records (default: 30) - TODO: implement cleanup */\n ttlDays?: number;\n}\n\n/**\n * Context for checking/marking items\n */\nexport interface PollingItemContext {\n /** Trigger identifier (e.g., 'stripe:paymentSucceededPolling') */\n triggerId: string;\n /** Workflow ID this trigger belongs to */\n workflowId: string;\n}\n\n// ============================================================================\n// Driver Functions (lazy loaded)\n// ============================================================================\n\n/**\n * Driver API interface - matches @ha-bits/bit-database-sql/driver exports\n */\ninterface DatabaseDriver {\n store: (params: { collection: string; key: string; value: any; database?: string }) => Promise<any>;\n get: (params: { collection: string; key: string; database?: string }) => Promise<{ found: boolean; value: any }>;\n del: (params: { collection: string; key: string; database?: string }) => Promise<any>;\n list: (params: { collection: string; prefix?: string; limit?: number; database?: string }) => Promise<{ keys: string[] }>;\n}\n\nlet driverModule: DatabaseDriver | null = null;\nlet driverLoadAttempted = false;\nlet useInMemoryFallback = false;\n\n// In-memory fallback storage\nconst inMemoryStore = new Map<string, any>();\n\n/**\n * In-memory driver fallback when SQLite is not available\n */\nconst inMemoryDriver: DatabaseDriver = {\n async store(params) {\n const key = `${params.collection}:${params.key}`;\n inMemoryStore.set(key, params.value);\n return { success: true };\n },\n async get(params) {\n const key = `${params.collection}:${params.key}`;\n if (inMemoryStore.has(key)) {\n return { found: true, value: inMemoryStore.get(key) };\n }\n return { found: false, value: null };\n },\n async del(params) {\n const key = `${params.collection}:${params.key}`;\n inMemoryStore.delete(key);\n return { success: true };\n },\n async list(params) {\n const prefix = `${params.collection}:${params.prefix || ''}`;\n const keys: string[] = [];\n for (const key of inMemoryStore.keys()) {\n if (key.startsWith(prefix)) {\n keys.push(key.replace(`${params.collection}:`, ''));\n }\n }\n return { keys: keys.slice(0, params.limit || 100) };\n },\n};\n\n/**\n * Get the database driver module.\n * Lazy-loads @ha-bits/bit-database-sql/driver to avoid circular dependencies.\n * Falls back to in-memory storage if the module is not available.\n */\nasync function getDriver(): Promise<DatabaseDriver> {\n if (useInMemoryFallback) {\n return inMemoryDriver;\n }\n \n if (!driverModule && !driverLoadAttempted) {\n driverLoadAttempted = true;\n try {\n // Try to load the driver - works in Node.js and bundled (via stub)\n // Using dynamic import with string variable to avoid TypeScript compile-time resolution\n const modulePath = '@ha-bits/bit-database-sql/driver';\n driverModule = await import(/* webpackIgnore: true */ modulePath) as DatabaseDriver;\n logger.log('\uD83D\uDCBE Polling store: Loaded database driver');\n } catch (err: any) {\n logger.warn(`\uD83D\uDCBE Polling store: Database driver not available, using in-memory fallback: ${err.message}`);\n useInMemoryFallback = true;\n return inMemoryDriver;\n }\n }\n \n return driverModule || inMemoryDriver;\n}\n\n// ============================================================================\n// Polling Store Class\n// ============================================================================\n\n/**\n * PollingStore - SQLite-backed store for polling trigger deduplication.\n * \n * @example\n * ```ts\n * const store = new PollingStore({\n * collection: 'stripe_payments',\n * dedupStrategy: 'id',\n * });\n * \n * const ctx = { triggerId: 'stripe:paymentSucceeded', workflowId: 'wf-123' };\n * \n * // Check if we've seen this payment before\n * if (await store.hasSeenItem(ctx, 'pi_abc123')) {\n * console.log('Already processed');\n * } else {\n * // Process the payment\n * await store.markItemSeen(ctx, 'pi_abc123', '2024-01-15T10:00:00Z');\n * }\n * ```\n */\nexport class PollingStore {\n private options: Required<PollingStoreOptions>;\n\n constructor(options: PollingStoreOptions = {}) {\n this.options = {\n database: options.database ?? 'habits-polling.db',\n collection: options.collection ?? 'polling',\n dedupStrategy: options.dedupStrategy ?? 'id',\n ttlDays: options.ttlDays ?? 30,\n };\n }\n\n /**\n * Generate a unique key for a seen item\n */\n private getItemKey(ctx: PollingItemContext, itemId: string): string {\n return `${ctx.workflowId}:${ctx.triggerId}:${itemId}`;\n }\n\n /**\n * Generate the key for storing last polled date\n */\n private getLastPolledKey(ctx: PollingItemContext): string {\n return `${ctx.workflowId}:${ctx.triggerId}:__lastPolled__`;\n }\n\n /**\n * Check if an item has been seen before\n */\n async hasSeenItem(ctx: PollingItemContext, itemId: string, itemDate?: string): Promise<boolean> {\n const driver = await getDriver();\n const key = this.getItemKey(ctx, itemId);\n\n const result = await driver.get({\n collection: this.options.collection,\n key,\n database: this.options.database,\n });\n\n if (!result.found) {\n return false;\n }\n\n // If using date-based dedup, also check the date\n if (this.options.dedupStrategy === 'date' && itemDate) {\n const record = result.value as SeenItemRecord;\n // Item is considered \"seen\" if we have a record with same or newer date\n return new Date(record.sourceDate) >= new Date(itemDate);\n }\n\n // For 'id' or 'both' strategy, existence is enough\n return true;\n }\n\n /**\n * Mark an item as seen\n */\n async markItemSeen(\n ctx: PollingItemContext,\n itemId: string,\n sourceDate: string,\n data?: any\n ): Promise<void> {\n const driver = await getDriver();\n const key = this.getItemKey(ctx, itemId);\n\n const record: SeenItemRecord = {\n id: itemId,\n sourceDate,\n seenAt: new Date().toISOString(),\n data: data,\n };\n\n await driver.store({\n collection: this.options.collection,\n key,\n value: record,\n database: this.options.database,\n });\n\n logger.log(`\uD83D\uDCBE Polling store: Marked item as seen: ${itemId}`);\n }\n\n /**\n * Get multiple items' seen status in batch\n * Returns a Set of item IDs that have been seen\n */\n async getSeenItems(ctx: PollingItemContext, itemIds: string[]): Promise<Set<string>> {\n const seen = new Set<string>();\n \n // Check each item - could be optimized with a query in the future\n for (const itemId of itemIds) {\n if (await this.hasSeenItem(ctx, itemId)) {\n seen.add(itemId);\n }\n }\n\n return seen;\n }\n\n /**\n * Mark multiple items as seen in batch\n */\n async markItemsSeen(\n ctx: PollingItemContext,\n items: Array<{ id: string; date: string; data?: any }>\n ): Promise<void> {\n for (const item of items) {\n await this.markItemSeen(ctx, item.id, item.date, item.data);\n }\n }\n\n /**\n * Get the last polled timestamp for a trigger\n * Returns null if never polled before\n */\n async getLastPolledDate(ctx: PollingItemContext): Promise<string | null> {\n const driver = await getDriver();\n const key = this.getLastPolledKey(ctx);\n\n const result = await driver.get({\n collection: this.options.collection,\n key,\n database: this.options.database,\n });\n\n if (!result.found) {\n return null;\n }\n\n return result.value as string;\n }\n\n /**\n * Set the last polled timestamp for a trigger\n */\n async setLastPolledDate(ctx: PollingItemContext, date: string): Promise<void> {\n const driver = await getDriver();\n const key = this.getLastPolledKey(ctx);\n\n await driver.store({\n collection: this.options.collection,\n key,\n value: date,\n database: this.options.database,\n });\n\n logger.log(`\uD83D\uDCBE Polling store: Updated last polled date: ${date}`);\n }\n\n /**\n * Get the count of seen items for a trigger\n */\n async getSeenCount(ctx: PollingItemContext): Promise<number> {\n const driver = await getDriver();\n const prefix = `${ctx.workflowId}:${ctx.triggerId}:`;\n\n const result = await driver.list({\n collection: this.options.collection,\n prefix,\n limit: 10000, // High limit to count all\n database: this.options.database,\n });\n\n // Subtract 1 if lastPolled key exists\n const count = result.keys.filter((k: string) => !k.endsWith('__lastPolled__')).length;\n return count;\n }\n\n /**\n * Clear all seen items for a trigger (useful for testing or reset)\n */\n async clearTrigger(ctx: PollingItemContext): Promise<number> {\n const driver = await getDriver();\n const prefix = `${ctx.workflowId}:${ctx.triggerId}:`;\n\n const result = await driver.list({\n collection: this.options.collection,\n prefix,\n limit: 10000,\n database: this.options.database,\n });\n\n let deleted = 0;\n for (const key of result.keys) {\n await driver.del({\n collection: this.options.collection,\n key,\n database: this.options.database,\n });\n deleted++;\n }\n\n logger.log(`\uD83D\uDCBE Polling store: Cleared ${deleted} items for trigger ${ctx.triggerId}`);\n return deleted;\n }\n\n /**\n * TODO: Implement TTL-based cleanup\n * Clean up old records based on ttlDays configuration\n */\n async cleanup(): Promise<number> {\n // TODO: Implement cleanup based on ttlDays\n // This would require querying all records and deleting those older than ttlDays\n // For now, this is a no-op placeholder\n logger.log(`\uD83D\uDCBE Polling store: Cleanup not yet implemented (TTL: ${this.options.ttlDays} days)`);\n return 0;\n }\n}\n\n// ============================================================================\n// Factory Function\n// ============================================================================\n\n/**\n * Create a new PollingStore instance\n */\nexport function createPollingStore(options?: PollingStoreOptions): PollingStore {\n return new PollingStore(options);\n}\n\n// ============================================================================\n// Default Export\n// ============================================================================\n\nexport default PollingStore;\n", "/**\n * OAuth2 Token Store\n * \n * In-memory storage for OAuth2 tokens with optional file persistence.\n * Tokens are keyed by bit module identifier.\n */\n\nimport { OAuth2TokenSet, OAuth2Config, TokenStoreEntry } from './oauth2Types';\nimport { ILogger, LoggerFactory } from '@ha-bits/core/logger';\n\n/**\n * In-memory OAuth2 token store\n */\nclass OAuth2TokenStore {\n private tokens: Map<string, TokenStoreEntry> = new Map();\n private logger: ILogger;\n\n constructor() {\n this.logger = LoggerFactory.create(undefined, undefined, { bitName: 'OAuth2TokenStore' });\n }\n\n /**\n * Store tokens for a bit\n * @param bitId - Unique identifier for the bit (e.g., \"bit-oauth-mock\")\n * @param tokens - Token set from OAuth provider\n * @param config - OAuth config used (for refresh)\n */\n setToken(bitId: string, tokens: OAuth2TokenSet, config: OAuth2Config): void {\n this.tokens.set(bitId, {\n tokens,\n config,\n storedAt: Date.now(),\n });\n this.logger.info('Token stored', { bitId, expiresAt: tokens.expiresAt });\n }\n\n /**\n * Get tokens for a bit\n * @param bitId - Unique identifier for the bit\n * @returns Token set or null if not found\n */\n getToken(bitId: string): OAuth2TokenSet | null {\n const entry = this.tokens.get(bitId);\n if (!entry) {\n return null;\n }\n return entry.tokens;\n }\n\n /**\n * Get full token entry including config\n * @param bitId - Unique identifier for the bit\n */\n getEntry(bitId: string): TokenStoreEntry | null {\n return this.tokens.get(bitId) || null;\n }\n\n /**\n * Check if a valid (non-expired) token exists for a bit\n * @param bitId - Unique identifier for the bit\n * @returns true if valid token exists\n */\n hasValidToken(bitId: string): boolean {\n const entry = this.tokens.get(bitId);\n if (!entry) {\n return false;\n }\n return !this.isExpired(bitId);\n }\n\n /**\n * Check if token is expired\n * @param bitId - Unique identifier for the bit\n * @returns true if token is expired or doesn't exist\n */\n isExpired(bitId: string): boolean {\n const entry = this.tokens.get(bitId);\n if (!entry) {\n return true;\n }\n if (!entry.tokens.expiresAt) {\n // No expiration set, assume valid\n return false;\n }\n // Add 60 second buffer to account for clock skew\n return Date.now() > entry.tokens.expiresAt - 60000;\n }\n\n /**\n * Remove token for a bit\n * @param bitId - Unique identifier for the bit\n */\n removeToken(bitId: string): void {\n this.tokens.delete(bitId);\n this.logger.info('Token removed', { bitId });\n }\n\n /**\n * Get all stored bit IDs\n */\n getAllBitIds(): string[] {\n return Array.from(this.tokens.keys());\n }\n\n /**\n * Clear all tokens\n */\n clear(): void {\n this.tokens.clear();\n this.logger.info('All tokens cleared');\n }\n\n /**\n * Refresh an expired token using the refresh token\n * @param bitId - Unique identifier for the bit\n * @returns New token set or null if refresh failed\n */\n async refreshToken(bitId: string): Promise<OAuth2TokenSet | null> {\n const entry = this.tokens.get(bitId);\n if (!entry || !entry.tokens.refreshToken) {\n this.logger.warn('Cannot refresh token: no refresh token available', { bitId });\n return null;\n }\n\n const { config, tokens } = entry;\n\n try {\n const params = new URLSearchParams({\n grant_type: 'refresh_token',\n refresh_token: tokens.refreshToken!,\n client_id: config.clientId,\n });\n\n if (config.clientSecret) {\n params.set('client_secret', config.clientSecret);\n }\n\n const response = await fetch(config.tokenUrl, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/x-www-form-urlencoded',\n },\n body: params.toString(),\n });\n\n if (!response.ok) {\n const errorText = await response.text();\n this.logger.error('Token refresh failed', { bitId, status: response.status, error: errorText });\n return null;\n }\n\n const data = await response.json() as any;\n\n const newTokens: OAuth2TokenSet = {\n accessToken: data.access_token,\n refreshToken: data.refresh_token || tokens.refreshToken, // Keep old refresh token if not returned\n tokenType: data.token_type || 'Bearer',\n expiresAt: data.expires_in ? Date.now() + data.expires_in * 1000 : undefined,\n scope: data.scope,\n };\n\n this.setToken(bitId, newTokens, config);\n this.logger.info('Token refreshed successfully', { bitId });\n\n return newTokens;\n } catch (error) {\n this.logger.error('Token refresh error', { bitId, error: String(error) });\n return null;\n }\n }\n}\n\n// Singleton instance\nexport const oauthTokenStore = new OAuth2TokenStore();\n", "/**\n * Bits Module Executor\n * \n * Executes bits modules.\n */\n\nimport { ensureModuleInstalled, getModuleName, getBundledModule, isBundledModule } from '../utils/moduleLoader';\nimport { getModuleMainFile, ModuleDefinition } from '../utils/moduleCloner';\nimport * as path from '@ha-bits/bindings/path';\nimport { simpleRequire } from '../utils/customRequire';\nimport { \n isDeclarativeNode, \n extractDeclarativeNode, \n executeDeclarativeNode,\n declarativeNodeToBitsAction,\n type IDeclarativeNodeType \n} from './declarativeExecutor';\nimport { PollingStore, DedupStrategy, PollingItemContext, SeenItemRecord, PollingStoreOptions } from '../store';\n\n// Re-export polling store types for consumers\nexport { PollingStore, DedupStrategy, PollingItemContext, SeenItemRecord, PollingStoreOptions };\nimport { oauthTokenStore } from './oauthTokenStore';\nimport { OAuth2TokenSet } from './oauth2Types';\nimport { ILogger, LoggerFactory } from '@ha-bits/core/logger';\n\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// Workflow Executor Interface (minimal for bits to invoke sub-workflows)\n// ============================================================================\n\n/**\n * Minimal interface for workflow executor that bits can use to invoke sub-workflows.\n * Avoids circular dependency with WorkflowExecutor.\n */\nexport interface IWorkflowExecutor {\n /** Execute a workflow by ID with optional initial context */\n executeWorkflow(workflowId: string, options?: {\n initialContext?: Record<string, any>;\n }): Promise<{\n id: string;\n workflowId: string;\n status: 'pending' | 'running' | 'completed' | 'failed' | 'cancelled';\n results: Array<{ success: boolean; result?: any; error?: string }>;\n output?: any;\n }>;\n}\n\n// ============================================================================\n// Types \n// ============================================================================\n\n/**\n * Represents a Bits action that can be executed\n */\nexport interface BitsAction {\n name: string;\n displayName: string;\n description: string;\n props: Record<string, any>;\n run: (context: BitsActionContext) => Promise<any>;\n}\n\n/**\n * Context passed to action.run()\n */\nexport interface BitsActionContext {\n auth?: any;\n propsValue: Record<string, any>;\n store?: BitsStore;\n files?: any;\n /** Logger instance for structured logging */\n logger?: ILogger;\n /** Workflow executor for invoking sub-workflows directly */\n executor?: IWorkflowExecutor;\n}\n\n/**\n * Webhook filter payload - passed to trigger.filter() to determine if trigger should handle the event\n */\nexport interface WebhookFilterPayload {\n /** Raw request body */\n body: any;\n /** HTTP headers */\n headers: Record<string, string>;\n /** Query string parameters */\n query: Record<string, string>;\n /** HTTP method */\n method: string;\n}\n\n/**\n * Represents a Bits trigger\n */\nexport interface BitsTrigger {\n name: string;\n displayName: string;\n description: string;\n type: BitsTriggerType;\n props: Record<string, any>;\n onEnable?: (context: BitsTriggerContext) => Promise<void>;\n onDisable?: (context: BitsTriggerContext) => Promise<void>;\n run?: (context: BitsTriggerContext) => Promise<any[]>;\n test?: (context: BitsTriggerContext) => Promise<any[]>;\n onHandshake?: (context: BitsTriggerContext) => Promise<any>;\n /**\n * Filter function for webhook triggers.\n * Called when a webhook is received for this bit's module.\n * Return true if this trigger should handle the event, false to skip.\n * If not defined, the trigger accepts all webhook events.\n */\n filter?: (payload: WebhookFilterPayload) => boolean | Promise<boolean>;\n}\n\n/**\n * Trigger types\n */\nexport enum BitsTriggerType {\n POLLING = 'POLLING',\n WEBHOOK = 'WEBHOOK',\n APP_WEBHOOK = 'APP_WEBHOOK',\n}\n\n/**\n * Context passed to trigger methods\n */\nexport interface BitsTriggerContext {\n auth?: any;\n propsValue: Record<string, any>;\n payload: unknown;\n webhookUrl?: string;\n store: BitsStore;\n app: {\n createListeners: (listener: BitsListener) => void;\n };\n setSchedule: (options: BitsScheduleOptions) => void;\n /** Workflow executor for invoking workflows (including self) */\n executor?: IWorkflowExecutor;\n /** ID of the workflow this trigger belongs to */\n workflowId?: string;\n /** ID of this trigger node */\n nodeId?: string;\n /** Webhook payload data (for webhook triggers) */\n webhookPayload?: WebhookFilterPayload;\n /** Polling store for deduplication (for polling triggers) */\n pollingStore?: BitsPollingStore;\n}\n\n/**\n * Listener configuration for app webhooks\n */\nexport interface BitsListener {\n events: string[];\n identifierValue: string;\n identifierKey: string;\n}\n\n/**\n * Schedule options for polling triggers\n */\nexport interface BitsScheduleOptions {\n cronExpression: string;\n timezone?: string;\n}\n\n/**\n * Simple key-value store interface\n */\nexport interface BitsStore {\n get: <T>(key: string) => Promise<T | null>;\n put: <T>(key: string, value: T) => Promise<void>;\n delete: (key: string) => Promise<void>;\n}\n\n/**\n * Extended store interface with polling deduplication support\n */\nexport interface BitsPollingStore extends BitsStore {\n /** Check if an item has been seen before (for deduplication) */\n hasSeenItem: (itemId: string, itemDate?: string) => Promise<boolean>;\n /** Mark an item as seen */\n markItemSeen: (itemId: string, sourceDate: string, data?: any) => Promise<void>;\n /** Get the last polled timestamp */\n getLastPolledDate: () => Promise<string | null>;\n /** Set the last polled timestamp */\n setLastPolledDate: (date: string) => Promise<void>;\n /** Get count of seen items */\n getSeenCount: () => Promise<number>;\n /** Clear all seen items for this trigger */\n clearTrigger: () => Promise<number>;\n}\n\n/**\n * Represents a loaded Bits piece/module\n */\nexport interface BitsPiece {\n /**\n * Unique identifier for this bit module.\n * Used for webhook routing: /webhook/:id\n * Example: 'gohighlevel', 'hubspot', 'salesforce'\n */\n id?: string;\n displayName: string;\n description?: string;\n logoUrl?: string;\n auth?: any;\n actions: () => Record<string, BitsAction>;\n triggers: () => Record<string, BitsTrigger>;\n}\n\n/**\n * Execution parameters for bits module\n */\nexport interface BitsExecutionParams {\n source: string;\n framework: string;\n moduleName: string;\n params: Record<string, any>;\n /** Logger instance to pass to bit context */\n logger?: ILogger;\n /** Workflow ID for context */\n workflowId?: string;\n /** Node ID for context */\n nodeId?: string;\n /** Execution ID for tracing */\n executionId?: string;\n /** Workflow executor for invoking sub-workflows directly */\n executor?: IWorkflowExecutor;\n /** \n * OAuth tokens from request cookies (per-user tokens).\n * These take precedence over the global token store.\n * Key is bitId (e.g., \"bit-google-drive\"), value is the token set.\n */\n oauthTokens?: Record<string, OAuth2TokenSet>;\n}\n\n/**\n * Result of bits module execution\n */\nexport interface BitsExecutionResult {\n success: boolean;\n module: string;\n pieceLoaded: boolean;\n params: Record<string, any>;\n result: any;\n executedAt: string;\n data: {\n message: string;\n status: string;\n pieceExports: string[];\n };\n}\n\n// ============================================================================\n// Module Loading\n// ============================================================================\n\n/**\n * Extract piece from a loaded module.\n * Bits modules export a piece object with 'actions' and 'triggers' properties.\n * Also supports declarative nodes (n8n-style) that have a description with routing.\n */\nexport function extractBitsPieceFromModule(loadedModule: any): BitsPiece {\n // First, check if this is a declarative node (n8n-style with routing)\n const declarativeNode = extractDeclarativeNode(loadedModule);\n if (declarativeNode) {\n logger.log(`\uD83D\uDCCB Detected declarative node: ${declarativeNode.description.displayName}`);\n return convertDeclarativeNodeToBitsPiece(declarativeNode);\n }\n\n // Find the piece export in the module\n // It's the object that has both 'actions' and 'triggers' methods/properties\n let piece: any = null;\n\n // Check if it's a direct export\n if (loadedModule && typeof loadedModule === 'object') {\n // Check direct properties\n for (const key of Object.keys(loadedModule)) {\n const exported = loadedModule[key];\n if (exported && typeof exported === 'object') {\n // Check if it has actions and triggers (either as functions or objects)\n const hasActions = 'actions' in exported;\n const hasTriggers = 'triggers' in exported;\n if (hasActions && hasTriggers) {\n piece = exported;\n break;\n }\n }\n }\n }\n\n if (!piece) {\n throw new Error('No valid bits piece found in module. Expected export with actions and triggers.');\n }\n\n // Normalize the piece to our interface\n return {\n id: piece.id, // Webhook routing ID (e.g., 'gohighlevel', 'hubspot')\n displayName: piece.displayName || 'Unknown Piece',\n description: piece.description,\n logoUrl: piece.logoUrl,\n auth: piece.auth,\n actions: typeof piece.actions === 'function' \n ? piece.actions.bind(piece)\n : () => piece.actions || {},\n triggers: typeof piece.triggers === 'function'\n ? piece.triggers.bind(piece)\n : () => piece.triggers || {},\n };\n}\n\n/**\n * Convert a declarative node to BitsPiece format\n */\nfunction convertDeclarativeNodeToBitsPiece(node: IDeclarativeNodeType): BitsPiece {\n const desc = node.description;\n \n // Extract operations from properties to create actions\n const actions: Record<string, BitsAction> = {};\n \n // Find operation/resource properties to determine available actions\n const operationProp = desc.properties.find(p => p.name === 'operation');\n const resourceProp = desc.properties.find(p => p.name === 'resource');\n \n if (operationProp?.options) {\n // Create an action for each operation\n for (const opt of operationProp.options as any[]) {\n if (opt.value && opt.routing) {\n const actionName = String(opt.value);\n actions[actionName] = {\n name: actionName,\n displayName: opt.name || actionName,\n description: opt.description || '',\n props: buildPropsForOperation(desc.properties, actionName, resourceProp?.default),\n run: createDeclarativeActionRunner(node, actionName),\n };\n }\n }\n }\n \n // If no operation-based actions found, create a single \"execute\" action\n if (Object.keys(actions).length === 0) {\n actions['execute'] = {\n name: 'execute',\n displayName: desc.displayName,\n description: desc.description || '',\n props: buildPropsFromDeclarative(desc.properties),\n run: createDeclarativeActionRunner(node),\n };\n }\n\n return {\n displayName: desc.displayName,\n description: desc.description,\n logoUrl: desc.icon,\n auth: undefined, // Declarative nodes handle auth differently\n actions: () => actions,\n triggers: () => ({}), // Declarative nodes typically don't have triggers\n };\n}\n\n/**\n * Build props for a specific operation\n */\nfunction buildPropsForOperation(\n properties: any[],\n operation: string,\n resource?: string\n): Record<string, any> {\n const props: Record<string, any> = {};\n \n for (const prop of properties) {\n // Skip operation and resource props - they're handled differently\n if (prop.name === 'operation' || prop.name === 'resource') continue;\n \n // Check if prop should be shown for this operation\n if (prop.displayOptions?.show) {\n const showOp = prop.displayOptions.show.operation;\n const showRes = prop.displayOptions.show.resource;\n \n if (showOp && !showOp.includes(operation)) continue;\n if (showRes && resource && !showRes.includes(resource)) continue;\n }\n \n props[prop.name] = convertDeclarativePropertyToProp(prop);\n }\n \n return props;\n}\n\n/**\n * Build props from declarative properties\n */\nfunction buildPropsFromDeclarative(properties: any[]): Record<string, any> {\n const props: Record<string, any> = {};\n \n for (const prop of properties) {\n props[prop.name] = convertDeclarativePropertyToProp(prop);\n }\n \n return props;\n}\n\n/**\n * Convert declarative property to bits prop format\n */\nfunction convertDeclarativePropertyToProp(prop: any): any {\n const base = {\n displayName: prop.displayName,\n description: prop.description,\n required: prop.required || false,\n defaultValue: prop.default,\n };\n\n switch (prop.type) {\n case 'string':\n return { ...base, type: 'SHORT_TEXT' };\n case 'number':\n return { ...base, type: 'NUMBER' };\n case 'boolean':\n return { ...base, type: 'CHECKBOX' };\n case 'options':\n return {\n ...base,\n type: 'STATIC_DROPDOWN',\n options: {\n options: (prop.options || []).map((opt: any) => ({\n label: opt.name,\n value: opt.value,\n })),\n },\n };\n case 'json':\n return { ...base, type: 'JSON' };\n case 'collection':\n case 'fixedCollection':\n return { ...base, type: 'OBJECT' };\n default:\n return { ...base, type: 'SHORT_TEXT' };\n }\n}\n\n/**\n * Create a runner function for declarative actions\n */\nfunction createDeclarativeActionRunner(\n node: IDeclarativeNodeType,\n operation?: string\n): (context: BitsActionContext) => Promise<any> {\n return async (context: BitsActionContext) => {\n const parameters = { ...context.propsValue };\n \n // Add operation to parameters if specified\n if (operation) {\n parameters.operation = operation;\n }\n \n const result = await executeDeclarativeNode(node, {\n parameters,\n credentials: context.auth,\n });\n \n return result.data;\n };\n}\n\n/**\n * Load a bits piece from module definition\n */\nexport async function pieceFromModule(moduleDefinition: ModuleDefinition): Promise<BitsPiece> {\n const moduleName = getModuleName(moduleDefinition);\n\n // Check if module is pre-bundled (for browser/IIFE bundles)\n if (isBundledModule(moduleDefinition.repository)) {\n logger.log(`\uD83D\uDCE6 Using pre-bundled module: ${moduleName}`);\n const loadedModule = getBundledModule(moduleDefinition.repository);\n if (loadedModule) {\n const piece = extractBitsPieceFromModule(loadedModule);\n return piece;\n }\n throw new Error(`Bundled module ${moduleName} not found in registry`);\n }\n\n // For non-bundled modules, use filesystem-based loading\n // Get the main file path\n const mainFilePath = getModuleMainFile(moduleDefinition);\n if (!mainFilePath) {\n throw new Error(`Could not locate main file for module: ${moduleName}`);\n }\n\n logger.log(`\uD83D\uDCE6 Bits module ready at: ${mainFilePath}`);\n\n // Save current working directory and change to module directory for proper resolution\n const originalCwd = process.cwd();\n const moduleDir = path.dirname(mainFilePath);\n\n // Find the node_modules directory containing the module\n let nodeModulesDir = moduleDir;\n while (nodeModulesDir && !nodeModulesDir.endsWith('/node_modules') && nodeModulesDir !== path.dirname(nodeModulesDir)) {\n nodeModulesDir = path.dirname(nodeModulesDir);\n }\n\n try {\n process.chdir(moduleDir);\n // Use simpleRequire which creates require from the node_modules context\n const loadedModule = simpleRequire(mainFilePath, nodeModulesDir);\n\n // Extract piece\n const piece = extractBitsPieceFromModule(loadedModule);\n \n process.chdir(originalCwd);\n return piece;\n } catch (error: any) {\n process.chdir(originalCwd);\n logger.error(error.stack);\n throw error;\n }\n}\n\n// ============================================================================\n// Action Execution\n// ============================================================================\n\n/**\n * Execute a bits module action\n */\nasync function executeGenericBitsPiece(\n params: BitsExecutionParams,\n moduleDefinition: ModuleDefinition\n): Promise<BitsExecutionResult> {\n try {\n const piece = await pieceFromModule(moduleDefinition);\n\n logger.log(`\uD83D\uDE80 Executing Bits piece: ${piece.displayName}`);\n const actionName = params.params.operation;\n const pieceActions = piece.actions();\n logger.log(`Available actions: ${Object.keys(pieceActions).join(', ')}`);\n logger.log(`Requested action: ${actionName}`);\n \n const action = pieceActions[actionName];\n\n // If action is not found, throw error with available actions\n if (!action) {\n throw new Error(\n `Action '${actionName}' not found in piece '${piece.displayName}'. Available actions: ${Object.keys(pieceActions).join(', ')}`\n );\n }\n\n // Extract auth from credentials if present\n let auth: any = undefined;\n const { credentials, ...actionProps } = params.params;\n \n // Check if this piece uses OAuth2 authentication\n if (piece.auth && ((piece.auth as any).type === 'OAUTH2' || (piece.auth as any).type === 'OAUTH2_PKCE')) {\n // Extract bit ID from module name (e.g., \"@ha-bits/bit-oauth-mock\" -> \"bit-oauth-mock\")\n const parts = moduleDefinition.repository.split('/');\n const bitId = parts[parts.length - 1];\n \n // Priority 1: Check if credentials contain OAuth tokens directly (bypasses OAuth callback flow)\n // This allows users to provide tokens obtained externally (e.g., from dev console)\n const oauthCredKey = Object.keys(credentials || {}).find(key => {\n const cred = credentials[key];\n return cred && (cred.accessToken || cred.access_token);\n });\n \n if (oauthCredKey && credentials[oauthCredKey]) {\n const directTokens = credentials[oauthCredKey];\n auth = {\n accessToken: directTokens.accessToken || directTokens.access_token,\n refreshToken: directTokens.refreshToken || directTokens.refresh_token,\n tokenType: directTokens.tokenType || directTokens.token_type || 'Bearer',\n expiresAt: directTokens.expiresAt || directTokens.expires_at,\n };\n logger.log(`\uD83D\uDD10 Using OAuth2 tokens from credentials for: ${bitId}`);\n \n // Optionally store in token store for future refresh capability\n if (auth.refreshToken) {\n const pieceAuth = piece.auth as any;\n oauthTokenStore.setToken(bitId, auth, {\n displayName: pieceAuth.displayName || bitId,\n required: pieceAuth.required || false,\n authorizationUrl: pieceAuth.authorizationUrl || '',\n tokenUrl: pieceAuth.tokenUrl || '',\n clientId: pieceAuth.clientId || '',\n clientSecret: pieceAuth.clientSecret,\n scopes: pieceAuth.scopes || [],\n });\n }\n } else if (params.oauthTokens && params.oauthTokens[bitId]) {\n // Priority 2: Check for per-user OAuth tokens from request cookies (server mode with multi-user)\n const userToken = params.oauthTokens[bitId];\n auth = {\n accessToken: userToken.accessToken,\n refreshToken: userToken.refreshToken,\n tokenType: userToken.tokenType,\n expiresAt: userToken.expiresAt,\n };\n logger.log(`\uD83D\uDD10 Using per-user OAuth2 token from cookies for: ${bitId}`);\n \n // Token refresh for per-user tokens would need to be handled differently\n // (e.g., trigger re-auth flow if expired)\n if (userToken.expiresAt && userToken.expiresAt < Date.now()) {\n logger.warn(`\u26A0\uFE0F Per-user OAuth token expired for ${bitId}. User needs to re-authenticate.`);\n }\n } else {\n // Priority 3: Try to get OAuth token from global store (single-user mode or Tauri)\n const oauthToken = oauthTokenStore.getToken(bitId);\n if (oauthToken) {\n auth = {\n accessToken: oauthToken.accessToken,\n refreshToken: oauthToken.refreshToken,\n tokenType: oauthToken.tokenType,\n expiresAt: oauthToken.expiresAt,\n };\n logger.log(`\uD83D\uDD10 Using OAuth2 PKCE token for: ${bitId}`);\n \n // Check if token is expired and try to refresh\n if (oauthTokenStore.isExpired(bitId)) {\n logger.log(`\u26A0\uFE0F OAuth token expired for ${bitId}, attempting refresh...`);\n const refreshedToken = await oauthTokenStore.refreshToken(bitId);\n if (refreshedToken) {\n auth = {\n accessToken: refreshedToken.accessToken,\n refreshToken: refreshedToken.refreshToken,\n tokenType: refreshedToken.tokenType,\n expiresAt: refreshedToken.expiresAt,\n };\n logger.log(`\u2705 OAuth token refreshed for ${bitId}`);\n } else {\n logger.warn(`\u274C Failed to refresh OAuth token for ${bitId}`);\n }\n }\n } else {\n logger.warn(`\u26A0\uFE0F No OAuth token found for ${bitId}. Provide tokens via credentials or complete the OAuth flow.`);\n }\n }\n } else if (credentials) {\n const credentialKeys = Object.keys(credentials);\n if (credentialKeys.length > 0) {\n // Pass auth data directly - pieces access auth properties directly (e.g., auth.host, auth.apiKey)\n auth = credentials[credentialKeys[0]];\n logger.log(`\uD83D\uDD10 Using credentials for: ${credentialKeys[0]}`);\n }\n }\n\n // Create bit-scoped logger if a parent logger was provided\n let bitLogger: ILogger | undefined = undefined;\n if (params.logger) {\n bitLogger = params.logger.child({\n bitName: moduleDefinition.repository,\n actionName: actionName,\n workflowId: params.workflowId,\n nodeId: params.nodeId,\n executionId: params.executionId,\n });\n }\n\n // Execute the action\n const result = await action.run({\n auth,\n propsValue: {\n ...actionProps,\n },\n logger: bitLogger,\n executor: params.executor,\n } as BitsActionContext);\n\n logger.log(`\u2705 Successfully executed Bits piece action: ${actionName}`, result);\n\n return {\n success: true,\n module: moduleDefinition.repository,\n pieceLoaded: true,\n params,\n result,\n executedAt: new Date().toISOString(),\n data: {\n message: `Successfully executed Bits piece: ${piece.displayName}`,\n status: 'completed',\n pieceExports: Object.keys(pieceActions),\n },\n };\n } catch (error: any) {\n logger.error(error.stack);\n throw error;\n }\n}\n\n// ============================================================================\n// Main Export\n// ============================================================================\n\n/**\n * Execute a bits module.\n * This is the main entry point for running bits modules.\n */\nexport async function executeBitsModule(params: BitsExecutionParams): Promise<BitsExecutionResult> {\n // Get module definition from config\n const moduleDefinition: ModuleDefinition = {\n framework: params.framework,\n source: params.source as 'github' | 'npm',\n repository: params.moduleName,\n };\n\n if (!moduleDefinition) {\n throw new Error(`Bits module '${params.moduleName}' not found in modules.json`);\n }\n\n // Ensure module is installed\n const inferredModuleName = getModuleName(moduleDefinition);\n logger.log(`\\n\uD83D\uDD0D Ensuring bits module is ready: ${inferredModuleName}`);\n await ensureModuleInstalled(moduleDefinition);\n\n try {\n return await executeGenericBitsPiece(params, moduleDefinition);\n } catch (error: any) {\n throw new Error(`Failed to load Bits module from '${moduleDefinition.repository}': ${error.message}`);\n }\n}\n\n/**\n * Get available actions from a bits module\n */\nexport async function getBitsModuleActions(params: {\n source: string;\n framework: string;\n moduleName: string;\n}): Promise<string[]> {\n const moduleDefinition: ModuleDefinition = {\n framework: params.framework,\n source: params.source as 'github' | 'npm',\n repository: params.moduleName,\n };\n\n await ensureModuleInstalled(moduleDefinition);\n const piece = await pieceFromModule(moduleDefinition);\n return Object.keys(piece.actions());\n}\n\n/**\n * Get available triggers from a bits module\n */\nexport async function getBitsModuleTriggers(params: {\n source: string;\n framework: string;\n moduleName: string;\n}): Promise<string[]> {\n const moduleDefinition: ModuleDefinition = {\n framework: params.framework,\n source: params.source as 'github' | 'npm',\n repository: params.moduleName,\n };\n\n await ensureModuleInstalled(moduleDefinition);\n const piece = await pieceFromModule(moduleDefinition);\n return Object.keys(piece.triggers());\n}\n", "/**\n * Bits Trigger Watcher\n * \n * Handles bits module triggers (polling, webhook, app webhook).\n */\n\nimport { ensureModuleInstalled } from '../utils/moduleLoader';\nimport { ModuleDefinition } from '../utils/moduleCloner';\nimport { \n pieceFromModule, \n BitsPiece, \n BitsTrigger, \n BitsTriggerType, \n BitsStore,\n BitsPollingStore,\n BitsTriggerContext,\n BitsListener,\n BitsScheduleOptions,\n} from './bitsDoer';\nimport { PollingStore, createPollingStore, DedupStrategy } from '../store';\nimport { LoggerFactory } from '@ha-bits/core/logger';\n\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport enum TriggerHookType {\n ON_ENABLE = 'ON_ENABLE',\n ON_DISABLE = 'ON_DISABLE',\n RUN = 'RUN',\n TEST = 'TEST',\n HANDSHAKE = 'HANDSHAKE',\n}\n\nexport interface TriggerExecutionParams {\n moduleDefinition: ModuleDefinition;\n triggerName: string;\n input: Record<string, any>;\n hookType: TriggerHookType;\n trigger?: BitsTrigger;\n payload?: unknown;\n webhookUrl?: string;\n isTest?: boolean;\n store?: BitsStore;\n /** Workflow executor for invoking workflows */\n executor?: any;\n /** ID of the workflow this trigger belongs to */\n workflowId?: string;\n /** ID of this trigger node */\n nodeId?: string;\n}\n\nexport interface TriggerExecutionResult {\n success: boolean;\n output?: unknown[];\n message?: string;\n listeners?: BitsListener[];\n scheduleOptions?: BitsScheduleOptions;\n response?: unknown;\n}\n\n// ============================================================================\n// Simple In-Memory Store\n// ============================================================================\n\nfunction createSimpleStore(prefix: string = ''): BitsStore {\n const storage = new Map<string, unknown>();\n\n return {\n async get<T>(key: string): Promise<T | null> {\n const fullKey = `${prefix}:${key}`;\n return (storage.get(fullKey) as T) ?? null;\n },\n async put<T>(key: string, value: T): Promise<void> {\n const fullKey = `${prefix}:${key}`;\n storage.set(fullKey, value);\n },\n async delete(key: string): Promise<void> {\n const fullKey = `${prefix}:${key}`;\n storage.delete(fullKey);\n },\n };\n}\n\n// ============================================================================\n// Polling Store Factory\n// ============================================================================\n\n/**\n * Create a polling store bound to a specific trigger context.\n * Returns a BitsPollingStore that wraps PollingStore with pre-bound context.\n */\nfunction createBoundPollingStore(\n workflowId: string,\n triggerId: string,\n dedupStrategy: DedupStrategy = 'id'\n): BitsPollingStore {\n const store = createPollingStore({\n collection: 'polling_seen_items',\n dedupStrategy,\n });\n\n const ctx = { workflowId, triggerId };\n const baseStore = createSimpleStore(`polling:${workflowId}:${triggerId}`);\n\n return {\n // Base store methods\n get: baseStore.get,\n put: baseStore.put,\n delete: baseStore.delete,\n\n // Polling-specific methods\n async hasSeenItem(itemId: string, itemDate?: string): Promise<boolean> {\n return store.hasSeenItem(ctx, itemId, itemDate);\n },\n async markItemSeen(itemId: string, sourceDate: string, data?: any): Promise<void> {\n return store.markItemSeen(ctx, itemId, sourceDate, data);\n },\n async getLastPolledDate(): Promise<string | null> {\n return store.getLastPolledDate(ctx);\n },\n async setLastPolledDate(date: string): Promise<void> {\n return store.setLastPolledDate(ctx, date);\n },\n async getSeenCount(): Promise<number> {\n return store.getSeenCount(ctx);\n },\n async clearTrigger(): Promise<number> {\n return store.clearTrigger(ctx);\n },\n };\n}\n\n// ============================================================================\n// Helper to check if value is nil (null or undefined)\n// ============================================================================\n\nfunction isNil(value: any): value is null | undefined {\n return value === null || value === undefined;\n}\n\n// ============================================================================\n// Map trigger type from loaded module to our enum\n// ============================================================================\n\nfunction mapTriggerType(type: string | undefined): BitsTriggerType {\n if (!type) return BitsTriggerType.POLLING;\n \n const typeUpper = type.toUpperCase();\n switch (typeUpper) {\n case 'POLLING':\n return BitsTriggerType.POLLING;\n case 'WEBHOOK':\n return BitsTriggerType.WEBHOOK;\n case 'APP_WEBHOOK':\n return BitsTriggerType.APP_WEBHOOK;\n default:\n return BitsTriggerType.POLLING;\n }\n}\n\n// ============================================================================\n// Bits Trigger Helper\n// ============================================================================\n\nexport const bitsTriggerHelper = {\n /**\n * Load a piece from module definition\n */\n async loadPieceFromModule(moduleDefinition: ModuleDefinition): Promise<BitsPiece> {\n await ensureModuleInstalled(moduleDefinition);\n return pieceFromModule(moduleDefinition);\n },\n\n /**\n * Get a specific trigger from a piece\n */\n async getTrigger(\n moduleDefinition: ModuleDefinition,\n triggerName: string\n ): Promise<{ piece: BitsPiece; trigger: BitsTrigger }> {\n const piece = await this.loadPieceFromModule(moduleDefinition);\n const triggers = piece.triggers();\n const trigger = triggers[triggerName];\n\n if (!trigger) {\n const availableTriggers = Object.keys(triggers).join(', ');\n throw new Error(\n `Trigger '${triggerName}' not found. Available triggers: ${availableTriggers || 'none'}`\n );\n }\n\n return { piece, trigger };\n },\n\n /**\n * Execute a trigger based on hook type\n */\n async executeTrigger(params: TriggerExecutionParams): Promise<TriggerExecutionResult> {\n const { moduleDefinition, triggerName, input, hookType, trigger, payload, webhookUrl, isTest, store, executor, workflowId, nodeId } = params;\n\n if (isNil(triggerName)) {\n throw new Error('Trigger name is not set');\n }\n\n let bitsTrigger: BitsTrigger;\n if (trigger) {\n bitsTrigger = trigger;\n } else {\n const { trigger: loadedTrigger } = await this.getTrigger(moduleDefinition, triggerName);\n bitsTrigger = loadedTrigger;\n }\n\n logger.log(`\uD83D\uDD14 Executing bits trigger: ${triggerName} (${hookType})`);\n\n const appListeners: BitsListener[] = [];\n let scheduleOptions: BitsScheduleOptions | undefined;\n const storePrefix = isTest ? 'test' : triggerName;\n\n // Use provided store or create a new one\n const triggerStore = store || createSimpleStore(storePrefix);\n\n // Determine trigger type to decide if we need a polling store\n const triggerType = mapTriggerType((bitsTrigger as any).type);\n \n // Create polling store for POLLING triggers\n let pollingStore: BitsPollingStore | undefined;\n if (triggerType === BitsTriggerType.POLLING && workflowId) {\n // Get dedup strategy from trigger props if specified\n const dedupStrategy = (input.dedupBy as DedupStrategy) || 'id';\n const triggerId = `${moduleDefinition.repository}:${triggerName}`;\n pollingStore = createBoundPollingStore(workflowId, triggerId, dedupStrategy);\n logger.log(`\uD83D\uDCCA Created polling store for ${triggerId} (dedup: ${dedupStrategy})`);\n }\n\n // Extract auth from credentials if present\n let auth: any = undefined;\n const { credentials, ...triggerProps } = input;\n if (credentials) {\n const credentialKeys = Object.keys(credentials);\n if (credentialKeys.length > 0) {\n const credentialData = credentials[credentialKeys[0]];\n // Wrap in props structure and also spread at top level\n auth = {\n props: credentialData,\n ...credentialData,\n };\n logger.log(`\uD83D\uDD10 Using credentials for trigger: ${credentialKeys[0]}`);\n }\n }\n\n // Build context for trigger execution\n const context: BitsTriggerContext = {\n auth,\n propsValue: triggerProps,\n payload: payload ?? {},\n webhookUrl,\n store: triggerStore,\n app: {\n createListeners(listener: BitsListener): void {\n appListeners.push(listener);\n },\n },\n setSchedule(options: BitsScheduleOptions): void {\n scheduleOptions = {\n cronExpression: options.cronExpression,\n timezone: options.timezone ?? 'UTC',\n };\n },\n executor,\n workflowId,\n nodeId,\n pollingStore,\n };\n\n try {\n switch (hookType) {\n case TriggerHookType.ON_ENABLE: {\n if (bitsTrigger.onEnable) {\n await bitsTrigger.onEnable(context);\n }\n const triggerTypeForResult = mapTriggerType((bitsTrigger as any).type);\n return {\n success: true,\n listeners: appListeners,\n scheduleOptions: triggerTypeForResult === BitsTriggerType.POLLING ? scheduleOptions : undefined,\n };\n }\n\n case TriggerHookType.ON_DISABLE: {\n if (bitsTrigger.onDisable) {\n await bitsTrigger.onDisable(context);\n }\n return { success: true };\n }\n\n case TriggerHookType.HANDSHAKE: {\n if (bitsTrigger.onHandshake) {\n const response = await bitsTrigger.onHandshake(context);\n return {\n success: true,\n response,\n };\n }\n return {\n success: false,\n message: 'Trigger does not support handshake',\n };\n }\n\n case TriggerHookType.TEST: {\n if (bitsTrigger.test) {\n const testResult = await bitsTrigger.test(context);\n return {\n success: true,\n output: Array.isArray(testResult) ? testResult : [testResult],\n };\n }\n return {\n success: false,\n message: 'Trigger does not support test mode',\n output: [],\n };\n }\n\n case TriggerHookType.RUN: {\n if (bitsTrigger.run) {\n const runResult = await bitsTrigger.run(context);\n return {\n success: true,\n output: Array.isArray(runResult) ? runResult : [runResult],\n };\n }\n return {\n success: false,\n message: 'Trigger does not have a run method',\n output: [],\n };\n }\n\n default:\n return {\n success: false,\n message: `Unknown hook type: ${hookType}`,\n };\n }\n } catch (error: any) {\n logger.error(`Error executing trigger ${triggerName}:`, error);\n return {\n success: false,\n message: `Error executing trigger: ${(error)}`,\n output: [],\n };\n }\n },\n\n /**\n * List all triggers from a piece\n */\n async listTriggers(moduleDefinition: ModuleDefinition): Promise<{\n triggers: Array<{\n name: string;\n displayName: string;\n description: string;\n type: BitsTriggerType;\n }>;\n }> {\n const piece = await this.loadPieceFromModule(moduleDefinition);\n const triggers = piece.triggers();\n\n return {\n triggers: Object.entries(triggers).map(([name, trigger]) => ({\n name,\n displayName: trigger.displayName,\n description: trigger.description,\n type: mapTriggerType((trigger as any).type),\n })),\n };\n },\n\n /**\n * Execute trigger with proper flow based on trigger type\n * For polling: calls onEnable first, then run\n * For webhooks: calls run directly\n */\n async executeBitsTrigger(params: {\n moduleDefinition: ModuleDefinition;\n triggerName: string;\n input: Record<string, any>;\n payload?: unknown;\n webhookUrl?: string;\n store?: BitsStore;\n executor?: any;\n workflowId?: string;\n nodeId?: string;\n }): Promise<TriggerExecutionResult> {\n const { moduleDefinition, triggerName, input, payload, webhookUrl, store, executor, workflowId, nodeId } = params;\n\n // Get the trigger to determine its type\n const { piece, trigger } = await this.getTrigger(moduleDefinition, triggerName);\n const triggerType = mapTriggerType((trigger as any).type);\n\n const triggerStore = store || createSimpleStore(`trigger:${triggerName}`);\n\n switch (triggerType) {\n case BitsTriggerType.POLLING: {\n logger.log(`Polling trigger flow: onEnable \u2192 run`);\n\n const onEnableResult = await this.executeTrigger({\n moduleDefinition,\n triggerName,\n input,\n hookType: TriggerHookType.ON_ENABLE,\n trigger,\n payload,\n webhookUrl,\n isTest: false,\n store: triggerStore,\n executor,\n workflowId,\n nodeId,\n });\n\n if (!onEnableResult.success) {\n return onEnableResult;\n }\n\n logger.log(` \u2705 onEnable completed`);\n if (onEnableResult.scheduleOptions) {\n logger.log(` \uD83D\uDCC5 Schedule: ${onEnableResult.scheduleOptions.cronExpression} (${onEnableResult.scheduleOptions.timezone})`);\n }\n if (onEnableResult.listeners && onEnableResult.listeners.length > 0) {\n logger.log(` \uD83D\uDC42 Listeners: ${onEnableResult.listeners.length}`);\n }\n\n logger.log(` \u2192 Calling run to fetch items...`);\n const runResult = await this.executeTrigger({\n moduleDefinition,\n triggerName,\n input,\n hookType: TriggerHookType.RUN,\n trigger,\n payload,\n webhookUrl,\n isTest: false,\n store: triggerStore,\n executor,\n workflowId,\n nodeId,\n });\n\n if (!runResult.success) {\n logger.warn(` \u26A0\uFE0F Run failed: ${runResult.message}`);\n } else {\n logger.log(` \u2705 Run completed, items found: ${runResult.output?.length || 0}`);\n }\n\n return runResult;\n }\n\n case BitsTriggerType.WEBHOOK: {\n logger.log(`Webhook trigger`);\n\n return await this.executeTrigger({\n moduleDefinition,\n triggerName,\n input,\n hookType: TriggerHookType.RUN,\n payload,\n webhookUrl,\n isTest: false,\n executor,\n workflowId,\n nodeId,\n });\n }\n\n default: {\n return {\n success: false,\n message: `Unsupported trigger type: ${triggerType}`,\n output: [],\n };\n }\n }\n },\n\n /**\n * Hook triggers for a piece - sets up polling/webhooks based on trigger type\n */\n async hookTriggers(\n moduleDefinition: ModuleDefinition,\n options?: {\n webhookBaseUrl?: string;\n onPollingTrigger?: (triggerName: string, trigger: BitsTrigger) => void;\n onWebhookTrigger?: (triggerName: string, trigger: BitsTrigger) => void;\n onAppWebhookTrigger?: (triggerName: string, trigger: BitsTrigger) => void;\n onTriggerResult?: (triggerName: string, result: TriggerExecutionResult) => void;\n input?: Record<string, any>;\n }\n ): Promise<void> {\n const piece = await this.loadPieceFromModule(moduleDefinition);\n const triggers = piece.triggers();\n\n for (const [triggerName, trigger] of Object.entries(triggers)) {\n const triggerType = mapTriggerType((trigger as any).type);\n logger.log(`\uD83D\uDD14 Hooking trigger: ${triggerName} (type: ${triggerType})`);\n\n switch (triggerType) {\n case BitsTriggerType.POLLING:\n logger.log(` \u2192 Setting up polling trigger`);\n if (options?.onPollingTrigger) {\n options.onPollingTrigger(triggerName, trigger);\n }\n\n // Auto-run polling trigger immediately\n logger.log(` \uD83D\uDE80 Running polling trigger immediately...`);\n try {\n const result = await this.executeBitsTrigger({\n moduleDefinition,\n triggerName,\n input: options?.input || {},\n });\n\n if (result.success) {\n logger.log(` \u2705 Trigger ${triggerName} executed successfully`);\n logger.log(` \uD83D\uDCE6 Output items: ${result.output?.length || 0}`);\n } else {\n logger.warn(` \u26A0\uFE0F Trigger ${triggerName} failed: ${result.message}`);\n }\n\n if (options?.onTriggerResult) {\n options.onTriggerResult(triggerName, result);\n }\n } catch (error: any) {\n logger.error(` \u274C Error running trigger ${triggerName}:`, error.message);\n }\n break;\n\n case BitsTriggerType.WEBHOOK:\n logger.log(` \u2192 Setting up webhook trigger`);\n if (options?.onWebhookTrigger) {\n options.onWebhookTrigger(triggerName, trigger);\n }\n break;\n\n case BitsTriggerType.APP_WEBHOOK:\n logger.log(` \u2192 Setting up app webhook trigger`);\n if (options?.onAppWebhookTrigger) {\n options.onAppWebhookTrigger(triggerName, trigger);\n }\n break;\n\n default:\n logger.warn(` \u26A0\uFE0F Unknown trigger type: ${triggerType}`);\n }\n }\n },\n\n /**\n * Validate cron expression (simple validation)\n */\n isValidCron(expression: string): boolean {\n const parts = expression.trim().split(/\\s+/);\n return parts.length >= 5 && parts.length <= 6;\n },\n\n /**\n * Check if a node is a Bits trigger (polling or webhook)\n */\n isBitsTrigger(node: any): boolean {\n return (\n node.data?.framework === 'bits' &&\n (node.data?.triggerType === 'polling' || node.data?.triggerType === 'webhook')\n );\n },\n\n /**\n * Check if a node is a webhook trigger\n */\n isWebhookTrigger(node: any): boolean {\n return (\n node.type === 'trigger' &&\n node.data?.framework === 'bits' &&\n (node.data?.triggerType === 'webhook' || node.data?.operation === 'catch_webhook')\n );\n },\n\n /**\n * Extract webhook trigger configuration from a node\n */\n getWebhookConfig(node: any): {\n nodeId: string;\n path: string;\n authType: 'none' | 'header' | 'query_param';\n authFields: Record<string, any>;\n } {\n return {\n nodeId: node.id,\n path: `/webhook/${node.id}`,\n authType: node.data?.triggerSettings?.authType || 'none',\n authFields: node.data?.triggerSettings?.authFields || {},\n };\n },\n\n /**\n * Execute a webhook trigger with received payload\n */\n async executeWebhookTrigger(\n nodeId: string,\n payload: any,\n headers?: Record<string, string>,\n query?: Record<string, string>\n ): Promise<TriggerExecutionResult> {\n logger.log(`\uD83D\uDD14 Executing webhook trigger for node: ${nodeId}`);\n\n return {\n success: true,\n output: [\n {\n body: payload,\n headers: headers || {},\n query: query || {},\n method: 'POST',\n timestamp: new Date().toISOString(),\n },\n ],\n message: 'Webhook received successfully',\n };\n },\n};\n\n// ============================================================================\n// Utility Functions\n// ============================================================================\n\n/**\n * Try-catch wrapper that returns a result object\n */\nexport async function tryCatch<T>(\n fn: () => Promise<T>\n): Promise<{ data: T | null; error: Error | null }> {\n try {\n const data = await fn();\n return { data, error: null };\n } catch (error: any) {\n return { data: null, error };\n }\n}\n\n// Re-export types for convenience\nexport { \n BitsTrigger, \n BitsTriggerType, \n BitsStore, \n BitsTriggerContext,\n BitsListener,\n BitsScheduleOptions,\n} from './bitsDoer';\n\nexport default bitsTriggerHelper;\n", "/**\n * Script Executor\n * \n * Executes scripts in a Node.js environment.\n * Supports TypeScript/JavaScript (converted from Deno), Python, Go, and Bash scripts.\n */\n\nimport * as fs from 'fs';\nimport * as path from 'path';\nimport * as vm from 'vm';\nimport { spawn, execSync } from 'child_process';\nimport * as os from 'os';\nimport * as ts from 'typescript';\nimport {\n ScriptDefinition,\n ScriptExecutionParams,\n ScriptExecutionResult,\n ScriptContext,\n ScriptState,\n DenoToNodeConversionResult,\n} from './types';\nimport { LoggerFactory } from '@ha-bits/core/logger';\n\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// Internal State Management\n// ============================================================================\n\nconst internalStates: Map<string, ScriptState> = new Map();\n\nfunction getInternalStatePath(scriptPath: string): string {\n return `state:${scriptPath}`;\n}\n\nasync function getInternalState(scriptPath: string): Promise<any> {\n return internalStates.get(getInternalStatePath(scriptPath)) || null;\n}\n\nasync function setInternalState(scriptPath: string, state: any): Promise<void> {\n internalStates.set(getInternalStatePath(scriptPath), state);\n}\n\n// ============================================================================\n// Deno to Node.js Conversion\n// ============================================================================\n\n/**\n * Convert Deno imports to Node.js compatible imports\n */\nfunction convertDenoImports(code: string): DenoToNodeConversionResult {\n const npmPackages: string[] = [];\n const imports: string[] = [];\n let convertedCode = code;\n\n // Replace Deno.land imports with npm equivalents\n const denoImportPatterns: Array<{\n pattern: RegExp;\n replacement: string | ((match: string, ...args: string[]) => string);\n npmPackage?: string;\n }> = [\n {\n pattern: /import\\s+\\*\\s+as\\s+wmill\\s+from\\s+[\"']https:\\/\\/deno\\.land\\/x\\/[@\\w.]*\\/mod\\.ts[\"'];?/g,\n replacement: `// Script SDK (mocked for Node.js)\nconst wmill = {\n getInternalStatePath: () => '__internal_state__',\n getInternalState: async () => globalThis.__script_state || null,\n setInternalState: async (state) => { globalThis.__script_state = state; },\n getVariable: async (path) => process.env[path] || null,\n setVariable: async (path, value) => { process.env[path] = value; },\n getResource: async (path) => globalThis.__script_resources?.[path] || null,\n};`,\n },\n // Standard library fetch (use native)\n {\n pattern: /import\\s*{\\s*([^}]+)\\s*}\\s*from\\s+[\"']https:\\/\\/deno\\.land\\/std[@\\w.]*\\/http\\/mod\\.ts[\"'];?/g,\n replacement: '', // fetch is native in Node 18+\n },\n // Crypto\n {\n pattern: /import\\s*{\\s*([^}]+)\\s*}\\s*from\\s+[\"']https:\\/\\/deno\\.land\\/std[@\\w.]*\\/crypto\\/mod\\.ts[\"'];?/g,\n replacement: `const crypto = require('crypto');`,\n },\n // Path\n {\n pattern: /import\\s*{\\s*([^}]+)\\s*}\\s*from\\s+[\"']https:\\/\\/deno\\.land\\/std[@\\w.]*\\/path\\/mod\\.ts[\"'];?/g,\n replacement: `const path = require('path');`,\n },\n // fs\n {\n pattern: /import\\s*{\\s*([^}]+)\\s*}\\s*from\\s+[\"']https:\\/\\/deno\\.land\\/std[@\\w.]*\\/fs\\/mod\\.ts[\"'];?/g,\n replacement: `const fs = require('fs').promises;`,\n },\n // npm: imports\n {\n pattern: /import\\s+(?:(\\*\\s+as\\s+\\w+)|{([^}]+)}|(\\w+))\\s+from\\s+[\"']npm:([^@\"']+)(?:@[^\"']*)?[\"'];?/g,\n replacement: (match: string, star: string, named: string, defaultImport: string, pkg: string) => {\n npmPackages.push(pkg);\n if (star) {\n return `const ${star.replace('* as ', '')} = require('${pkg}');`;\n } else if (named) {\n return `const { ${named} } = require('${pkg}');`;\n } else {\n return `const ${defaultImport} = require('${pkg}');`;\n }\n },\n },\n ];\n\n for (const { pattern, replacement, npmPackage } of denoImportPatterns) {\n if (typeof replacement === 'function') {\n convertedCode = convertedCode.replace(pattern, replacement as any);\n } else {\n convertedCode = convertedCode.replace(pattern, replacement);\n }\n if (npmPackage) {\n npmPackages.push(npmPackage);\n }\n }\n\n // Replace Deno.* APIs with Node.js equivalents\n const denoApiReplacements: Array<[RegExp, string]> = [\n [/Deno\\.env\\.get\\(([^)]+)\\)/g, 'process.env[$1]'],\n [/Deno\\.env\\.set\\(([^,]+),\\s*([^)]+)\\)/g, 'process.env[$1] = $2'],\n [/Deno\\.args/g, 'process.argv.slice(2)'],\n [/Deno\\.exit\\(([^)]*)\\)/g, 'process.exit($1)'],\n [/Deno\\.cwd\\(\\)/g, 'process.cwd()'],\n [/Deno\\.readTextFile\\(([^)]+)\\)/g, 'fs.readFileSync($1, \"utf-8\")'],\n [/Deno\\.writeTextFile\\(([^,]+),\\s*([^)]+)\\)/g, 'fs.writeFileSync($1, $2)'],\n [/Deno\\.readFile\\(([^)]+)\\)/g, 'fs.readFileSync($1)'],\n [/Deno\\.writeFile\\(([^,]+),\\s*([^)]+)\\)/g, 'fs.writeFileSync($1, $2)'],\n [/Deno\\.remove\\(([^)]+)\\)/g, 'fs.unlinkSync($1)'],\n [/Deno\\.mkdir\\(([^)]+)\\)/g, 'fs.mkdirSync($1, { recursive: true })'],\n [/Deno\\.stat\\(([^)]+)\\)/g, 'fs.statSync($1)'],\n ];\n\n for (const [pattern, replacement] of denoApiReplacements) {\n convertedCode = convertedCode.replace(pattern, replacement);\n }\n\n // Extract import statements for reference\n const importRegex = /^(import\\s+.+from\\s+['\"].+['\"];?)$/gm;\n let match;\n while ((match = importRegex.exec(code)) !== null) {\n imports.push(match[1]);\n }\n\n return {\n code: convertedCode,\n imports,\n npmPackages: [...new Set(npmPackages)],\n };\n}\n\n/**\n * Convert TypeScript to JavaScript using the TypeScript compiler\n */\nfunction transpileTypeScript(code: string): string {\n // Use TypeScript compiler to transpile\n const result = ts.transpileModule(code, {\n compilerOptions: {\n module: ts.ModuleKind.CommonJS,\n target: ts.ScriptTarget.ES2020,\n strict: false,\n esModuleInterop: true,\n skipLibCheck: true,\n removeComments: false,\n },\n });\n\n let jsCode = result.outputText;\n\n // Remove CommonJS exports wrapper if present\n jsCode = jsCode.replace(/^\"use strict\";\\s*/m, '');\n jsCode = jsCode.replace(/Object\\.defineProperty\\(exports,\\s*\"__esModule\",\\s*\\{\\s*value:\\s*true\\s*\\}\\);?\\s*/g, '');\n jsCode = jsCode.replace(/exports\\.\\w+\\s*=\\s*/g, '');\n\n return jsCode;\n}\n\n/**\n * Convert Deno script to Node.js compatible JavaScript\n */\nexport function convertDenoToNode(code: string): string {\n // First convert Deno-specific imports and APIs\n const { code: convertedCode } = convertDenoImports(code);\n \n // Then transpile TypeScript to JavaScript\n const jsCode = transpileTypeScript(convertedCode);\n \n return jsCode;\n}\n\n// ============================================================================\n// Script Execution\n// ============================================================================\n\n/**\n * Execute a JavaScript/TypeScript script in Node.js\n */\nasync function executeJavaScript(\n code: string,\n params: Record<string, any>,\n context: ScriptContext\n): Promise<any> {\n // Convert Deno code to Node.js\n const nodeCode = convertDenoToNode(code);\n \n // Create a wrapper that exports the main function result\n const wrappedCode = `\n ${nodeCode}\n \n // Execute main function\n (async () => {\n if (typeof main === 'function') {\n return await main(...Object.values(__params__));\n }\n throw new Error('No main function found in script');\n })();\n `;\n\n // Create a sandbox context\n const sandbox: Record<string, any> = {\n __params__: params,\n __context__: context,\n globalThis: {\n __script_state: null,\n __script_resources: {},\n },\n console,\n process,\n require,\n fetch,\n Buffer,\n setTimeout,\n setInterval,\n clearTimeout,\n clearInterval,\n Promise,\n JSON,\n Object,\n Array,\n String,\n Number,\n Boolean,\n Date,\n Math,\n RegExp,\n Error,\n URL,\n URLSearchParams,\n TextEncoder: globalThis.TextEncoder,\n TextDecoder: globalThis.TextDecoder,\n crypto: globalThis.crypto,\n fs: require('fs'),\n path: require('path'),\n };\n\n const vmContext = vm.createContext(sandbox);\n \n try {\n const script = new vm.Script(wrappedCode, {\n filename: 'script-executor.js',\n });\n \n const result = await script.runInContext(vmContext, {\n timeout: 300000, // 5 minute timeout\n });\n \n return result;\n } catch (error: any) {\n logger.error(`JavaScript execution error: ${error.message}`);\n throw error;\n }\n}\n\n/**\n * Execute a Python script\n */\nasync function executePython(\n code: string,\n params: Record<string, any>,\n context: ScriptContext\n): Promise<any> {\n const tmpDir = os.tmpdir();\n const scriptPath = path.join(tmpDir, `script_${Date.now()}.py`);\n \n // Create a wrapper that calls main with parameters\n const paramsList = Object.entries(params)\n .map(([key, value]) => `${key}=${JSON.stringify(value)}`)\n .join(', ');\n \n const wrappedCode = `\nimport json\nimport sys\n\n# Inject context\nflow_input = json.loads('''${JSON.stringify(context.flow_input)}''')\nprevious_result = json.loads('''${JSON.stringify(context.previous_result)}''')\n\n${code}\n\nif __name__ == \"__main__\":\n try:\n result = main(${paramsList})\n print(json.dumps({\"success\": True, \"result\": result}))\n except Exception as e:\n print(json.dumps({\"success\": False, \"error\": str(e)}))\n sys.exit(1)\n`;\n\n fs.writeFileSync(scriptPath, wrappedCode);\n\n return new Promise((resolve, reject) => {\n const pythonCmd = process.platform === 'win32' ? 'python' : 'python3';\n const proc = spawn(pythonCmd, [scriptPath], {\n env: { ...process.env },\n cwd: tmpDir,\n });\n\n let stdout = '';\n let stderr = '';\n\n proc.stdout.on('data', (data) => {\n stdout += data.toString();\n });\n\n proc.stderr.on('data', (data) => {\n stderr += data.toString();\n });\n\n proc.on('close', (exitCode) => {\n // Clean up temp file\n try {\n fs.unlinkSync(scriptPath);\n } catch {}\n\n if (exitCode !== 0) {\n reject(new Error(`Python script failed: ${stderr || stdout}`));\n return;\n }\n\n try {\n // Parse the last line as JSON result\n const lines = stdout.trim().split('\\n');\n const lastLine = lines[lines.length - 1];\n const result = JSON.parse(lastLine);\n \n if (result.success) {\n resolve(result.result);\n } else {\n reject(new Error(result.error));\n }\n } catch (parseError) {\n // Return raw output if not JSON\n resolve(stdout.trim());\n }\n });\n\n proc.on('error', (error) => {\n try {\n fs.unlinkSync(scriptPath);\n } catch {}\n reject(new Error(`Failed to spawn Python: ${error.message}`));\n });\n });\n}\n\n/**\n * Execute a Go script\n */\nasync function executeGo(\n code: string,\n params: Record<string, any>,\n context: ScriptContext\n): Promise<any> {\n const tmpDir = os.tmpdir();\n const scriptDir = path.join(tmpDir, `script_go_${Date.now()}`);\n const scriptPath = path.join(scriptDir, 'main.go');\n \n // Create directory\n fs.mkdirSync(scriptDir, { recursive: true });\n\n // Create a wrapper for the Go code\n const wrappedCode = `\npackage main\n\nimport (\n\t\"encoding/json\"\n\t\"fmt\"\n\t\"os\"\n)\n\nvar flowInput = \\`${JSON.stringify(context.flow_input)}\\`\nvar previousResult = \\`${JSON.stringify(context.previous_result)}\\`\nvar params = \\`${JSON.stringify(params)}\\`\n\n${code}\n\nfunc main() {\n\tvar p map[string]interface{}\n\tjson.Unmarshal([]byte(params), &p)\n\t\n\tresult := Main(p)\n\t\n\toutput, _ := json.Marshal(map[string]interface{}{\n\t\t\"success\": true,\n\t\t\"result\": result,\n\t})\n\tfmt.Println(string(output))\n}\n`;\n\n fs.writeFileSync(scriptPath, wrappedCode);\n\n return new Promise((resolve, reject) => {\n try {\n // Build the Go program\n execSync(`go build -o main`, { cwd: scriptDir, stdio: 'pipe' });\n \n // Run the compiled program\n const proc = spawn('./main', [], {\n cwd: scriptDir,\n env: { ...process.env },\n });\n\n let stdout = '';\n let stderr = '';\n\n proc.stdout.on('data', (data) => {\n stdout += data.toString();\n });\n\n proc.stderr.on('data', (data) => {\n stderr += data.toString();\n });\n\n proc.on('close', (exitCode) => {\n // Clean up\n try {\n fs.rmSync(scriptDir, { recursive: true, force: true });\n } catch {}\n\n if (exitCode !== 0) {\n reject(new Error(`Go script failed: ${stderr || stdout}`));\n return;\n }\n\n try {\n const lines = stdout.trim().split('\\n');\n const lastLine = lines[lines.length - 1];\n const result = JSON.parse(lastLine);\n \n if (result.success) {\n resolve(result.result);\n } else {\n reject(new Error(result.error));\n }\n } catch {\n resolve(stdout.trim());\n }\n });\n\n proc.on('error', (error) => {\n try {\n fs.rmSync(scriptDir, { recursive: true, force: true });\n } catch {}\n reject(new Error(`Failed to run Go: ${error.message}`));\n });\n } catch (error: any) {\n try {\n fs.rmSync(scriptDir, { recursive: true, force: true });\n } catch {}\n reject(new Error(`Failed to build Go: ${error.message}`));\n }\n });\n}\n\n/**\n * Execute a Bash script\n */\nasync function executeBash(\n code: string,\n params: Record<string, any>,\n context: ScriptContext\n): Promise<any> {\n const tmpDir = os.tmpdir();\n const scriptPath = path.join(tmpDir, `script_${Date.now()}.sh`);\n \n // Export parameters as environment variables\n const envExports = Object.entries(params)\n .map(([key, value]) => {\n const safeValue = typeof value === 'string' \n ? value.replace(/'/g, \"'\\\\''\") \n : JSON.stringify(value);\n return `export ${key}='${safeValue}'`;\n })\n .join('\\n');\n \n const wrappedCode = `#!/bin/bash\nset -e\n\n# Exported parameters\n${envExports}\n\n# Context\nexport FLOW_INPUT='${JSON.stringify(context.flow_input)}'\nexport PREVIOUS_RESULT='${JSON.stringify(context.previous_result)}'\n\n# User script\n${code}\n`;\n\n fs.writeFileSync(scriptPath, wrappedCode, { mode: 0o755 });\n\n return new Promise((resolve, reject) => {\n const proc = spawn('bash', [scriptPath], {\n env: { ...process.env },\n cwd: tmpDir,\n });\n\n let stdout = '';\n let stderr = '';\n\n proc.stdout.on('data', (data) => {\n stdout += data.toString();\n });\n\n proc.stderr.on('data', (data) => {\n stderr += data.toString();\n });\n\n proc.on('close', (exitCode) => {\n try {\n fs.unlinkSync(scriptPath);\n } catch {}\n\n if (exitCode !== 0) {\n reject(new Error(`Bash script failed: ${stderr || stdout}`));\n return;\n }\n\n // Try to parse as JSON, otherwise return raw output\n try {\n resolve(JSON.parse(stdout.trim()));\n } catch {\n resolve(stdout.trim());\n }\n });\n\n proc.on('error', (error) => {\n try {\n fs.unlinkSync(scriptPath);\n } catch {}\n reject(new Error(`Failed to spawn Bash: ${error.message}`));\n });\n });\n}\n\n// ============================================================================\n// Script Loading\n// ============================================================================\n\n/**\n * Load a script from the local filesystem\n */\nfunction loadLocalScript(moduleName: string): ScriptDefinition | null {\n const basePath = path.resolve(__dirname, '../../nodes/script', moduleName);\n \n // Try different file extensions\n const extensions = [\n { ext: 'script.ts', language: 'deno' as const },\n { ext: 'script.js', language: 'javascript' as const },\n { ext: 'script.py', language: 'python3' as const },\n { ext: 'script.go', language: 'go' as const },\n { ext: 'script.sh', language: 'bash' as const },\n ];\n\n for (const { ext, language } of extensions) {\n const scriptPath = path.join(basePath, ext);\n if (fs.existsSync(scriptPath)) {\n const content = fs.readFileSync(scriptPath, 'utf-8');\n return {\n type: 'script',\n language,\n content,\n path: scriptPath,\n };\n }\n }\n\n return null;\n}\n\n// ============================================================================\n// Main Execution Function\n// ============================================================================\n\n/**\n * Execute a Script module\n */\nexport async function executeScriptModule(\n params: ScriptExecutionParams\n): Promise<ScriptExecutionResult>;\nexport async function executeScriptModule(\n moduleName: string,\n params: Record<string, any>\n): Promise<ScriptExecutionResult>;\nexport async function executeScriptModule(\n paramsOrModuleName: ScriptExecutionParams | string,\n maybeParams?: Record<string, any>\n): Promise<ScriptExecutionResult> {\n let source: 'local' | 'hub' | 'inline';\n let moduleName: string;\n let executionParams: Record<string, any>;\n let inlineScript: ScriptDefinition | undefined;\n\n if (typeof paramsOrModuleName === 'string') {\n source = 'local';\n moduleName = paramsOrModuleName;\n executionParams = maybeParams || {};\n } else {\n source = paramsOrModuleName.source;\n moduleName = paramsOrModuleName.moduleName;\n executionParams = paramsOrModuleName.params;\n inlineScript = paramsOrModuleName.script;\n }\n\n logger.log(`\\n\uD83C\uDF00 Executing Script module: ${moduleName}`);\n logger.log(` Source: ${source}`);\n\n // Load the script\n let script: ScriptDefinition | null = null;\n\n if (source === 'inline' && inlineScript) {\n script = inlineScript;\n } else if (source === 'local') {\n script = loadLocalScript(moduleName);\n } else if (source === 'hub') {\n // TODO: Implement Script Hub integration\n throw new Error('Script Hub source not yet implemented');\n }\n\n if (!script || !script.content) {\n throw new Error(`Could not load script: ${moduleName}`);\n }\n\n logger.log(` Language: ${script.language}`);\n\n // Create execution context\n const context: ScriptContext = {\n flow_input: executionParams,\n previous_result: executionParams.previous_result || null,\n result: null,\n };\n\n // Execute based on language\n let result: any;\n\n try {\n switch (script.language) {\n case 'deno':\n case 'typescript':\n case 'javascript':\n result = await executeJavaScript(script.content, executionParams, context);\n break;\n\n case 'python3':\n result = await executePython(script.content, executionParams, context);\n break;\n\n case 'go':\n result = await executeGo(script.content, executionParams, context);\n break;\n\n case 'bash':\n result = await executeBash(script.content, executionParams, context);\n break;\n\n default:\n throw new Error(`Unsupported language: ${script.language}`);\n }\n\n logger.log(`\u2705 Script executed successfully`);\n\n return {\n success: true,\n module: moduleName,\n result,\n executedAt: new Date().toISOString(),\n language: script.language,\n data: {\n message: `Successfully executed script: ${moduleName}`,\n status: 'completed',\n output: result,\n },\n };\n } catch (error: any) {\n logger.error(`\u274C Script failed: ${error.message}`);\n\n return {\n success: false,\n module: moduleName,\n result: null,\n executedAt: new Date().toISOString(),\n language: script.language,\n data: {\n message: `Failed to execute script: ${moduleName}`,\n status: 'failed',\n output: null,\n error: error.message,\n },\n };\n }\n}\n\n/**\n * Execute a raw script (inline content)\n */\nexport async function executeScript(\n content: string,\n language: ScriptDefinition['language'],\n params: Record<string, any>,\n options?: { previous_result?: any }\n): Promise<any> {\n const result = await executeScriptModule({\n source: 'inline',\n framework: 'script',\n moduleName: 'inline-script',\n params: {\n ...params,\n previous_result: options?.previous_result,\n },\n script: {\n type: 'script',\n language,\n content,\n },\n });\n\n if (!result.success) {\n throw new Error(result.data.error || 'Script execution failed');\n }\n\n return result.result;\n}\n\n// ============================================================================\n// Exports\n// ============================================================================\n\nexport {\n loadLocalScript,\n getInternalState,\n setInternalState,\n};\n", "/**\n * Security Scanning Module (DLP, PII, Moderation)\n * \n * Provides input scanning capabilities for security concerns.\n * Uses @codenteam/intersect package from private registry.\n */\n\nimport type { ILogger } from '@ha-bits/core/logger';\n\n// ============================================================================\n// Types\n// ============================================================================\n\n/**\n * Security scan configuration from environment variables\n */\nexport interface SecurityScanConfig {\n dlpEnabled: boolean;\n dlpIcapUrl: string | null;\n dlpIcapTimeout: number;\n piiMode: 'log' | 'eradicate' | 'replace' | null;\n moderationEnabled: boolean;\n}\n\n// ============================================================================\n// Configuration\n// ============================================================================\n\n/**\n * Get security configuration from environment variables\n * \n * Environment variables:\n * - HABITS_DLP_ENABLED: Set to 'true' to enable DLP scanning\n * - HABITS_DLP_ICAP_URL: ICAP server URL for enterprise DLP (e.g., icap://server:1344/scan)\n * - HABITS_DLP_ICAP_TIMEOUT: ICAP request timeout in ms (default: 5000)\n * - HABITS_PII_PROTECTION: Set to 'log', 'eradicate', or 'replace'\n * - HABITS_MODERATION_ENABLED: Set to 'true' to enable content moderation\n */\nexport function getSecurityConfig(): SecurityScanConfig {\n const dlpEnabled = process.env.HABITS_DLP_ENABLED === 'true';\n const dlpIcapUrl = process.env.HABITS_DLP_ICAP_URL || null;\n const dlpIcapTimeout = parseInt(process.env.HABITS_DLP_ICAP_TIMEOUT || '5000', 10);\n const piiValue = process.env.HABITS_PII_PROTECTION;\n const piiMode = (piiValue === 'log' || piiValue === 'eradicate' || piiValue === 'replace') ? piiValue : null;\n const moderationEnabled = process.env.HABITS_MODERATION_ENABLED === 'true';\n \n return { dlpEnabled, dlpIcapUrl, dlpIcapTimeout, piiMode, moderationEnabled };\n}\n\n// ============================================================================\n// Scanning Functions\n// ============================================================================\n\n/**\n * Scan input data for security concerns (DLP, PII, Moderation)\n * Called on habits.input.* data and trigger output data\n * \n * @param data - The input data to scan (string, object, or array)\n * @param config - Security configuration from getSecurityConfig()\n * @param logger - Logger instance for output\n * @returns Processed data (potentially redacted/modified based on config)\n */\nexport async function scanInputForSecurity(\n data: any,\n config: SecurityScanConfig,\n logger: ILogger\n): Promise<any> {\n let processedData = data;\n \n // Skip if no security features enabled\n if (!config.dlpEnabled && !config.piiMode && !config.moderationEnabled) {\n return processedData;\n }\n \n try {\n // Import @codenteam/intersect from private registry\n // This package is hosted on a private npm registry and provides DLP, PII, and moderation capabilities\n // @ts-ignore - Package is from private registry, not available at compile time\n const intersect = await import('@codenteam/intersect');\n \n // DLP Scanning\n if (config.dlpEnabled) {\n logger.log('\uD83D\uDD10 [Security] Running DLP scan on input data...');\n try {\n const dlpOptions: { icapUrl?: string; timeout?: number } = {};\n if (config.dlpIcapUrl) {\n dlpOptions.icapUrl = config.dlpIcapUrl;\n dlpOptions.timeout = config.dlpIcapTimeout;\n logger.log(`\uD83D\uDD10 [DLP] Using ICAP server: ${config.dlpIcapUrl}`);\n }\n const dlpResult = await intersect.dlp.consume(processedData, dlpOptions);\n processedData = dlpResult.data ?? processedData;\n if (dlpResult.findings && dlpResult.findings.length > 0) {\n logger.log(`\uD83D\uDD10 [DLP] Found ${dlpResult.findings.length} sensitive data instance(s)`);\n }\n } catch (dlpError: any) {\n logger.warn(`\u26A0\uFE0F [DLP] Scan failed: ${dlpError.message}`);\n }\n }\n \n // PII Protection\n if (config.piiMode) {\n logger.log(`\uD83D\uDD10 [Security] Running PII scan (mode: ${config.piiMode}) on input data...`);\n try {\n const piiResult = await intersect.pii.consume(processedData, { mode: config.piiMode });\n processedData = piiResult.data ?? processedData;\n if (piiResult.detections && piiResult.detections.length > 0) {\n logger.log(`\uD83D\uDD10 [PII] Found ${piiResult.detections.length} PII instance(s) - mode: ${config.piiMode}`);\n }\n } catch (piiError: any) {\n logger.warn(`\u26A0\uFE0F [PII] Scan failed: ${piiError.message}`);\n }\n }\n \n // Content Moderation\n if (config.moderationEnabled) {\n logger.log('\uD83D\uDD10 [Security] Running moderation scan on input data...');\n try {\n const modResult = await intersect.moderation.consume(processedData);\n if (modResult.flagged) {\n logger.warn(`\u26A0\uFE0F [Moderation] Content flagged: ${JSON.stringify(modResult.categories)}`);\n }\n processedData = modResult.data ?? processedData;\n } catch (modError: any) {\n logger.warn(`\u26A0\uFE0F [Moderation] Scan failed: ${modError.message}`);\n }\n }\n } catch (importError: any) {\n // Package not available - log and continue without security scanning\n logger.warn(`\u26A0\uFE0F [Security] @codenteam/intersect package not available: ${importError.message}`);\n logger.warn(' Security features (DLP, PII, Moderation) are disabled.');\n }\n \n return processedData;\n}\n", "/**\n * @ha-bits/cortex ESM Entry Point\n * \n * This module provides a framework-agnostic API for executing habits (workflows)\n * that works in both browser and Node.js environments.\n * \n * Usage:\n * ```typescript\n * import { HabitsExecutor } from '@ha-bits/cortex/esm';\n * \n * const executor = new HabitsExecutor(config, workflows, env);\n * const result = await executor.startWorkflow('my-workflow', { input: 'data' });\n * ```\n * \n * Note: Webhook triggers are NOT supported in this ESM module.\n * For webhook support, use the full server-based exports from '@ha-bits/cortex'.\n */\n\nimport {\n Workflow,\n WorkflowExecution,\n WorkflowConfig,\n LoadedWorkflow,\n StreamCallback,\n} from '@habits/shared/types';\nimport { WorkflowExecutor, InitFromDataOptions } from './WorkflowExecutor';\n\n/**\n * Options for starting a workflow execution.\n */\nexport interface StartWorkflowOptions {\n /** Initial context data (e.g., { habits: { input: {...} } }) */\n initialContext?: Record<string, any>;\n /** Callback for streaming execution events */\n onStream?: StreamCallback;\n /** Pre-populated trigger node outputs */\n triggerData?: Record<string, any>;\n /** Start execution from a specific node */\n startFromNode?: string;\n}\n\n/**\n * HabitsExecutor - Browser/ESM-compatible workflow executor.\n * \n * This class wraps the core WorkflowExecutor and provides a clean OOP API\n * for executing workflows without any Node.js or Express dependencies.\n * \n * Features:\n * - Works in browsers, Deno, Bun, and Node.js\n * - No file system access (all data passed in-memory)\n * - No webhook trigger support (throws error if webhook triggers detected)\n * - Streaming support via callbacks\n * \n * @example\n * ```typescript\n * // Initialize\n * const config: WorkflowConfig = { version: '1.0', workflows: [...] };\n * const workflows = new Map([['my-workflow', workflowDef]]);\n * const env = { OPENAI_API_KEY: 'sk-...' };\n * \n * const executor = new HabitsExecutor(config, workflows, env);\n * \n * // Execute a workflow\n * const result = await executor.startWorkflow('my-workflow', {\n * initialContext: {\n * habits: {\n * input: { prompt: 'Hello world' }\n * }\n * }\n * });\n * \n * console.log(result.output);\n * ```\n */\nexport class HabitsExecutor {\n private executor: WorkflowExecutor;\n private initialized: boolean = false;\n private initPromise: Promise<void> | null = null;\n\n /**\n * Create a new HabitsExecutor instance.\n * \n * @param config - The workflow configuration (describes which workflows are available)\n * @param workflows - Map or Record of workflow ID to workflow definition\n * @param env - Environment variables to pass to workflows (e.g., API keys)\n */\n constructor(\n private config: WorkflowConfig,\n private workflows: Map<string, Workflow> | Record<string, Workflow>,\n private env?: Record<string, string>\n ) {\n this.executor = new WorkflowExecutor();\n // Start initialization immediately\n this.initPromise = this.initialize();\n }\n\n /**\n * Initialize the executor. This is called automatically in the constructor,\n * but can be awaited explicitly if needed.\n */\n private async initialize(): Promise<void> {\n if (this.initialized) return;\n \n await this.executor.initFromData({\n config: this.config,\n workflows: this.workflows,\n env: this.env,\n });\n \n this.initialized = true;\n }\n\n /**\n * Ensure the executor is initialized before operations.\n */\n private async ensureInitialized(): Promise<void> {\n if (this.initPromise) {\n await this.initPromise;\n }\n }\n\n /**\n * Execute a workflow by ID.\n * \n * @param workflowId - The ID of the workflow to execute\n * @param options - Execution options\n * @returns The workflow execution result\n * \n * @throws If the workflow is not found\n * @throws If the workflow contains webhook triggers (not supported in ESM mode)\n * \n * @example\n * ```typescript\n * const result = await executor.startWorkflow('analyze-text', {\n * initialContext: {\n * habits: {\n * input: { text: 'Hello world' }\n * }\n * },\n * onStream: (event) => {\n * console.log('Event:', event.type, event.nodeId);\n * }\n * });\n * ```\n */\n async startWorkflow(\n workflowId: string,\n options?: StartWorkflowOptions\n ): Promise<WorkflowExecution> {\n await this.ensureInitialized();\n \n const loadedWorkflow = this.executor.getWorkflow(workflowId);\n if (!loadedWorkflow) {\n throw new Error(`Workflow not found: ${workflowId}`);\n }\n\n // Execute with no webhook handler - will throw if webhooks are needed\n return this.executor.executeWorkflow(loadedWorkflow.workflow, {\n // No webhookHandler - will throw a clear error if webhook triggers exist\n initialContext: options?.initialContext,\n onStream: options?.onStream,\n triggerData: options?.triggerData,\n startFromNode: options?.startFromNode,\n });\n }\n\n /**\n * Execute a workflow object directly (without loading from config).\n * \n * @param workflow - The workflow definition to execute\n * @param options - Execution options\n * @returns The workflow execution result\n * \n * @example\n * ```typescript\n * const workflow: Workflow = { id: 'inline', name: 'Inline', nodes: [...], edges: [...] };\n * const result = await executor.executeWorkflow(workflow, {\n * initialContext: { habits: { input: { data: 'test' } } }\n * });\n * ```\n */\n async executeWorkflow(\n workflow: Workflow,\n options?: StartWorkflowOptions\n ): Promise<WorkflowExecution> {\n await this.ensureInitialized();\n \n return this.executor.executeWorkflow(workflow, {\n initialContext: options?.initialContext,\n onStream: options?.onStream,\n triggerData: options?.triggerData,\n startFromNode: options?.startFromNode,\n });\n }\n\n /**\n * Get a workflow definition by ID.\n * \n * @param workflowId - The ID of the workflow\n * @returns The loaded workflow or undefined if not found\n */\n async getWorkflow(workflowId: string): Promise<LoadedWorkflow | undefined> {\n await this.ensureInitialized();\n return this.executor.getWorkflow(workflowId);\n }\n\n /**\n * Get all loaded workflows.\n * \n * @returns Array of all loaded workflows\n */\n async getAllWorkflows(): Promise<LoadedWorkflow[]> {\n await this.ensureInitialized();\n return this.executor.getAllWorkflows();\n }\n\n /**\n * Get an execution by ID.\n * \n * @param executionId - The execution ID\n * @returns The execution or undefined if not found\n */\n async getExecution(executionId: string): Promise<WorkflowExecution | undefined> {\n await this.ensureInitialized();\n return this.executor.getExecution(executionId);\n }\n\n /**\n * List all executions.\n * \n * @returns Array of all executions\n */\n async listExecutions(): Promise<WorkflowExecution[]> {\n await this.ensureInitialized();\n return this.executor.listExecutions();\n }\n\n /**\n * Cancel a running execution.\n * \n * @param executionId - The execution ID to cancel\n * @returns True if cancelled, false if not found or not running\n */\n async cancelExecution(executionId: string): Promise<boolean> {\n await this.ensureInitialized();\n return this.executor.cancelExecution(executionId);\n }\n\n /**\n * Get the current configuration.\n * \n * @returns The workflow configuration\n */\n async getConfig(): Promise<WorkflowConfig | null> {\n await this.ensureInitialized();\n return this.executor.getConfig();\n }\n}\n\n// Re-export types for convenience\nexport type {\n Workflow,\n WorkflowExecution,\n WorkflowConfig,\n LoadedWorkflow,\n StreamCallback,\n InitFromDataOptions,\n};\n", "export function assertNotNullOrUndefined<T>(\n value: T | null | undefined,\n fieldName: string,\n): asserts value is T {\n if (value === null || value === undefined) {\n throw new Error(`${fieldName} is null or undefined`)\n }\n}\n\nexport { getNodesBasePath, getNodesPath, getModuleFullPath, getLocalModulePath, clearNodesBasePathCache } from './utils';", "/**\n * Bits Framework\n * \n * This module provides framework utilities for creating bits modules,\n * \n * Modules can import from '@ha-bits/cortex' to access these utilities.\n */\n\nimport { fetch } from '@ha-bits/bindings';\nimport { ILogger } from '@ha-bits/core/logger';\n// ============================================================================\n// HTTP Client Types and Implementation\n// ============================================================================\n\n/**\n * Authentication types for HTTP requests\n */\nexport enum AuthenticationType {\n BEARER_TOKEN = 'BEARER_TOKEN',\n BASIC = 'BASIC',\n API_KEY = 'API_KEY',\n CUSTOM = 'CUSTOM',\n NONE = 'NONE',\n}\n\n/**\n * HTTP Methods\n */\nexport enum HttpMethod {\n GET = 'GET',\n POST = 'POST',\n PUT = 'PUT',\n DELETE = 'DELETE',\n PATCH = 'PATCH',\n HEAD = 'HEAD',\n OPTIONS = 'OPTIONS',\n}\n\n/**\n * HTTP request configuration\n */\nexport interface HttpRequest {\n url: string;\n method: HttpMethod;\n headers?: Record<string, string>;\n body?: any;\n queryParams?: Record<string, string>;\n timeout?: number;\n authentication?: {\n type: AuthenticationType;\n token?: string;\n username?: string;\n password?: string;\n apiKey?: string;\n headerName?: string;\n };\n}\n\n/**\n * HTTP response\n */\nexport interface HttpResponse<T = any> {\n status: number;\n headers: Record<string, string>;\n body: T;\n}\n\n/**\n * HTTP client for making requests\n */\nexport const httpClient = {\n async sendRequest<T = any>(request: HttpRequest): Promise<HttpResponse<T>> {\n const headers: Record<string, string> = { ...request.headers };\n\n // Handle authentication\n if (request.authentication) {\n switch (request.authentication.type) {\n case AuthenticationType.BEARER_TOKEN:\n headers['Authorization'] = `Bearer ${request.authentication.token}`;\n break;\n case AuthenticationType.BASIC:\n const credentials = Buffer.from(\n `${request.authentication.username || ''}:${request.authentication.password || ''}`\n ).toString('base64');\n headers['Authorization'] = `Basic ${credentials}`;\n break;\n case AuthenticationType.API_KEY:\n const headerName = request.authentication.headerName || 'X-API-Key';\n headers[headerName] = request.authentication.apiKey || '';\n break;\n }\n }\n\n // Build URL with query params\n let url = request.url;\n if (request.queryParams && Object.keys(request.queryParams).length > 0) {\n const params = new URLSearchParams(request.queryParams);\n url += (url.includes('?') ? '&' : '?') + params.toString();\n }\n\n const response = await fetch(url, {\n method: request.method,\n headers,\n body: request.body ? JSON.stringify(request.body) : undefined,\n });\n\n // Convert Headers to plain object\n const responseHeaders: Record<string, string> = {};\n response.headers.forEach((value, key) => {\n responseHeaders[key] = value;\n });\n\n return {\n status: response.status,\n headers: responseHeaders,\n body: await response.json() as T,\n };\n },\n};\n\n// ============================================================================\n// Property Types and Builders\n// ============================================================================\n\n/**\n * Store scope for persistent storage\n */\nexport enum StoreScope {\n PROJECT = 'PROJECT',\n FLOW = 'FLOW',\n}\n\n/**\n * Property value types\n */\nexport type PropertyType = \n | 'SHORT_TEXT'\n | 'LONG_TEXT'\n | 'NUMBER'\n | 'CHECKBOX'\n | 'DROPDOWN'\n | 'STATIC_DROPDOWN'\n | 'MULTI_SELECT_DROPDOWN'\n | 'JSON'\n | 'OBJECT'\n | 'ARRAY'\n | 'FILE'\n | 'DATE_TIME'\n | 'MARKDOWN'\n | 'CUSTOM_AUTH'\n | 'SECRET_TEXT';\n\n/**\n * Base property definition\n */\nexport interface PropertyDefinition<T = any> {\n type: PropertyType;\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: T;\n}\n\n/**\n * Dropdown option\n */\nexport interface DropdownOption<T = any> {\n label: string;\n value: T;\n}\n\n/**\n * Dropdown state (for dynamic dropdowns)\n */\nexport interface DropdownState<T = any> {\n disabled: boolean;\n placeholder?: string;\n options: DropdownOption<T>[];\n}\n\n/**\n * Dynamic dropdown property\n */\nexport interface DynamicDropdownProperty<T = any> extends PropertyDefinition<T> {\n type: 'DROPDOWN';\n refreshers: string[];\n options: (context: { auth?: any; propsValue?: Record<string, any> }) => Promise<DropdownState<T>>;\n}\n\n/**\n * Static dropdown property\n */\nexport interface StaticDropdownProperty<T = any> extends PropertyDefinition<T> {\n type: 'STATIC_DROPDOWN';\n options: {\n disabled?: boolean;\n options: DropdownOption<T>[];\n };\n}\n\n/**\n * Array property for defining arrays with sub-properties\n */\nexport interface ArrayProperty<T = any> extends PropertyDefinition<T[]> {\n type: 'ARRAY';\n properties: Record<string, PropertyDefinition>;\n}\n\n/**\n * File property value\n */\nexport interface FilePropertyValue {\n filename: string;\n data: Buffer;\n extension?: string;\n}\n\n/**\n * Short text property config\n */\ninterface ShortTextConfig {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: string;\n}\n\n/**\n * Long text property config\n */\ninterface LongTextConfig {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: string;\n}\n\n/**\n * Number property config\n */\ninterface NumberConfig {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: number;\n}\n\n/**\n * Checkbox property config\n */\ninterface CheckboxConfig {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: boolean;\n}\n\n/**\n * Dropdown property config\n */\ninterface DropdownConfig<T = any> {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: T;\n refreshers: string[];\n auth?: any;\n options: (context: { auth?: any; propsValue?: Record<string, any> }) => Promise<DropdownState<T>>;\n}\n\n/**\n * Static dropdown property config\n */\ninterface StaticDropdownConfig<T = any> {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: T;\n options: {\n disabled?: boolean;\n options: DropdownOption<T>[];\n };\n}\n\n/**\n * JSON property config\n */\ninterface JsonConfig {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: any;\n}\n\n/**\n * Object property config\n */\ninterface ObjectConfig<T = any> {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: T;\n properties?: Record<string, PropertyDefinition>;\n}\n\n/**\n * Array property config\n */\ninterface ArrayConfig {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: any[];\n properties: Record<string, PropertyDefinition>;\n}\n\n/**\n * File property config\n */\ninterface FileConfig {\n displayName: string;\n description?: string;\n required: boolean;\n}\n\n/**\n * Property builder - creates property definitions\n */\nexport const Property = {\n ShortText(config: ShortTextConfig): PropertyDefinition<string> {\n return {\n type: 'SHORT_TEXT',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n LongText(config: LongTextConfig): PropertyDefinition<string> {\n return {\n type: 'LONG_TEXT',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n Number(config: NumberConfig): PropertyDefinition<number> {\n return {\n type: 'NUMBER',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n Checkbox(config: CheckboxConfig): PropertyDefinition<boolean> {\n return {\n type: 'CHECKBOX',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n Dropdown<T = any>(config: DropdownConfig<T>): DynamicDropdownProperty<T> {\n return {\n type: 'DROPDOWN',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n refreshers: config.refreshers,\n options: config.options,\n };\n },\n\n StaticDropdown<T = any>(config: StaticDropdownConfig<T>): StaticDropdownProperty<T> {\n return {\n type: 'STATIC_DROPDOWN',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n options: config.options,\n };\n },\n\n Json(config: JsonConfig): PropertyDefinition<any> {\n return {\n type: 'JSON',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n Object<T = any>(config: ObjectConfig<T>): PropertyDefinition<T> {\n return {\n type: 'OBJECT',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n Array(config: ArrayConfig): ArrayProperty {\n return {\n type: 'ARRAY',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n properties: config.properties,\n };\n },\n\n File(config: FileConfig): PropertyDefinition<FilePropertyValue> {\n return {\n type: 'FILE',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n };\n },\n\n DateTime(config: { displayName: string; description?: string; required: boolean; defaultValue?: string }): PropertyDefinition<string> {\n return {\n type: 'DATE_TIME',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n Markdown(config: { displayName: string; description?: string; value: string }): PropertyDefinition<string> {\n return {\n type: 'MARKDOWN',\n displayName: config.displayName,\n description: config.description,\n required: false,\n defaultValue: config.value,\n };\n },\n};\n\n// ============================================================================\n// Auth Definitions\n// ============================================================================\n\n/**\n * Custom auth validation result\n */\nexport interface AuthValidationResult {\n valid: boolean;\n error?: string;\n}\n\n/**\n * Custom auth configuration\n */\ninterface CustomAuthConfig<T = any> {\n description?: string;\n required: boolean;\n props: Record<string, PropertyDefinition>;\n validate?: (context: { auth: T }) => Promise<AuthValidationResult>;\n}\n\n/**\n * Secret text configuration\n */\ninterface SecretTextConfig {\n displayName: string;\n description?: string;\n required: boolean;\n}\n\n/**\n * Authentication property builders\n */\nexport const BitAuth = {\n CustomAuth<T = any>(config: CustomAuthConfig<T>): PropertyDefinition & { props: Record<string, PropertyDefinition>; validate?: (context: { auth: T }) => Promise<AuthValidationResult> } {\n return {\n type: 'CUSTOM_AUTH',\n displayName: 'Authentication',\n description: config.description,\n required: config.required,\n props: config.props,\n validate: config.validate,\n };\n },\n\n SecretText(config: SecretTextConfig): PropertyDefinition<string> {\n return {\n type: 'SECRET_TEXT',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n };\n },\n\n None(): PropertyDefinition<void> {\n return {\n type: 'CUSTOM_AUTH',\n displayName: 'None',\n required: false,\n };\n },\n\n OAuth2(config: {\n displayName: string;\n description?: string;\n required: boolean;\n authorizationUrl: string;\n tokenUrl: string;\n clientId?: string;\n clientSecret?: string;\n scopes: string[];\n pkce?: boolean;\n extraAuthParams?: Record<string, string>;\n }): PropertyDefinition<{ accessToken: string; refreshToken?: string; tokenType: string; expiresAt?: number }> {\n return {\n type: 'OAUTH2',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n authorizationUrl: config.authorizationUrl,\n tokenUrl: config.tokenUrl,\n clientId: config.clientId,\n clientSecret: config.clientSecret,\n scopes: config.scopes,\n pkce: config.pkce ?? true, // PKCE enabled by default\n extraAuthParams: config.extraAuthParams,\n } as any;\n },\n\n /** @deprecated Use OAuth2() instead */\n OAuth2PKCE(config: {\n displayName: string;\n description?: string;\n required: boolean;\n authorizationUrl: string;\n tokenUrl: string;\n clientId?: string;\n clientSecret?: string;\n scopes: string[];\n extraAuthParams?: Record<string, string>;\n }): PropertyDefinition<{ accessToken: string; refreshToken?: string; tokenType: string; expiresAt?: number }> {\n return BitAuth.OAuth2({ ...config, pkce: true });\n },\n\n BasicAuth(config: any): PropertyDefinition<{ username: string; password: string }> {\n return {\n type: 'CUSTOM_AUTH',\n displayName: 'Basic Authentication',\n description: config.description,\n required: config.required,\n ...config,\n };\n },\n};\n\nexport const PieceAuth = BitAuth; // Alias for compatibility with AP if needed\n\n// ============================================================================\n// Action Builder\n// ============================================================================\n\n/**\n * Action context passed to run function\n */\nexport interface BitActionContext<AuthType = any, PropsType = any> {\n auth: AuthType;\n propsValue: PropsType;\n store: {\n get: <T>(key: string, scope?: StoreScope) => Promise<T | null>;\n put: <T>(key: string, value: T, scope?: StoreScope) => Promise<void>;\n delete: (key: string, scope?: StoreScope) => Promise<void>;\n };\n files: {\n write: (params: { fileName: string; data: Buffer }) => Promise<string>;\n };\n server: {\n publicUrl: string;\n apiUrl: string;\n };\n /** Logger instance for structured logging within the bit */\n logger?: ILogger;\n}\n\n/**\n * Action definition\n */\nexport interface BitAction<AuthType = any, PropsType = Record<string, any>> {\n name: string;\n displayName: string;\n description: string;\n auth?: PropertyDefinition;\n props: Record<string, PropertyDefinition>;\n run: (context: BitActionContext<AuthType, PropsType>) => Promise<any>;\n}\n\n/**\n * Action configuration for createAction\n */\ninterface ActionConfig<AuthType = any, PropsType = Record<string, any>> {\n name: string;\n displayName: string;\n description: string;\n auth?: PropertyDefinition;\n props: Record<string, PropertyDefinition>;\n run: (context: BitActionContext<AuthType, PropsType>) => Promise<any>;\n}\n\n/**\n * Create a bit action\n */\nexport function createAction<AuthType = any, PropsType = Record<string, any>>(\n config: ActionConfig<AuthType, PropsType>\n): BitAction<AuthType, PropsType> {\n return {\n name: config.name,\n displayName: config.displayName,\n description: config.description,\n auth: config.auth,\n props: config.props,\n run: config.run,\n };\n}\n\n// Alias for compatibility\nexport const createBitAction = createAction;\n\n// ============================================================================\n// Trigger Builder\n// ============================================================================\n\n/**\n * Trigger types\n */\nexport enum TriggerStrategy {\n POLLING = 'POLLING',\n WEBHOOK = 'WEBHOOK',\n APP_WEBHOOK = 'APP_WEBHOOK',\n}\n\n/**\n * Webhook filter payload - passed to trigger.filter() to determine if trigger should handle the event\n */\nexport interface WebhookFilterPayload {\n /** Raw request body */\n body: any;\n /** HTTP headers */\n headers: Record<string, string>;\n /** Query string parameters */\n query: Record<string, string>;\n /** HTTP method */\n method: string;\n}\n\n/**\n * Trigger context\n */\nexport interface BitTriggerContext<AuthType = any, PropsType = any> {\n auth: AuthType;\n propsValue: PropsType;\n payload: unknown;\n webhookUrl?: string;\n store: {\n get: <T>(key: string, scope?: StoreScope) => Promise<T | null>;\n put: <T>(key: string, value: T, scope?: StoreScope) => Promise<void>;\n delete: (key: string, scope?: StoreScope) => Promise<void>;\n };\n app: {\n createListeners: (listener: { events: string[]; identifierValue: string; identifierKey: string }) => void;\n };\n setSchedule: (options: { cronExpression: string; timezone?: string }) => void;\n /** Webhook payload data (for webhook triggers) */\n webhookPayload?: WebhookFilterPayload;\n}\n\n/**\n * Trigger definition\n */\nexport interface BitTrigger<AuthType = any, PropsType = Record<string, any>> {\n name: string;\n displayName: string;\n description: string;\n type: TriggerStrategy;\n auth?: PropertyDefinition;\n props: Record<string, PropertyDefinition>;\n onEnable?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<void>;\n onDisable?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<void>;\n run?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<any[]>;\n test?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<any[]>;\n onHandshake?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<any>;\n /**\n * Filter function for webhook triggers.\n * Called when a webhook is received for this bit's module.\n * Return true if this trigger should handle the event, false to skip.\n * If not defined, the trigger accepts all webhook events.\n */\n filter?: (payload: WebhookFilterPayload) => boolean | Promise<boolean>;\n sampleData?: any;\n}\n\n/**\n * Trigger configuration\n */\ninterface TriggerConfig<AuthType = any, PropsType = Record<string, any>> {\n name: string;\n displayName: string;\n description: string;\n type: TriggerStrategy;\n auth?: PropertyDefinition;\n props: Record<string, PropertyDefinition>;\n onEnable?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<void>;\n onDisable?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<void>;\n run?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<any[]>;\n test?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<any[]>;\n onHandshake?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<any>;\n filter?: (payload: WebhookFilterPayload) => boolean | Promise<boolean>;\n sampleData?: any;\n}\n\n/**\n * Create a bit trigger\n */\nexport function createTrigger<AuthType = any, PropsType = Record<string, any>>(\n config: TriggerConfig<AuthType, PropsType>\n): BitTrigger<AuthType, PropsType> {\n return {\n name: config.name,\n displayName: config.displayName,\n description: config.description,\n type: config.type,\n auth: config.auth,\n props: config.props,\n onEnable: config.onEnable,\n onDisable: config.onDisable,\n run: config.run,\n test: config.test,\n onHandshake: config.onHandshake,\n filter: config.filter,\n sampleData: config.sampleData,\n };\n}\n\n// Alias for compatibility\nexport const createBitTrigger = createTrigger;\n\n// ============================================================================\n// Piece/Bit Builder\n// ============================================================================\n\n/**\n * Piece/Bit categories\n */\nexport enum BitCategory {\n ARTIFICIAL_INTELLIGENCE = 'ARTIFICIAL_INTELLIGENCE',\n COMMUNICATION = 'COMMUNICATION',\n CORE = 'CORE',\n CONTENT_AND_FILES = 'CONTENT_AND_FILES',\n DEVELOPER_TOOLS = 'DEVELOPER_TOOLS',\n BUSINESS_INTELLIGENCE = 'BUSINESS_INTELLIGENCE',\n ACCOUNTING = 'ACCOUNTING',\n SALES_AND_CRM = 'SALES_AND_CRM',\n PRODUCTIVITY = 'PRODUCTIVITY',\n MARKETING = 'MARKETING',\n CUSTOMER_SUPPORT = 'CUSTOMER_SUPPORT',\n PREMIUM = 'PREMIUM',\n}\n\nexport enum PieceCategory {\n ARTIFICIAL_INTELLIGENCE = 'ARTIFICIAL_INTELLIGENCE',\n COMMUNICATION = 'COMMUNICATION',\n CORE = 'CORE',\n CONTENT_AND_FILES = 'CONTENT_AND_FILES',\n DEVELOPER_TOOLS = 'DEVELOPER_TOOLS',\n BUSINESS_INTELLIGENCE = 'BUSINESS_INTELLIGENCE',\n ACCOUNTING = 'ACCOUNTING',\n SALES_AND_CRM = 'SALES_AND_CRM',\n PRODUCTIVITY = 'PRODUCTIVITY',\n MARKETING = 'MARKETING',\n CUSTOMER_SUPPORT = 'CUSTOMER_SUPPORT',\n PREMIUM = 'PREMIUM',\n}\n\n/**\n * Bit/Piece definition\n */\nexport interface Bit<AuthType = any> {\n /**\n * Unique identifier for this bit module.\n * Used for webhook routing: /webhook/:id\n * Example: 'gohighlevel', 'hubspot', 'salesforce'\n */\n id?: string;\n displayName: string;\n description?: string;\n logoUrl: string;\n minimumSupportedRelease?: string;\n maximumSupportedRelease?: string;\n categories?: BitCategory[];\n auth?: PropertyDefinition;\n actions: Record<string, BitAction<AuthType>>;\n triggers: Record<string, BitTrigger<AuthType>>;\n authors?: string[];\n}\n\n/**\n * Bit configuration for createBit/createPiece\n */\ninterface BitConfig<AuthType = any> {\n id?: string;\n displayName: string;\n description?: string;\n logoUrl: string;\n minimumSupportedRelease?: string;\n maximumSupportedRelease?: string;\n categories?: BitCategory[];\n auth?: PropertyDefinition;\n actions: BitAction<AuthType>[];\n triggers?: BitTrigger<AuthType>[];\n authors?: string[];\n}\n\n/**\n * Create a bit/piece module\n */\nexport function createBit<AuthType = any>(config: BitConfig<AuthType>): Bit<AuthType> {\n // Convert arrays to records keyed by name\n const actionsRecord: Record<string, BitAction<AuthType>> = {};\n for (const action of config.actions) {\n actionsRecord[action.name] = action;\n }\n\n const triggersRecord: Record<string, BitTrigger<AuthType>> = {};\n if (config.triggers) {\n for (const trigger of config.triggers) {\n triggersRecord[trigger.name] = trigger;\n }\n }\n\n return {\n id: config.id,\n displayName: config.displayName,\n description: config.description,\n logoUrl: config.logoUrl,\n minimumSupportedRelease: config.minimumSupportedRelease,\n maximumSupportedRelease: config.maximumSupportedRelease,\n categories: config.categories,\n auth: config.auth,\n actions: actionsRecord,\n triggers: triggersRecord,\n authors: config.authors,\n };\n}\n\nexport const createPiece = createBit;\n\n// ============================================================================\n// Utility: Custom API Call Action\n// ============================================================================\n\n/**\n * Create a custom API call action \n */\nexport function createCustomApiCallAction(config: {\n baseUrl: (auth: any) => string;\n auth: PropertyDefinition;\n authMapping?: (auth: any) => Promise<{ headers: Record<string, string> }>;\n}): BitAction {\n return createAction({\n name: 'custom_api_call',\n displayName: 'Custom API Call',\n description: 'Make a custom API call to any endpoint',\n auth: config.auth,\n props: {\n method: Property.StaticDropdown({\n displayName: 'Method',\n required: true,\n defaultValue: 'GET',\n options: {\n options: [\n { label: 'GET', value: 'GET' },\n { label: 'POST', value: 'POST' },\n { label: 'PUT', value: 'PUT' },\n { label: 'PATCH', value: 'PATCH' },\n { label: 'DELETE', value: 'DELETE' },\n ],\n },\n }),\n path: Property.ShortText({\n displayName: 'Path',\n description: 'API path (e.g., /users)',\n required: true,\n }),\n headers: Property.Json({\n displayName: 'Headers',\n description: 'Request headers as JSON object',\n required: false,\n defaultValue: {},\n }),\n queryParams: Property.Json({\n displayName: 'Query Parameters',\n description: 'Query parameters as JSON object',\n required: false,\n defaultValue: {},\n }),\n body: Property.Json({\n displayName: 'Body',\n description: 'Request body as JSON (for POST, PUT, PATCH)',\n required: false,\n defaultValue: {},\n }),\n },\n async run({ auth, propsValue }) {\n const baseUrl = config.baseUrl(auth);\n const authHeaders = config.authMapping \n ? await config.authMapping(auth)\n : { headers: {} };\n\n const response = await httpClient.sendRequest({\n url: `${baseUrl}${propsValue.path}`,\n method: propsValue.method as HttpMethod,\n headers: {\n ...authHeaders.headers,\n ...(propsValue.headers || {}),\n },\n queryParams: propsValue.queryParams,\n body: propsValue.body,\n });\n\n return response.body;\n },\n });\n}\n\n// ============================================================================\n// Re-exports for convenience\n// ============================================================================\n\nexport {\n // BitsDoer types (for runtime)\n type BitsAction,\n type BitsActionContext,\n type BitsTrigger,\n type BitsTriggerType,\n type BitsTriggerContext,\n type BitsStore,\n type BitsPiece,\n} from './bitsDoer';\n\n// ============================================================================\n// Declarative Node Types (for creating n8n-style declarative bits)\n// ============================================================================\n\nexport {\n // Core types for declarative nodes\n type IDeclarativeNodeType,\n type DeclarativeNodeDescription,\n type DeclarativeProperty,\n type PropertyOption,\n type DisplayOptions,\n type CredentialDefinition,\n \n // Routing configuration\n type RoutingConfig,\n type RoutingRequest,\n type RoutingSend,\n type RoutingOutput,\n type PostReceiveAction,\n type PreSendAction,\n type RequestDefaults,\n type DeclarativeHttpMethod,\n \n // Execution\n type DeclarativeExecutionContext,\n type DeclarativeExecutionResult,\n type ExpressionContext,\n \n // Functions\n executeDeclarativeNode,\n buildRequest,\n resolveExpression,\n processResponse,\n isDeclarativeNode,\n extractDeclarativeNode,\n declarativeNodeToBitsAction,\n} from './declarativeExecutor';\n", "/**\n * OAuth2 Discovery\n * \n * Scans workflows and bits to discover OAuth2 PKCE authentication requirements.\n * Used at server startup to display authorization URLs to users.\n */\n\nimport { Workflow, WorkflowNode } from '@habits/shared/types';\nimport { OAuth2Status, OAuth2Config } from './oauth2Types';\nimport { oauthTokenStore } from './oauthTokenStore';\nimport { pieceFromModule, extractBitsPieceFromModule } from './bitsDoer';\nimport { getModuleName, getBundledModule, isBundledModule } from '../utils/moduleLoader';\nimport { getModuleMainFile, ModuleDefinition } from '../utils/moduleCloner';\nimport { simpleRequire } from '../utils/customRequire';\nimport { ILogger, LoggerFactory } from '@ha-bits/core/logger';\nimport * as path from '@ha-bits/bindings/path';\n\nconst logger = LoggerFactory.create(undefined, undefined, { bitName: 'OAuthDiscovery' });\n\n/**\n * Resolve {{habits.env.VAR}} expressions in a value to actual env values\n */\nfunction resolveEnvExpression(value: any): any {\n if (typeof value !== 'string') return value;\n \n // Match {{habits.env.VAR_NAME}} pattern\n const envPattern = /\\{\\{habits\\.env\\.([A-Za-z_][A-Za-z0-9_]*)\\}\\}/g;\n return value.replace(envPattern, (match, envVar) => {\n return process.env[envVar] || '';\n });\n}\n\n/**\n * Extract clientId and clientSecret from node's auth configuration\n * Handles both camelCase (clientId) and UPPER_CASE (CLIENT_ID) formats\n */\nfunction extractAuthCredentials(nodeAuth: Record<string, any> | undefined): { clientId?: string; clientSecret?: string } {\n if (!nodeAuth) return {};\n \n // Look for clientId (camelCase or UPPER_CASE)\n let clientId = nodeAuth.clientId || nodeAuth.CLIENT_ID || nodeAuth.client_id;\n let clientSecret = nodeAuth.clientSecret || nodeAuth.CLIENT_SECRET || nodeAuth.client_secret;\n \n // Resolve any env expressions\n if (clientId) clientId = resolveEnvExpression(clientId);\n if (clientSecret) clientSecret = resolveEnvExpression(clientSecret);\n \n return { clientId, clientSecret };\n}\n\n/**\n * OAuth2 requirement for a bit in the workflow\n */\nexport interface OAuthRequirement {\n /** Bit ID (derived from module name) */\n bitId: string;\n /** Module name (e.g., \"@ha-bits/bit-oauth-mock\") */\n moduleName: string;\n /** Display name of the bit */\n displayName: string;\n /** OAuth2 configuration */\n config: OAuth2Config;\n /** Whether a valid token already exists */\n hasValidToken: boolean;\n /** Status: 'needed', 'valid', or 'expired' */\n status: 'needed' | 'valid' | 'expired';\n}\n\n/**\n * Extract bit ID from module name\n * e.g., \"@ha-bits/bit-oauth-mock\" -> \"bit-oauth-mock\"\n */\nfunction extractBitId(moduleName: string): string {\n const parts = moduleName.split('/');\n return parts[parts.length - 1];\n}\n\n/**\n * Get auth definition from a loaded bit module\n */\nasync function getAuthFromModule(moduleDefinition: ModuleDefinition): Promise<{ auth: any; displayName: string } | null> {\n const moduleName = getModuleName(moduleDefinition);\n\n try {\n // Check if module is pre-bundled\n if (isBundledModule(moduleDefinition.repository)) {\n const loadedModule = getBundledModule(moduleDefinition.repository);\n if (loadedModule) {\n const piece = extractBitsPieceFromModule(loadedModule);\n return { auth: piece.auth, displayName: piece.displayName };\n }\n return null;\n }\n\n // For non-bundled modules, use filesystem-based loading\n const mainFilePath = getModuleMainFile(moduleDefinition);\n if (!mainFilePath) {\n return null;\n }\n\n const originalCwd = process.cwd();\n const moduleDir = path.dirname(mainFilePath);\n let nodeModulesDir = moduleDir;\n while (nodeModulesDir && !nodeModulesDir.endsWith('/node_modules') && nodeModulesDir !== path.dirname(nodeModulesDir)) {\n nodeModulesDir = path.dirname(nodeModulesDir);\n }\n\n try {\n process.chdir(moduleDir);\n const loadedModule = simpleRequire(mainFilePath, nodeModulesDir);\n const piece = extractBitsPieceFromModule(loadedModule);\n process.chdir(originalCwd);\n return { auth: piece.auth, displayName: piece.displayName };\n } catch (error) {\n process.chdir(originalCwd);\n throw error;\n }\n } catch (error) {\n logger.warn('Failed to load auth from module', { moduleName, error: String(error) });\n return null;\n }\n}\n\n/**\n * Check if an auth definition is OAuth2\n */\nfunction isOAuth2(auth: any): auth is { type: 'OAUTH2' } & OAuth2Config {\n return auth && (auth.type === 'OAUTH2' || auth.type === 'OAUTH2_PKCE');\n}\n\n/**\n * Discover OAuth2 requirements from workflows\n * @param workflows - Map of workflow ID to workflow definition\n * @returns Array of OAuth requirements\n */\nexport async function discoverOAuthRequirements(\n workflows: Map<string, Workflow>\n): Promise<OAuthRequirement[]> {\n const requirements: OAuthRequirement[] = [];\n const processedModules = new Set<string>();\n\n for (const [workflowId, workflow] of workflows) {\n for (const node of workflow.nodes) {\n const nodeData = node.data;\n \n // Only process bits framework nodes\n if (nodeData?.framework !== 'bits') {\n continue;\n }\n\n const moduleName = nodeData.module;\n if (!moduleName || processedModules.has(moduleName)) {\n continue;\n }\n\n processedModules.add(moduleName);\n\n // Create module definition\n const moduleDefinition: ModuleDefinition = {\n repository: moduleName,\n source: 'npm',\n framework: 'bits',\n };\n\n // Get auth from module\n const moduleAuth = await getAuthFromModule(moduleDefinition);\n if (!moduleAuth || !isOAuth2(moduleAuth.auth)) {\n continue;\n }\n\n const bitId = extractBitId(moduleName);\n const hasValidToken = oauthTokenStore.hasValidToken(bitId);\n const isExpired = oauthTokenStore.isExpired(bitId);\n\n let status: 'needed' | 'valid' | 'expired';\n if (hasValidToken && !isExpired) {\n status = 'valid';\n } else if (hasValidToken && isExpired) {\n status = 'expired';\n } else {\n status = 'needed';\n }\n\n // Extract auth credentials from node's auth config (supports {{habits.env.VAR}} expressions)\n const nodeAuthCredentials = extractAuthCredentials(nodeData.auth);\n \n // Merge: node auth credentials take precedence over bit's static config\n const clientId = nodeAuthCredentials.clientId || moduleAuth.auth.clientId;\n const clientSecret = nodeAuthCredentials.clientSecret || moduleAuth.auth.clientSecret;\n\n requirements.push({\n bitId,\n moduleName,\n displayName: moduleAuth.displayName,\n config: {\n displayName: moduleAuth.auth.displayName,\n description: moduleAuth.auth.description,\n required: moduleAuth.auth.required,\n authorizationUrl: moduleAuth.auth.authorizationUrl,\n tokenUrl: moduleAuth.auth.tokenUrl,\n clientId,\n clientSecret,\n scopes: moduleAuth.auth.scopes,\n extraAuthParams: moduleAuth.auth.extraAuthParams,\n },\n hasValidToken,\n status,\n });\n }\n }\n\n return requirements;\n}\n\n/**\n * Print OAuth requirements to terminal\n * @param requirements - OAuth requirements to print\n * @param getAuthUrl - Function to generate authorization URL for a requirement (can be async)\n */\nexport async function printOAuthRequirements(\n requirements: OAuthRequirement[],\n getAuthUrl: (req: OAuthRequirement) => string | Promise<string>\n): Promise<void> {\n const neededRequirements = requirements.filter(r => r.status !== 'valid');\n\n if (neededRequirements.length === 0) {\n logger.info('All OAuth2 tokens are valid');\n return;\n }\n\n console.log('\\n' + '='.repeat(60));\n console.log('\uD83D\uDD10 OAuth2 Authorization Required');\n console.log('='.repeat(60));\n\n for (const req of neededRequirements) {\n const statusIcon = req.status === 'expired' ? '\u26A0\uFE0F (expired)' : '\u274C (missing)';\n console.log(`\\n\uD83D\uDCE6 ${req.displayName} ${statusIcon}`);\n console.log(` Module: ${req.moduleName}`);\n console.log(` Scopes: ${req.config.scopes.join(', ')}`);\n const authUrl = await getAuthUrl(req);\n console.log(` \u279C Visit: ${authUrl}`);\n }\n\n console.log('\\n' + '='.repeat(60));\n console.log('Open the URLs above in your browser to authorize access.');\n console.log('After authorization, the tokens will be stored automatically.');\n console.log('='.repeat(60) + '\\n');\n}\n", "/**\n * OAuthFlowManager - Platform-Agnostic OAuth2 Flow Manager\n * \n * Handles OAuth2 Authorization Code Flow with optional PKCE for secure authentication.\n * This module is platform-agnostic (works in Node.js, browsers, and Tauri).\n * \n * Features:\n * - PKCE (Proof Key for Code Exchange) support\n * - Builds authorization URLs\n * - Exchanges authorization codes for tokens\n * - Parses callback URLs (both fragment and query params)\n * - Manages pending OAuth flows in memory\n * \n * For server environments, use OAuthCallbackServer which wraps this manager\n * and provides Express routing.\n */\n\nimport { OAuth2Config, OAuth2State, OAuth2TokenSet } from './oauth2Types';\nimport { oauthTokenStore } from './oauthTokenStore';\nimport { ILogger, LoggerFactory } from '@ha-bits/core/logger';\n\n/**\n * Result of parsing an OAuth callback URL\n */\nexport interface OAuthCallbackParams {\n /** Authorization code (if present) */\n code?: string;\n /** State parameter for CSRF protection */\n state?: string;\n /** Access token (implicit flow or hash fragment) */\n accessToken?: string;\n /** Refresh token (if provided) */\n refreshToken?: string;\n /** Token expiration in seconds */\n expiresIn?: number;\n /** Token type */\n tokenType?: string;\n /** Error code if authorization failed */\n error?: string;\n /** Human-readable error description */\n errorDescription?: string;\n}\n\n/**\n * Result of initiating an OAuth flow\n */\nexport interface InitiateFlowResult {\n /** Authorization URL to redirect user to */\n authUrl: string;\n /** State parameter used for CSRF protection */\n state: string;\n /** Redirect URI that will receive the callback */\n redirectUri: string;\n}\n\n/**\n * Result of exchanging an authorization code\n */\nexport interface ExchangeResult {\n /** Bit ID the tokens are for */\n bitId: string;\n /** Token set received from the provider */\n tokens: OAuth2TokenSet;\n}\n\n/**\n * Options for creating an OAuthFlowManager\n */\nexport interface OAuthFlowManagerOptions {\n /**\n * Base callback URL for OAuth redirects.\n * For server mode: \"http://localhost:3000/oauth\"\n * For Tauri mode: \"myapp://oauth\" (custom URL scheme)\n */\n callbackBaseUrl: string;\n /**\n * Custom logger instance (optional)\n */\n logger?: ILogger;\n}\n\n/**\n * Platform-agnostic OAuth2 Flow Manager\n * \n * @example Server mode:\n * ```typescript\n * const manager = new OAuthFlowManager({ callbackBaseUrl: 'http://localhost:3000/oauth' });\n * const { authUrl } = manager.initiateFlow('bit-google-drive', config);\n * // User visits authUrl, server receives callback at /oauth/bit-google-drive/callback\n * const result = await manager.exchangeCode(state, code);\n * ```\n * \n * @example Tauri mode:\n * ```typescript\n * const manager = new OAuthFlowManager({ callbackBaseUrl: 'myapp://oauth' });\n * const { authUrl } = manager.initiateFlow('bit-dropbox', config);\n * // Open authUrl with Tauri opener, listen for deep link callback\n * const params = manager.parseCallbackUrl('myapp://oauth/callback?code=...&state=...');\n * const result = await manager.exchangeCode(params.state!, params.code!);\n * ```\n */\nexport class OAuthFlowManager {\n private pendingFlows: Map<string, OAuth2State> = new Map();\n private logger: ILogger;\n private callbackBaseUrl: string;\n\n constructor(options: OAuthFlowManagerOptions) {\n this.callbackBaseUrl = options.callbackBaseUrl.replace(/\\/$/, ''); // Remove trailing slash\n this.logger = options.logger ?? LoggerFactory.create(undefined, undefined, { bitName: 'OAuthFlowManager' });\n }\n\n /**\n * Generate a cryptographically secure random string for PKCE code verifier.\n * RFC 7636 requires 43-128 characters, URL-safe.\n * \n * Uses Web Crypto API for platform compatibility.\n */\n private generateCodeVerifier(): string {\n // Generate 32 random bytes -> 43 base64url characters\n const randomBytes = new Uint8Array(32);\n if (typeof crypto !== 'undefined' && crypto.getRandomValues) {\n crypto.getRandomValues(randomBytes);\n } else {\n // Fallback for older environments (should not happen in modern Node.js/browsers)\n for (let i = 0; i < 32; i++) {\n randomBytes[i] = Math.floor(Math.random() * 256);\n }\n }\n return this.base64UrlEncode(randomBytes).slice(0, 43);\n }\n\n /**\n * Generate code challenge from verifier using SHA256.\n * RFC 7636 S256 method.\n */\n private async generateCodeChallenge(codeVerifier: string): Promise<string> {\n const encoder = new TextEncoder();\n const data = encoder.encode(codeVerifier);\n \n // Use Web Crypto API for SHA-256\n if (typeof crypto !== 'undefined' && crypto.subtle) {\n const hashBuffer = await crypto.subtle.digest('SHA-256', data);\n return this.base64UrlEncode(new Uint8Array(hashBuffer));\n }\n \n // Fallback: Try Node.js crypto (for older Node.js without Web Crypto)\n try {\n const nodeCrypto = await import('crypto');\n const hash = nodeCrypto.createHash('sha256').update(codeVerifier).digest();\n return this.base64UrlEncode(new Uint8Array(hash));\n } catch {\n throw new Error('No crypto implementation available for PKCE code challenge');\n }\n }\n\n /**\n * Generate a random state parameter for CSRF protection.\n */\n private generateState(): string {\n const randomBytes = new Uint8Array(16);\n if (typeof crypto !== 'undefined' && crypto.getRandomValues) {\n crypto.getRandomValues(randomBytes);\n } else {\n for (let i = 0; i < 16; i++) {\n randomBytes[i] = Math.floor(Math.random() * 256);\n }\n }\n return Array.from(randomBytes).map(b => b.toString(16).padStart(2, '0')).join('');\n }\n\n /**\n * Base64URL encode a Uint8Array (RFC 4648).\n */\n private base64UrlEncode(data: Uint8Array): string {\n // Convert to regular base64 first\n let binary = '';\n for (let i = 0; i < data.length; i++) {\n binary += String.fromCharCode(data[i]);\n }\n const base64 = btoa(binary);\n \n // Convert to base64url\n return base64\n .replace(/\\+/g, '-')\n .replace(/\\//g, '_')\n .replace(/=+$/, '');\n }\n\n /**\n * Initiate an OAuth2 flow for a bit.\n * \n * @param bitId - Unique identifier for the bit (e.g., \"bit-google-drive\")\n * @param config - OAuth2 configuration\n * @returns Authorization URL and flow info\n */\n async initiateFlow(bitId: string, config: OAuth2Config): Promise<InitiateFlowResult> {\n const state = this.generateState();\n const redirectUri = `${this.callbackBaseUrl}/${bitId}/callback`;\n const usePkce = config.pkce !== false; // PKCE enabled by default\n \n // Generate PKCE codes only if enabled\n const codeVerifier = usePkce ? this.generateCodeVerifier() : undefined;\n const codeChallenge = usePkce && codeVerifier ? await this.generateCodeChallenge(codeVerifier) : undefined;\n\n // Store OAuth state for later verification\n const oauthState: OAuth2State = {\n codeVerifier,\n codeChallenge,\n state,\n redirectUri,\n bitId,\n createdAt: Date.now(),\n config,\n };\n\n this.pendingFlows.set(state, oauthState);\n this.logger.info('OAuth flow initiated', { bitId, redirectUri, pkce: usePkce });\n\n // Build authorization URL\n const params = new URLSearchParams({\n response_type: 'code',\n client_id: config.clientId,\n redirect_uri: redirectUri,\n scope: config.scopes.join(' '),\n state,\n });\n \n // Add PKCE parameters if enabled\n if (usePkce && codeChallenge) {\n params.set('code_challenge', codeChallenge);\n params.set('code_challenge_method', 'S256');\n }\n\n // Add any extra parameters\n if (config.extraAuthParams) {\n for (const [key, value] of Object.entries(config.extraAuthParams)) {\n params.set(key, value);\n }\n }\n\n const authUrl = `${config.authorizationUrl}?${params.toString()}`;\n\n return { authUrl, state, redirectUri };\n }\n\n /**\n * Parse an OAuth callback URL to extract parameters.\n * Supports both query parameters (?code=...) and hash fragments (#access_token=...).\n * \n * @param callbackUrl - Full callback URL received from OAuth provider\n * @returns Parsed callback parameters\n */\n parseCallbackUrl(callbackUrl: string): OAuthCallbackParams {\n const result: OAuthCallbackParams = {};\n \n try {\n const url = new URL(callbackUrl);\n \n // First, try query parameters (standard authorization code flow)\n const queryParams = url.searchParams;\n if (queryParams.has('code')) {\n result.code = queryParams.get('code') || undefined;\n }\n if (queryParams.has('state')) {\n result.state = queryParams.get('state') || undefined;\n }\n if (queryParams.has('error')) {\n result.error = queryParams.get('error') || undefined;\n result.errorDescription = queryParams.get('error_description') || undefined;\n }\n \n // Then, try hash fragment (implicit flow or some providers)\n if (url.hash) {\n const hashParams = new URLSearchParams(url.hash.slice(1)); // Remove leading #\n \n // Access token in hash (implicit flow)\n if (hashParams.has('access_token')) {\n result.accessToken = hashParams.get('access_token') || undefined;\n result.tokenType = hashParams.get('token_type') || 'Bearer';\n const expiresIn = hashParams.get('expires_in');\n if (expiresIn) {\n result.expiresIn = parseInt(expiresIn, 10);\n }\n result.refreshToken = hashParams.get('refresh_token') || undefined;\n }\n \n // State can also be in hash\n if (hashParams.has('state') && !result.state) {\n result.state = hashParams.get('state') || undefined;\n }\n \n // Error can also be in hash\n if (hashParams.has('error') && !result.error) {\n result.error = hashParams.get('error') || undefined;\n result.errorDescription = hashParams.get('error_description') || undefined;\n }\n }\n } catch (e) {\n // If URL parsing fails, try to parse as fragment only (e.g., custom schemes)\n const parts = callbackUrl.split('#');\n if (parts.length > 1) {\n const hashParams = new URLSearchParams(parts[1]);\n result.accessToken = hashParams.get('access_token') || undefined;\n result.tokenType = hashParams.get('token_type') || undefined;\n result.state = hashParams.get('state') || undefined;\n result.error = hashParams.get('error') || undefined;\n result.errorDescription = hashParams.get('error_description') || undefined;\n const expiresIn = hashParams.get('expires_in');\n if (expiresIn) {\n result.expiresIn = parseInt(expiresIn, 10);\n }\n }\n \n // Also try query string parsing\n const queryParts = callbackUrl.split('?');\n if (queryParts.length > 1) {\n const queryStr = queryParts[1].split('#')[0]; // Remove any hash portion\n const queryParams = new URLSearchParams(queryStr);\n if (!result.code) result.code = queryParams.get('code') || undefined;\n if (!result.state) result.state = queryParams.get('state') || undefined;\n if (!result.error) result.error = queryParams.get('error') || undefined;\n if (!result.errorDescription) result.errorDescription = queryParams.get('error_description') || undefined;\n }\n }\n \n return result;\n }\n\n /**\n * Handle a callback URL directly (convenience method combining parse + exchange/handleImplicit).\n * \n * @param callbackUrl - Full callback URL received from OAuth provider\n * @returns Exchange result with bit ID and tokens\n */\n async handleCallback(callbackUrl: string): Promise<ExchangeResult> {\n const params = this.parseCallbackUrl(callbackUrl);\n \n if (params.error) {\n throw new Error(`OAuth error: ${params.error}${params.errorDescription ? ` - ${params.errorDescription}` : ''}`);\n }\n \n // Check for implicit flow (access token directly in callback)\n if (params.accessToken && params.state) {\n return this.handleImplicitCallback(params);\n }\n \n // Standard authorization code flow\n if (!params.code || !params.state) {\n throw new Error('Missing code or state parameter in OAuth callback');\n }\n \n return this.exchangeCode(params.state, params.code);\n }\n\n /**\n * Handle implicit flow callback (access token directly in callback URL).\n */\n private handleImplicitCallback(params: OAuthCallbackParams): ExchangeResult {\n if (!params.state || !params.accessToken) {\n throw new Error('Missing state or access_token for implicit flow');\n }\n \n const oauthState = this.pendingFlows.get(params.state);\n if (!oauthState) {\n throw new Error('Invalid or expired OAuth state. Please restart the authorization flow.');\n }\n \n // Remove the pending flow\n this.pendingFlows.delete(params.state);\n \n const tokens: OAuth2TokenSet = {\n accessToken: params.accessToken,\n refreshToken: params.refreshToken,\n tokenType: params.tokenType || 'Bearer',\n expiresAt: params.expiresIn ? Date.now() + params.expiresIn * 1000 : undefined,\n };\n \n // Store tokens\n oauthTokenStore.setToken(oauthState.bitId, tokens, oauthState.config);\n this.logger.info('OAuth implicit flow completed successfully', { bitId: oauthState.bitId });\n \n return { bitId: oauthState.bitId, tokens };\n }\n\n /**\n * Exchange authorization code for tokens.\n * \n * @param state - State parameter from callback\n * @param code - Authorization code from callback\n * @returns Token set or throws error\n */\n async exchangeCode(state: string, code: string): Promise<ExchangeResult> {\n const oauthState = this.pendingFlows.get(state);\n if (!oauthState) {\n throw new Error('Invalid or expired OAuth state. Please restart the authorization flow.');\n }\n\n // Remove the pending flow\n this.pendingFlows.delete(state);\n\n const { config, codeVerifier, redirectUri, bitId } = oauthState;\n\n // Exchange code for tokens\n const params = new URLSearchParams({\n grant_type: 'authorization_code',\n code,\n redirect_uri: redirectUri,\n client_id: config.clientId,\n });\n \n // Add code_verifier if PKCE was used\n if (codeVerifier) {\n params.set('code_verifier', codeVerifier);\n }\n\n if (config.clientSecret) {\n params.set('client_secret', config.clientSecret);\n }\n\n this.logger.info('Exchanging authorization code', { bitId });\n\n const response = await fetch(config.tokenUrl, {\n method: 'POST',\n headers: {\n 'Content-Type': 'application/x-www-form-urlencoded',\n 'Accept': 'application/json',\n },\n body: params.toString(),\n });\n\n if (!response.ok) {\n const errorText = await response.text();\n this.logger.error('Token exchange failed', { bitId, status: response.status, error: errorText });\n throw new Error(`Token exchange failed: ${response.status} - ${errorText}`);\n }\n\n const data = await response.json() as any;\n\n const tokens: OAuth2TokenSet = {\n accessToken: data.access_token,\n refreshToken: data.refresh_token,\n tokenType: data.token_type || 'Bearer',\n expiresAt: data.expires_in ? Date.now() + data.expires_in * 1000 : undefined,\n scope: data.scope,\n };\n\n // Store tokens\n oauthTokenStore.setToken(bitId, tokens, config);\n this.logger.info('OAuth flow completed successfully', { bitId });\n\n return { bitId, tokens };\n }\n\n /**\n * Get the pending OAuth state for a given state parameter.\n * Useful for validation without consuming the state.\n */\n getPendingFlow(state: string): OAuth2State | undefined {\n return this.pendingFlows.get(state);\n }\n\n /**\n * Check if a flow is pending for a bit.\n */\n hasPendingFlow(bitId: string): boolean {\n for (const state of this.pendingFlows.values()) {\n if (state.bitId === bitId) {\n return true;\n }\n }\n return false;\n }\n\n /**\n * Get pending authorization URL for a bit (if flow already initiated).\n */\n getPendingAuthUrl(bitId: string): string | null {\n for (const [state, oauthState] of this.pendingFlows.entries()) {\n if (oauthState.bitId === bitId) {\n // Rebuild the auth URL\n const { config, codeChallenge, redirectUri } = oauthState;\n const params = new URLSearchParams({\n response_type: 'code',\n client_id: config.clientId,\n redirect_uri: redirectUri,\n scope: config.scopes.join(' '),\n state,\n });\n \n if (codeChallenge) {\n params.set('code_challenge', codeChallenge);\n params.set('code_challenge_method', 'S256');\n }\n \n if (config.extraAuthParams) {\n for (const [key, value] of Object.entries(config.extraAuthParams)) {\n params.set(key, value);\n }\n }\n return `${config.authorizationUrl}?${params.toString()}`;\n }\n }\n return null;\n }\n\n /**\n * Cancel a pending OAuth flow.\n */\n cancelFlow(state: string): boolean {\n return this.pendingFlows.delete(state);\n }\n\n /**\n * Cancel all pending flows for a bit.\n */\n cancelFlowsForBit(bitId: string): number {\n let cancelled = 0;\n for (const [state, oauthState] of this.pendingFlows.entries()) {\n if (oauthState.bitId === bitId) {\n this.pendingFlows.delete(state);\n cancelled++;\n }\n }\n return cancelled;\n }\n\n /**\n * Clean up expired flows (older than 10 minutes).\n */\n cleanupExpiredFlows(): number {\n const now = Date.now();\n const expirationTime = 10 * 60 * 1000; // 10 minutes\n let cleaned = 0;\n\n for (const [state, oauthState] of this.pendingFlows.entries()) {\n if (now - oauthState.createdAt > expirationTime) {\n this.pendingFlows.delete(state);\n this.logger.debug('Expired OAuth flow cleaned up', { bitId: oauthState.bitId });\n cleaned++;\n }\n }\n\n return cleaned;\n }\n\n /**\n * Get all pending flow states (for debugging/status).\n */\n getPendingFlowStates(): Array<{ bitId: string; state: string; createdAt: number; redirectUri: string }> {\n return Array.from(this.pendingFlows.entries()).map(([state, oauthState]) => ({\n bitId: oauthState.bitId,\n state,\n createdAt: oauthState.createdAt,\n redirectUri: oauthState.redirectUri,\n }));\n }\n}\n\n/**\n * IOAuthHandler interface - Platform-specific OAuth handling\n * \n * Implement this interface to handle OAuth flows on different platforms.\n * The WorkflowExecutor uses this to trigger OAuth when tokens are missing.\n */\nexport interface IOAuthHandler {\n /**\n * Open an authorization URL in the appropriate context.\n * - Server: Print URL to console for user to visit\n * - Tauri: Open in system browser via opener plugin\n * - Browser: Redirect or open popup\n * \n * @param authUrl - The authorization URL to open\n * @param bitId - The bit ID this is for (for context)\n */\n openAuthUrl(authUrl: string, bitId: string): Promise<void>;\n \n /**\n * Wait for OAuth callback and return the result.\n * - Server: Wait for Express callback route to be hit\n * - Tauri: Listen for deep link callback\n * - Browser: Listen for postMessage or redirect\n * \n * @param state - The state parameter to wait for\n * @param timeoutMs - Timeout in milliseconds (default: 5 minutes)\n * @returns Exchange result with tokens\n */\n waitForCallback(state: string, timeoutMs?: number): Promise<ExchangeResult>;\n \n /**\n * Check if this handler supports the current platform.\n */\n isSupported(): boolean;\n}\n\n/**\n * OAuth requirement for workflow execution\n */\nexport interface WorkflowOAuthRequirement {\n /** Bit ID (derived from module name) */\n bitId: string;\n /** Module name (e.g., \"@ha-bits/bit-google-drive\") */\n moduleName: string;\n /** Display name of the bit */\n displayName: string;\n /** OAuth2 configuration */\n config: OAuth2Config;\n /** Status: 'needed', 'valid', or 'expired' */\n status: 'needed' | 'valid' | 'expired';\n}\n", "// Shared types for workflow execution system\n// This file consolidates DTOs from both frontend and backend\n\n// Core workflow execution types (from backend)\nexport interface WorkflowStep {\n id: string;\n type: 'trigger' | 'action';\n framework: 'activepieces' | 'n8n' | 'script';\n module: string;\n params: Record<string, any>;\n conditions?: {\n skipIf?: string;\n stopIf?: string;\n };\n retries?: number;\n timeout?: number;\n}\n\nexport interface ExecutionResult {\n nodeId: string;\n success: boolean;\n result?: any;\n error?: string;\n timestamp: Date;\n duration: number;\n}\n\nexport interface WorkflowExecution {\n id: string;\n workflowId: string;\n status: 'pending' | 'running' | 'completed' | 'failed' | 'cancelled';\n results: ExecutionResult[];\n nodeStatuses: NodeExecutionStatus[];\n startTime: Date;\n endTime?: Date;\n currentNode?: string;\n output?: any; // Resolved workflow output\n}\n\n// Backend workflow definition\nexport interface BackendWorkflow {\n id?: string;\n name: string;\n description?: string;\n steps: WorkflowStep[];\n variables?: Record<string, any>;\n metadata?: Record<string, any>;\n}\n\n// Frontend workflow UI types\nexport interface WorkflowNode {\n id: string;\n type: 'n8n' | 'activepieces' | 'script' | 'trigger' | 'action' | 'bits';\n position: { x: number; y: number };\n data: {\n label: string;\n framework: 'n8n' | 'activepieces' | 'script' | 'bits';\n source?: 'npm' | 'github' | 'local' | 'hub' | 'inline';\n module?: string;\n resource?: string;\n operation?: string;\n params?: Record<string, any>;\n credentials?: Record<string, any>;\n /** OAuth credentials config - clientId/clientSecret can reference env vars via {{habits.env.VAR}} */\n auth?: Record<string, any>;\n inputs?: string[];\n outputs?: string[];\n // Script-specific properties\n scriptPath?: string;\n language?: 'deno' | 'python3' | 'go' | 'bash' | 'sql' | 'typescript' | 'javascript';\n content?: string;\n inputTransforms?: Record<string, any>;\n stopAfterIf?: { expr: string; skipIfStopped?: boolean };\n // Script inline script\n script?: {\n type: 'script';\n language: 'deno' | 'python3' | 'go' | 'bash' | 'typescript' | 'javascript';\n content?: string;\n path?: string;\n };\n // Trigger-specific properties\n triggerType?: 'webhook' | 'polling' | 'schedule' | 'app_webhook';\n triggerSettings?: {\n authType?: 'none' | 'header' | 'query_param';\n authFields?: Record<string, any>;\n };\n };\n}\n\nexport interface WorkflowEdge {\n id: string;\n source: string;\n target: string;\n sourceHandle?: string;\n targetHandle?: string;\n optional?: boolean; // If true, target node can run when ANY optional edge is satisfied\n}\n\n// Generate all export files\nexport interface ExportBundle {\n id: string; // Stack UUID for build caching\n stackYaml: string;\n habitFiles: Array<{ filename: string; content: string }>;\n envFile: string;\n frontendHtml?: string;\n}\n\n// Frontend workflow definition (visual representation)\nexport interface FrontendWorkflow {\n id: string;\n name: string;\n description?: string;\n nodes: WorkflowNode[];\n edges: WorkflowEdge[];\n version: string;\n output?: Record<string, any>; // Template-based output definition\n}\n\n// Use frontend workflow format as the primary workflow type\nexport type Workflow = FrontendWorkflow;\n\n// ============================================================================\n// Visual Canvas Types - Structurally compatible with reactflow\n// ============================================================================\n\n/**\n * Visual canvas node type - structurally compatible with reactflow's Node<T>\n * Used by visual components for rendering workflow canvas\n */\nexport interface CanvasNode<T = any> {\n id: string;\n type?: string;\n position: { x: number; y: number };\n data: T;\n selected?: boolean;\n dragging?: boolean;\n}\n\n/**\n * Visual canvas edge type - structurally compatible with reactflow's Edge\n * Used by visual components for rendering workflow connections\n */\nexport interface CanvasEdge {\n id: string;\n source: string;\n target: string;\n sourceHandle?: string | null;\n targetHandle?: string | null;\n type?: string;\n animated?: boolean;\n label?: any; // Compatible with ReactNode from reactflow\n}\n\n// ============================================================================\n// Export Format Types - Used for YAML/JSON serialization\n// ============================================================================\n\n/**\n * Node format for habit YAML export files\n * Simplified format for serialization and sharing\n */\nexport interface HabitNode {\n id: string;\n type: string;\n position?: { x: number; y: number };\n data: {\n framework: 'n8n' | 'activepieces' | 'script' | 'bits';\n module?: string;\n label?: string;\n source?: string;\n operation?: string;\n params?: Record<string, any>;\n credentials?: Record<string, any>;\n script?: {\n type: string;\n language: string;\n content: string;\n };\n content?: string;\n language?: string;\n };\n}\n\n/**\n * Edge format for habit YAML export files\n */\nexport interface HabitEdge {\n id: string;\n source: string;\n target: string;\n sourceHandle?: string;\n targetHandle?: string;\n}\n\n/**\n * Complete habit definition for export/import\n */\nexport interface Habit {\n id: string;\n name: string;\n description: string;\n nodes: HabitNode[];\n edges: HabitEdge[];\n output?: Record<string, string>; // Habit-level output mappings\n version: string;\n createdAt: string;\n updatedAt: string;\n}\n\n// ============================================================================\n// Flow Control Types - Allow nodes to control downstream execution\n// ============================================================================\n\n/**\n * Flow control metadata returned by nodes that control branching.\n * This allows nodes like bit-if, switch, router to specify which downstream\n * branches should be executed and which should be skipped.\n */\nexport interface FlowControlMetadata {\n /**\n * Array of sourceHandle identifiers that should be activated.\n * Downstream nodes connected via these handles will execute.\n * e.g., [\"branch-0\"] to only activate the first branch\n */\n activeBranches?: string[];\n \n /**\n * Array of sourceHandle identifiers that should be skipped.\n * Downstream nodes connected via these handles will be marked as skipped.\n * If activeBranches is provided, skipBranches is ignored.\n */\n skipBranches?: string[];\n \n /**\n * If true, only connections from activeBranches will execute.\n * If false or undefined, flow control is not applied.\n */\n controlsFlow?: boolean;\n}\n\n/**\n * Edge information for dependency tracking\n */\nexport interface EdgeInfo {\n sourceNodeId: string;\n sourceHandle?: string; // e.g., \"branch-0\", \"branch-1\"\n targetHandle?: string;\n optional?: boolean;\n}\n\n// Node dependency tracking for execution\nexport interface NodeDependencies {\n nodeId: string;\n dependsOn: string[]; // Node IDs this node depends on (incoming edges) - required\n optionalDependsOn: string[]; // Optional dependencies - node runs when ANY is satisfied\n dependencyFor: string[]; // Node IDs that depend on this node (outgoing edges)\n /**\n * Detailed edge information for flow control.\n * Maps source node ID to edge info including sourceHandle.\n */\n incomingEdges?: EdgeInfo[];\n}\n\n// Execution context for tracking node execution status\nexport interface NodeExecutionStatus {\n nodeId: string;\n status: 'pending' | 'running' | 'completed' | 'failed' | 'skipped';\n result?: any;\n error?: string;\n startTime?: Date;\n endTime?: Date;\n duration?: number;\n}\n\n// Module management types\nexport interface AvailableModuleDefinition {\n framework: string;\n name: string;\n package: string;\n version: string;\n description: string;\n license: string;\n repository?: string;\n cloned?: boolean;\n built?: boolean;\n installed?: boolean;\n /** Icon URL or Lucide icon reference (e.g., \"lucide:Database\") */\n logoUrl?: string;\n displayName?: string;\n}\n\n// Script-specific types\nexport interface ScriptModule {\n id: string;\n summary?: string;\n value: {\n type: 'script' | 'forloopflow' | 'branchone' | 'branchall';\n path?: string;\n content?: string;\n language?: 'deno' | 'python3' | 'go' | 'bash' | 'sql' | 'typescript' | 'javascript';\n lock?: string;\n inputTransforms?: Record<string, any>;\n modules?: ScriptModule[]; // For flow types\n iterator?: { expr: string; type: string }; // For forloopflow\n branches?: { expr: string; modules: ScriptModule[] }[]; // For branches\n parallel?: boolean;\n skipFailures?: boolean;\n };\n stopAfterIf?: {\n expr: string;\n skipIfStopped?: boolean;\n };\n}\n\nexport interface ScriptWorkflow {\n summary: string;\n description?: string;\n value: {\n modules: ScriptModule[];\n failureModule?: ScriptModule;\n };\n schema: {\n type: string;\n $schema: string;\n required?: string[];\n properties: Record<string, any>;\n };\n}\n\n// Node templates for UI\nexport interface NodeTemplate {\n id: string;\n label: string;\n framework: 'n8n' | 'activepieces' | 'script' | 'bits';\n module: string;\n icon?: string;\n color: string;\n description?: string;\n resources?: {\n name: string;\n operations: string[];\n }[];\n // Script-specific template properties\n scriptType?: 'script' | 'flow';\n language?: 'deno' | 'python3' | 'go' | 'bash' | 'sql' | 'typescript';\n}\n\n// Execution API types\nexport interface ExecutionRequest {\n framework: string;\n module: string;\n async?: boolean;\n params: Record<string, any>;\n}\n\n// Webhook trigger types\nexport interface WebhookTriggerInfo {\n nodeId: string;\n path: string;\n method?: string;\n authType?: 'none' | 'header' | 'query_param';\n authFields?: Record<string, any>;\n}\n\nexport interface WebhookPayload {\n nodeId: string;\n payload: any;\n headers?: Record<string, string>;\n query?: Record<string, string>;\n}\n\n// Multi-workflow configuration types\nexport interface WorkflowReference {\n id?: string; // Optional - if not provided, uses the id from the workflow JSON file\n path: string; // Path to workflow JSON file (relative to config.json or absolute)\n enabled?: boolean; // Whether this workflow is enabled (default: true)\n webhookTimeout?: number; // Optional per-workflow webhook timeout\n}\n\n/**\n * Modules operation mode:\n * - 'restricted': Only allows using modules already defined in modules.json\n * - 'open': Allows adding any module and appends it to modules.json if it doesn't exist\n */\nexport type ModulesMode = 'restricted' | 'open';\n\nexport interface WorkflowConfig {\n version?: string;\n workflows: WorkflowReference[];\n server?: {\n port?: number;\n host?: string;\n webhookPort?: number; // Deprecated: webhooks now served on same port under /webhook\n webhookHost?: string; // Deprecated: webhooks now served on same port under /webhook\n frontend?: string; // Path to static frontend folder to serve at \"/\" (relative to config.json or absolute)\n openapi?: boolean; // Enable OpenAPI/Swagger documentation at /api/docs (default: false)\n };\n modules?: {\n mode?: ModulesMode; // 'restricted' (default) or 'open' - can also be set via HABITS_MODULES_MODE env var\n };\n defaults?: {\n webhookTimeout?: number;\n };\n /**\n * Application configuration for desktop/mobile builds\n */\n application?: {\n /** Custom URL scheme for OAuth deep links (e.g., \"myapp\" for myapp://oauth/callback) */\n scheme?: string;\n /** Application display name (used in Tauri builds) */\n name?: string;\n /** Application identifier (e.g., \"com.mycompany.myapp\") */\n identifier?: string;\n };\n /**\n * Logging configuration\n * Can be overridden by environment variables (HABITS_LOG_*)\n */\n logging?: {\n /** Default log level: trace, debug, info, warn, error, fatal, none */\n level?: 'trace' | 'debug' | 'info' | 'warn' | 'error' | 'fatal' | 'none';\n /** Output destinations */\n outputs?: ('console' | 'file' | 'json')[];\n /** File output configuration */\n file?: {\n path?: string;\n maxSize?: string; // e.g., '10mb'\n maxFiles?: number;\n };\n /** Output format for console/file */\n format?: 'text' | 'json';\n /** Enable colors in console output */\n colorize?: boolean;\n /** Per-bit log level overrides (e.g., { 'bit-http': 'debug' }) */\n bitOverrides?: Record<string, 'trace' | 'debug' | 'info' | 'warn' | 'error' | 'fatal' | 'none'>;\n };\n}\n\nexport interface LoadedWorkflow {\n reference: WorkflowReference;\n workflow: Workflow;\n}\n\nexport function isFrontendWorkflow(workflow: Workflow): workflow is FrontendWorkflow {\n return 'nodes' in workflow && 'edges' in workflow && Array.isArray(workflow.nodes) && Array.isArray(workflow.edges);\n}\n\n// ============================================================================\n// Execution Response Types (shared between streaming and non-streaming)\n// ============================================================================\n\n/**\n * Base execution context - common fields for all responses\n */\nexport interface ExecutionContext {\n executionId: string;\n workflowId: string;\n}\n\n/**\n * Node result - emitted when a node completes or fails\n * Used in both streaming (per-node) and non-streaming (in nodeResults array)\n */\nexport interface NodeResult extends ExecutionContext {\n nodeId: string;\n nodeName: string;\n status: 'completed' | 'failed';\n output?: any;\n error?: string;\n duration?: number;\n}\n\n/**\n * Execution summary - final execution status\n * Used in both streaming (final event) and non-streaming (response)\n */\nexport interface ExecutionSummary extends ExecutionContext {\n status: 'completed' | 'failed' | 'cancelled';\n output?: any;\n error?: string;\n startTime: string;\n endTime: string;\n}\n\n/**\n * Full execution response (non-streaming mode)\n * Contains summary plus optional node results\n */\nexport interface ExecutionResponse extends ExecutionSummary {\n nodeResults?: NodeResult[];\n}\n\n// ============================================================================\n// Streaming Types\n// ============================================================================\n\nexport type StreamEventType = 'execution_started' | 'node_started' | 'node_completed' | 'node_failed' | 'execution_completed' | 'execution_failed';\n\n/**\n * Minimal node stream event (non-debug mode)\n * Mirrors NodeResult structure for consistency\n */\nexport interface StreamNodeEvent extends NodeResult {\n type?: 'node_completed' | 'node_failed';\n}\n\n/**\n * Minimal execution stream event (non-debug mode) \n * Mirrors ExecutionSummary structure for consistency\n */\nexport interface StreamExecutionEvent extends ExecutionContext {\n type: 'execution_completed' | 'execution_failed';\n status: 'completed' | 'failed';\n output?: any;\n error?: string;\n}\n\n/**\n * Verbose stream event - contains all fields (used in debug mode)\n */\nexport interface StreamEvent extends ExecutionContext {\n type: StreamEventType;\n timestamp: string;\n nodeId?: string;\n nodeName?: string;\n status?: 'pending' | 'running' | 'completed' | 'failed' | 'skipped';\n result?: any; // Alias for output in verbose mode\n output?: any; // Final workflow output (only in execution_completed)\n error?: string;\n duration?: number;\n progress?: {\n completed: number;\n total: number;\n percentage: number;\n };\n}\n\nexport type StreamCallback = (event: StreamEvent) => void;\n\n// Common framework types\nexport type Framework = 'activepieces' | 'n8n' | 'script' | 'bits';\nexport type StepType = 'trigger' | 'action';\nexport type ExecutionStatus = 'pending' | 'running' | 'completed' | 'failed' | 'cancelled';\nexport type ScriptLanguage = 'deno' | 'python3' | 'go' | 'bash' | 'sql' | 'typescript';\nexport type ScriptModuleType = 'script' | 'forloopflow' | 'branchone' | 'branchall';"],
|
|
5
|
-
"mappings": "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",
|
|
6
|
-
"names": ["path", "
|
|
3
|
+
"sources": ["../../../../packages/cortex/core/src/WorkflowExecutor.ts", "../../../../packages/bindings/src/runtime.ts", "../../../../packages/bindings/src/fs.ts", "../../../../packages/bindings/src/path.ts", "../../../../packages/bindings/src/shell.ts", "../../../../packages/core/src/types.ts", "../../../../packages/core/src/logger/types.ts", "../../../../packages/core/src/logger/Logger.ts", "../../../../packages/core/src/logger/ConfigResolver.ts", "../../../../packages/core/src/logger/transports/Transport.ts", "../../../../packages/core/src/logger/transports/ConsoleTransport.ts", "../../../../packages/core/src/logger/transports/FileTransport.ts", "../../../../packages/core/src/logger/formatters/Formatter.ts", "../../../../packages/core/src/logger/formatters/JsonFormatter.ts", "../../../../packages/core/src/logger/transports/JsonTransport.ts", "../../../../packages/core/src/logger/formatters/TextFormatter.ts", "../../../../packages/core/src/logger/LoggerFactory.ts", "../../../../packages/cortex/core/src/utils/utils.ts", "../../../../packages/cortex/core/src/utils/customRequire.ts", "../../../../packages/cortex/core/src/utils/moduleCloner.ts", "../../../../packages/cortex/core/src/utils/moduleLoader.ts", "../../../../packages/cortex/core/src/n8n/executionContext.ts", "../../../../packages/cortex/core/src/n8n/httpRequest.ts", "../../../../packages/cortex/core/src/n8n/credentialLoader.ts", "../../../../packages/cortex/core/src/n8n/nodeExecution.ts", "../../../../packages/cortex/core/src/n8n/n8nExecutor.ts", "../../../../packages/cortex/core/src/activepieces/activepiecesExecutor.ts", "../../../../packages/cortex/core/src/activepieces/activepiecesTrigger.ts", "../../../../packages/cortex/core/src/bits/declarativeExecutor.ts", "../../../../packages/cortex/core/src/bits/bitsDoer.ts", "../../../../packages/cortex/core/src/bits/bitsWatcher.ts", "../../../../packages/cortex/core/src/script/scriptExecutor.ts", "../../../../packages/cortex/core/src/security/inputScanner.ts", "../../../../packages/cortex/core/src/esm.ts", "../../../../packages/cortex/core/src/utils/index.ts", "../../../../packages/cortex/core/src/bits/framework.ts"],
|
|
4
|
+
"sourcesContent": ["import { v4 as uuidv4 } from 'uuid';\nimport { executeN8nModule } from './n8n/n8nExecutor';\nimport { executeActivepiecesModule } from './activepieces/activepiecesExecutor';\nimport { triggerHelper, TriggerHookType } from './activepieces/activepiecesTrigger';\nimport { executeBitsModule } from './bits/bitsDoer';\nimport { bitsTriggerHelper } from './bits/bitsWatcher';\nimport { executeScriptModule } from './script/scriptExecutor';\nimport { ensureModuleInstalled } from './utils/moduleLoader';\nimport { getSecurityConfig, scanInputForSecurity } from './security/inputScanner';\nimport { LoggerFactory, ILogger } from '@ha-bits/core';\nimport { IWebhookHandler } from './WebhookHandler';\nimport {\n Workflow,\n WorkflowNode,\n WorkflowEdge,\n ExecutionResult,\n WorkflowExecution,\n NodeDependencies,\n NodeExecutionStatus,\n WebhookTriggerInfo,\n WorkflowConfig,\n WorkflowReference,\n LoadedWorkflow,\n StreamCallback,\n StreamEvent,\n FlowControlMetadata,\n} from '@habits/shared/types';\n\n// ============================================================================\n// Workflow Executor\n// ============================================================================\n\n/**\n * Options for initializing WorkflowExecutor from in-memory data\n */\nexport interface InitFromDataOptions {\n /** The workflow configuration (equivalent to config.json content) */\n config: WorkflowConfig;\n /** Map of workflow id to workflow object (instead of loading from file paths) */\n workflows: Map<string, Workflow> | Record<string, Workflow>;\n /** Environment variables to set (equivalent to .env file content parsed) */\n env?: Record<string, string>;\n}\n\nexport class WorkflowExecutor {\n private executions: Map<string, WorkflowExecution> = new Map();\n private loadedWorkflows: Map<string, LoadedWorkflow> = new Map();\n private config: WorkflowConfig | null = null;\n private logger: ILogger = LoggerFactory.getRoot();\n private env: Record<string, string | undefined> = {};\n\n /**\n * Initialize from in-memory data (no file system access needed)\n * This is the ONLY initialization method - it's platform-agnostic (works in browser and Node.js)\n */\n async initFromData(options: InitFromDataOptions): Promise<void> {\n const { config, workflows, env } = options;\n\n // Store environment variables in class property (platform-agnostic)\n if (env) {\n this.env = { ...env };\n // Also set process.env for Node.js compatibility with modules that read it directly\n if (typeof process !== 'undefined' && process.env) {\n for (const [key, value] of Object.entries(env)) {\n process.env[key] = value;\n }\n }\n }\n\n // Initialize logger from config (env vars are applied automatically by ConfigResolver)\n this.logger = LoggerFactory.initRoot(config.logging);\n this.logger.info('Environment variables set from config');\n\n this.config = config;\n this.logger.info('Loading workflow configuration from data');\n this.logger.debug('Config details', { \n version: this.config.version || 'not specified',\n workflowCount: this.config.workflows.length \n });\n\n // Convert Record to Map if needed\n const workflowsMap = workflows instanceof Map \n ? workflows \n : new Map(Object.entries(workflows));\n\n // Load each workflow from the provided map\n for (const workflowRef of this.config.workflows) {\n if (workflowRef.enabled === false) {\n this.logger.log(` \u23ED\uFE0F Skipping disabled workflow: ${workflowRef.id || workflowRef.path}`);\n continue;\n }\n\n // Try to find workflow by id first, then by path (as a key)\n const workflowId = workflowRef.id || workflowRef.path;\n let workflow = workflowsMap.get(workflowId);\n \n // Also try the path as a fallback key\n if (!workflow && workflowRef.path) {\n workflow = workflowsMap.get(workflowRef.path);\n }\n\n if (!workflow) {\n this.logger.error(` \u274C Workflow not found in data: ${workflowId}`);\n continue;\n }\n\n try {\n const finalWorkflowId = workflowRef.id || workflow.id || workflowId;\n\n if (!finalWorkflowId) {\n this.logger.error(` \u274C No id found for workflow - please specify id in config or workflow`);\n continue;\n }\n\n // Update workflow id to match the resolved id\n workflow.id = finalWorkflowId;\n\n // Update reference with resolved id for consistency\n const resolvedRef = { ...workflowRef, id: finalWorkflowId };\n\n this.loadedWorkflows.set(finalWorkflowId, {\n reference: resolvedRef,\n workflow\n });\n\n this.logger.log(` \u2705 Loaded workflow: ${finalWorkflowId} (${workflow.name})`);\n\n // Print all env variables starting with HABITS_, only the names not values\n this.logger.log(` \uD83D\uDD11 Environment variables:`);\n for (const key of Object.keys(this.env)) {\n if (key.startsWith('HABITS_')) {\n this.logger.log(` - ${key}: ${this.env[key]}`);\n }\n }\n\n // Log resolvable params that start with \"habits.\"\n this.logger.log(` \uD83D\uDCCB Resolvable habits params in workflow:`);\n const habitsParams = this.findHabitsParams(workflow);\n if (habitsParams.length > 0) {\n for (const param of habitsParams) {\n if (param.startsWith('habits.env.')) {\n const envVar = param.slice('habits.env.'.length);\n const value = this.env[envVar];\n this.logger.log(` - {{${param}}} \u2192 ${value !== undefined ? value : '(not set)'}`);\n } else {\n this.logger.log(` - {{${param}}} \u2192 (resolved at runtime)`);\n }\n }\n } else {\n this.logger.log(` (none found)`);\n }\n } catch (error: any) {\n this.logger.error(` \u274C Failed to load workflow ${workflowRef.id || workflowRef.path}: ${error.message}`);\n }\n }\n\n // Make sure no repeated workflowId\n const workflowIds = Array.from(this.loadedWorkflows.keys());\n const duplicates = workflowIds.filter((id, index) => workflowIds.indexOf(id) !== index);\n if (duplicates.length > 0) {\n throw new Error(`Duplicate workflow IDs found: ${duplicates.join(', ')}`);\n }\n\n this.logger.log(`\\n\uD83D\uDCE6 Successfully loaded ${this.loadedWorkflows.size} workflow(s)\\n`);\n\n // Pre-load all modules to ensure they're ready before first request\n await this.preloadModules();\n }\n\n /**\n * Pre-load all modules referenced in loaded workflows\n * This ensures dependencies are cloned/installed before the first request\n */\n private async preloadModules(): Promise<void> {\n const modulesToPreload: Set<string> = new Set();\n const moduleDefinitions: Map<string, { framework: string; source: string; module: string }> = new Map();\n\n // Scan all loaded workflows for modules\n for (const [workflowId, { workflow }] of this.loadedWorkflows) {\n for (const node of workflow.nodes || []) {\n const { framework, source, module: moduleName } = node.data;\n // Skip inline scripts - they don't need preloading\n if (source === 'inline') {\n continue;\n }\n if (framework && source && moduleName) {\n const key = `${framework}:${source}:${moduleName}`;\n if (!modulesToPreload.has(key)) {\n modulesToPreload.add(key);\n moduleDefinitions.set(key, { framework, source, module: moduleName });\n }\n }\n }\n }\n\n if (modulesToPreload.size === 0) {\n this.logger.log(`\\n\uD83D\uDCE6 No modules to preload\\n`);\n return;\n }\n\n this.logger.log(`\\n\uD83D\uDCE6 Pre-loading ${modulesToPreload.size} module(s)...`);\n\n // Preload all modules in parallel\n const preloadPromises = Array.from(moduleDefinitions.entries()).map(async ([key, def]) => {\n try {\n this.logger.log(` \u23F3 Preloading: ${def.module}`);\n await ensureModuleInstalled({\n framework: def.framework,\n source: def.source as 'github' | 'npm',\n repository: def.module,\n });\n this.logger.log(` \u2705 Preloaded: ${def.module}`);\n } catch (error: any) {\n this.logger.error(` \u274C Failed to preload ${def.module}: ${error.message}`);\n }\n });\n\n await Promise.all(preloadPromises);\n this.logger.log(`\\n\uD83D\uDCE6 Module preloading complete\\n`);\n\n // Hook polling triggers for activepieces modules\n await this.hookPollingTriggers();\n }\n\n /**\n * Hook polling triggers for all loaded workflows\n * This sets up activepieces polling triggers to run immediately\n */\n private async hookPollingTriggers(): Promise<void> {\n for (const [workflowId, { workflow }] of this.loadedWorkflows) {\n for (const node of workflow.nodes || []) {\n // Check if this is an activepieces polling trigger\n if (triggerHelper.isActivepiecesTrigger(node) && node.data?.triggerType === 'polling') {\n const triggerName = node.data.operation;\n if (!triggerName) {\n this.logger.warn(`\u26A0\uFE0F No operation specified for polling trigger: ${node.id}`);\n continue;\n }\n\n this.logger.log(`\\n\uD83D\uDD14 Hooking polling trigger: ${node.id} (${triggerName}) in workflow ${workflowId}`);\n \n try {\n const moduleDefinition = {\n framework: node.data.framework,\n source: node.data.source as 'github' | 'npm',\n repository: node.data.module || '',\n };\n\n // Resolve template strings in params and credentials\n const resolvedParams = this.resolveParameters(node.data.params || {}, {});\n const resolvedCredentials = this.resolveParameters(node.data.credentials || {}, {});\n\n // Merge params and credentials for trigger input\n const triggerInput = {\n ...resolvedParams,\n credentials: resolvedCredentials,\n };\n\n this.logger.log(` \uD83D\uDCCB Trigger input: ${JSON.stringify(triggerInput, null, 2)}`);\n\n // Execute the specific trigger immediately\n this.logger.log(` \uD83D\uDE80 Running trigger ${triggerName} immediately...`);\n const result = await triggerHelper.executeActivepiecesTrigger({\n moduleDefinition,\n triggerName,\n input: triggerInput,\n });\n\n this.logger.log(`\\n\uD83D\uDCEC Trigger result for ${triggerName}:`);\n this.logger.log(` Success: ${result.success}`);\n this.logger.log(` Output items: ${result.output?.length || 0}`);\n if (result.output && result.output.length > 0) {\n this.logger.log(` Output: ${JSON.stringify(result.output, null, 2)}`);\n \n // Trigger returned data - execute workflow continuation\n this.logger.log(`\\n\uD83D\uDE80 Trigger ${node.id} returned data, executing workflow continuation...`);\n for (const item of result.output) {\n try {\n // Execute workflow with trigger node pre-populated\n const executionResult = await this.executeWorkflow(workflowId, {\n startFromNode: node.id,\n triggerData: { [node.id]: item },\n });\n this.logger.log(` \u2705 Workflow execution completed: ${executionResult.status}`);\n } catch (execError: any) {\n this.logger.error(` \u274C Workflow execution failed: ${execError.message}`);\n }\n }\n }\n } catch (error: any) {\n this.logger.error(` \u274C Failed to hook trigger ${node.id}: ${error.message}`);\n }\n }\n }\n }\n }\n\n /**\n * Find all template params starting with \"habits.\" in a workflow\n */\n private findHabitsParams(workflow: Workflow): string[] {\n const habitsParams: Set<string> = new Set();\n const templateRegex = /\\{\\{(habits\\.[^}]+)\\}\\}/g;\n\n const scanObject = (obj: any) => {\n if (typeof obj === 'string') {\n let match;\n while ((match = templateRegex.exec(obj)) !== null) {\n habitsParams.add(match[1].trim());\n }\n } else if (Array.isArray(obj)) {\n obj.forEach(item => scanObject(item));\n } else if (typeof obj === 'object' && obj !== null) {\n Object.values(obj).forEach(value => scanObject(value));\n }\n };\n\n // Scan nodes\n workflow.nodes?.forEach(node => scanObject(node.data));\n // Scan output\n if (workflow.output) scanObject(workflow.output);\n if ((workflow as any).outputs) scanObject((workflow as any).outputs);\n\n return Array.from(habitsParams).sort();\n }\n\n /**\n * Get a loaded workflow by ID\n */\n getWorkflow(workflowId: string): LoadedWorkflow | undefined {\n return this.loadedWorkflows.get(workflowId);\n }\n\n /**\n * Get all loaded workflows\n */\n getAllWorkflows(): LoadedWorkflow[] {\n return Array.from(this.loadedWorkflows.values());\n }\n\n /**\n * Add a workflow programmatically (for OpenAPI generation without file loading)\n */\n addWorkflow(workflow: Workflow, reference?: Partial<WorkflowReference>): void {\n const workflowId = reference?.id || workflow.id;\n if (!workflowId) {\n throw new Error('Workflow must have an id');\n }\n \n const fullReference: WorkflowReference = {\n id: workflowId,\n path: reference?.path || `inline:${workflowId}`,\n enabled: reference?.enabled !== false,\n ...(reference?.webhookTimeout && { webhookTimeout: reference.webhookTimeout }),\n };\n \n this.loadedWorkflows.set(workflowId, {\n reference: fullReference,\n workflow: { ...workflow, id: workflowId },\n });\n }\n\n /**\n * Get the current config\n */\n getConfig(): WorkflowConfig | null {\n return this.config;\n }\n\n /**\n * Execute a complete workflow using dependency-based execution\n */\n async executeWorkflow(workflowOrId: Workflow | string, options?: {\n webhookHandler?: IWebhookHandler; // Optional webhook handler for workflow triggers (Node.js server only)\n webhookTimeout?: number;\n initialContext?: Record<string, any>;\n onStream?: StreamCallback;\n triggerData?: Record<string, any>; // Pre-populate trigger node outputs\n startFromNode?: string; // Start execution from a specific node\n }): Promise<WorkflowExecution> {\n // Resolve workflow from ID if string provided\n let workflow: Workflow;\n if (typeof workflowOrId === 'string') {\n const loaded = this.loadedWorkflows.get(workflowOrId);\n if (!loaded) {\n throw new Error(`Workflow not found: ${workflowOrId}`);\n }\n workflow = loaded.workflow;\n } else {\n workflow = workflowOrId;\n }\n\n const executionId = uuidv4();\n const execution: WorkflowExecution = {\n id: executionId,\n workflowId: workflow.id,\n status: 'running',\n results: [],\n nodeStatuses: [],\n startTime: new Date(),\n };\n\n this.executions.set(executionId, execution);\n this.logger.log(`\\n\uD83D\uDE80 Starting workflow execution: ${workflow.name} (${executionId})`);\n\n // Helper function to emit stream events\n const emitStreamEvent = (event: Omit<StreamEvent, 'timestamp' | 'executionId' | 'workflowId'>) => {\n if (options?.onStream) {\n const completedCount = execution.nodeStatuses.filter(s => s.status === 'completed' || s.status === 'failed').length;\n const totalCount = workflow.nodes.length;\n options.onStream({\n ...event,\n timestamp: new Date().toISOString(),\n executionId,\n workflowId: workflow.id,\n progress: {\n completed: completedCount,\n total: totalCount,\n percentage: totalCount > 0 ? Math.round((completedCount / totalCount) * 100) : 0\n }\n });\n }\n };\n\n // Emit execution started event\n emitStreamEvent({\n type: 'execution_started',\n status: 'running'\n });\n\n try {\n // Scan for webhook triggers\n const webhookTriggers = this.findWebhookTriggers(workflow.nodes);\n\n // If there are webhook triggers, ensure a webhook handler is provided\n if (webhookTriggers.length > 0) {\n if (!options?.webhookHandler) {\n throw new Error(\n `Workflow \"${workflow.name}\" contains ${webhookTriggers.length} webhook trigger(s) but no webhookHandler was provided. ` +\n `Webhook triggers are only supported in Node.js server environments. ` +\n `Provide a webhookHandler via options or remove webhook triggers from the workflow.`\n );\n }\n\n this.logger.log(`\\n\uD83D\uDCCB Detected ${webhookTriggers.length} webhook trigger(s):`);\n for (const trigger of webhookTriggers) {\n this.logger.log(` - Node: ${trigger.nodeId}`);\n }\n this.logger.log('\\n\u23F3 Waiting for webhook(s) to be triggered...\\n');\n }\n\n // Build dependency arrays\n const dependencies = this.buildDependencyMap(workflow.nodes, workflow?.edges || []);\n\n // Initialize node statuses\n execution.nodeStatuses = workflow.nodes.map(node => ({\n nodeId: node.id,\n status: 'pending' as const\n }));\n\n // Execution context to share data between nodes\n // Initialize with any provided initial context (e.g., habits.input, habits.headers, habits.cookies)\n let context: Record<string, any> = options?.initialContext ? { ...options.initialContext } : {};\n\n // Initialize habits namespace if not present\n if (!context.habits) {\n context.habits = {};\n }\n\n // Add habits.context with workflow execution metadata\n context.habits.context = {\n workflowId: workflow.id,\n workflowName: workflow.name,\n executionId,\n timestamp: new Date().toISOString(),\n startTime: execution.startTime.toISOString(),\n nodeId: '', // Will be set per-node during execution\n };\n\n // Security scanning on habits.input.* data (DLP, PII, Moderation)\n const securityConfig = getSecurityConfig();\n if (context.habits?.input) {\n context.habits.input = await scanInputForSecurity(context.habits.input, securityConfig, this.logger);\n }\n\n // If triggerData provided, mark trigger nodes as completed and add to context\n if (options?.triggerData) {\n for (const [nodeId, data] of Object.entries(options.triggerData)) {\n // Security scanning on trigger output data\n const scannedData = await scanInputForSecurity(data, securityConfig, this.logger);\n context[nodeId] = scannedData;\n this.updateNodeStatus(execution, nodeId, 'completed', { result: data });\n this.logger.log(`\uD83D\uDCCD Pre-populated trigger node: ${nodeId}`);\n \n // Add result to execution\n execution.results.push({\n nodeId,\n success: true,\n result: data,\n duration: 0,\n timestamp: new Date(),\n });\n }\n }\n\n // Keep executing until all nodes are completed or failed\n while (this.hasRunnableNodes(execution.nodeStatuses, dependencies)) {\n const runnableNodes = this.findRunnableNodes(execution.nodeStatuses, dependencies);\n\n if (runnableNodes.length === 0) {\n this.logger.log('\u26A0\uFE0F No runnable nodes found, stopping execution');\n break;\n }\n\n // Execute all runnable nodes in parallel\n const nodeExecutionPromises = runnableNodes.map(async (nodeId) => {\n const node = workflow.nodes.find(n => n.id === nodeId);\n if (!node) return;\n\n // Check flow control - skip nodes on non-activated branches\n const flowControlResult = this.checkFlowControl(nodeId, dependencies, context);\n if (flowControlResult === 'skip') {\n // Mark node as skipped and add minimal context\n context[nodeId] = { _skipped: true, _reason: 'Branch not activated by upstream flow control' };\n this.updateNodeStatus(execution, nodeId, 'skipped');\n \n // Emit node skipped event\n emitStreamEvent({\n type: 'node_completed',\n nodeId,\n nodeName: node.data.label,\n status: 'skipped',\n result: { _skipped: true },\n duration: 0\n });\n return;\n }\n\n execution.currentNode = nodeId;\n this.logger.log(`\\n\uD83D\uDCDD Executing node: ${nodeId} (${node.data.label})`);\n\n // Update habits.context.nodeId for the current node\n if (context.habits?.context) {\n context.habits.context.nodeId = nodeId;\n }\n\n // Update node status to running\n this.updateNodeStatus(execution, nodeId, 'running');\n\n // Emit node started event\n emitStreamEvent({\n type: 'node_started',\n nodeId,\n nodeName: node.data.label,\n status: 'running'\n });\n\n try {\n // Check if this is a webhook trigger node\n if (this.isWebhookTriggerNode(node)) {\n // webhookHandler is guaranteed to exist here - we validated at the start of executeWorkflow\n const webhookResult = await this.handleWebhookTrigger(node, context, execution, options!.webhookHandler!, options?.webhookTimeout);\n\n // Security scanning on webhook trigger output data\n const scannedResult = await scanInputForSecurity(webhookResult.result, securityConfig, this.logger);\n\n // Update context with scanned webhook result\n context[`${nodeId}`] = scannedResult;\n context[nodeId] = scannedResult;\n context.previous_result = scannedResult;\n context.webhookPayload = scannedResult; // Also store as webhookPayload for easy access\n\n this.updateNodeStatus(execution, nodeId, webhookResult.success ? 'completed' : 'failed', {\n result: scannedResult,\n error: webhookResult.error,\n startTime: new Date(webhookResult.timestamp.getTime() - webhookResult.duration),\n endTime: webhookResult.timestamp,\n duration: webhookResult.duration\n });\n\n // Emit node completed/failed event\n emitStreamEvent({\n type: webhookResult.success ? 'node_completed' : 'node_failed',\n nodeId,\n nodeName: node.data.label,\n status: webhookResult.success ? 'completed' : 'failed',\n result: scannedResult,\n error: webhookResult.error,\n duration: webhookResult.duration\n });\n\n if (!webhookResult.success) {\n this.logger.error(`\u274C Webhook trigger ${nodeId} failed: ${webhookResult.error}`);\n }\n } else {\n const nodeResult = await this.executeNode(node, context, execution);\n\n // Update context with node result\n context[`${nodeId}`] = nodeResult.result;\n context[nodeId] = nodeResult.result; // Also store by node ID for easier access\n context.previous_result = nodeResult.result;\n\n // Update node status based on result\n this.updateNodeStatus(execution, nodeId, nodeResult.success ? 'completed' : 'failed', {\n result: nodeResult.result,\n error: nodeResult.error,\n startTime: new Date(nodeResult.timestamp.getTime() - nodeResult.duration),\n endTime: nodeResult.timestamp,\n duration: nodeResult.duration\n });\n\n // Emit node completed/failed event\n emitStreamEvent({\n type: nodeResult.success ? 'node_completed' : 'node_failed',\n nodeId,\n nodeName: node.data.label,\n status: nodeResult.success ? 'completed' : 'failed',\n result: nodeResult.result,\n error: nodeResult.error,\n duration: nodeResult.duration\n });\n\n // If node failed, we might want to stop (depending on strategy)\n if (!nodeResult.success) {\n this.logger.error(`\u274C Workflow Node ${nodeId} failed: ${nodeResult.error}`);\n // For now, continue with other nodes - could add failure strategies later\n }\n }\n\n } catch (error: any) {\n this.logger.error(`\u274C Node ${nodeId} execution failed: ${error.message}`);\n this.updateNodeStatus(execution, nodeId, 'failed', {\n error: error.message,\n startTime: new Date(),\n endTime: new Date(),\n duration: 0\n });\n\n // Emit node failed event\n emitStreamEvent({\n type: 'node_failed',\n nodeId,\n nodeName: node.data.label,\n status: 'failed',\n error: error.message,\n duration: 0\n });\n }\n });\n\n // Wait for all parallel node executions to complete\n await Promise.all(nodeExecutionPromises);\n\n // Wait one second before next iteration to avoid tight loop, disabling for now, making stuff slow as hell if serving a backend!!\n // await new Promise(resolve => setTimeout(resolve, 1000));\n }\n\n // Determine final execution status\n const failedNodes = execution.nodeStatuses.filter(s => s.status === 'failed');\n const completedNodes = execution.nodeStatuses.filter(s => s.status === 'completed');\n const skippedNodes = execution.nodeStatuses.filter(s => s.status === 'skipped');\n const totalProcessed = completedNodes.length + skippedNodes.length;\n\n if (failedNodes.length > 0) {\n execution.status = 'failed';\n this.logger.log(`\u274C Workflow failed - ${failedNodes.length} nodes failed`);\n } else if (totalProcessed === workflow.nodes.length) {\n execution.status = 'completed';\n if (skippedNodes.length > 0) {\n this.logger.log(`\u2705 Workflow completed successfully - ${completedNodes.length} nodes executed, ${skippedNodes.length} skipped (flow control)`);\n } else {\n this.logger.log(`\u2705 Workflow completed successfully - all ${completedNodes.length} nodes executed`);\n }\n } else {\n execution.status = 'failed';\n this.logger.log(`\u26A0\uFE0F Workflow incomplete - ${totalProcessed}/${workflow.nodes.length} nodes processed (${completedNodes.length} completed, ${skippedNodes.length} skipped)`);\n }\n\n // Process workflow output if defined (support both 'output' and 'outputs' keys)\n const workflowOutput = workflow. output || (workflow as any).outputs;\n if (workflowOutput) {\n try {\n this.logger.log(`\\n\uD83D\uDCE4 Processing workflow output...`);\n execution.output = this.resolveParameters(workflowOutput, context);\n this.logger.log(` Output resolved successfully`);\n } catch (error: any) {\n this.logger.error(`\u26A0\uFE0F Failed to resolve workflow output: ${error.message}`);\n execution.output = { error: `Failed to resolve output: ${error.message}` };\n }\n }\n\n // Emit execution completed/failed event\n emitStreamEvent({\n type: execution.status === 'completed' ? 'execution_completed' : 'execution_failed',\n status: execution.status as any,\n output: execution.output\n });\n\n } catch (error: any) {\n this.logger.error(`\u274C Workflow execution failed: ${error.message}`);\n this.logger.error(error.stack);\n execution.status = 'failed';\n execution.results.push({\n nodeId: 'workflow',\n success: false,\n error: error.message,\n timestamp: new Date(),\n duration: 0,\n });\n\n // Emit execution failed event\n emitStreamEvent({\n type: 'execution_failed',\n status: 'failed',\n error: error.message\n });\n } finally {\n execution.endTime = new Date();\n execution.currentNode = undefined;\n this.logger.log(`\\n\u2705 Workflow execution completed: ${execution.status}`);\n }\n\n return execution;\n }\n\n /**\n * Find all webhook trigger nodes in the workflow\n */\n private findWebhookTriggers(nodes: WorkflowNode[]): WebhookTriggerInfo[] {\n return nodes\n .filter(node => this.isWebhookTriggerNode(node))\n .map(node => triggerHelper.getWebhookConfig(node));\n }\n\n /**\n * Check if a node is a webhook trigger\n */\n private isWebhookTriggerNode(node: WorkflowNode): boolean {\n return triggerHelper.isWebhookTrigger(node);\n }\n\n /**\n * Handle webhook trigger execution - waits for webhook to be received\n * Requires a webhookHandler to be passed (typically provided by the server layer)\n */\n private async handleWebhookTrigger(\n node: WorkflowNode,\n context: Record<string, any>,\n execution: WorkflowExecution,\n webhookHandler: IWebhookHandler,\n timeout?: number\n ): Promise<ExecutionResult> {\n const startTime = Date.now();\n const result: ExecutionResult = {\n nodeId: node.id,\n success: false,\n timestamp: new Date(),\n duration: 0,\n };\n\n try {\n const workflowId = execution.workflowId;\n this.logger.log(`\uD83D\uDD14 Waiting for webhook for workflow ${workflowId}, node ${node.id}`);\n\n // Wait for the webhook to be triggered (with workflow ID)\n const webhookPayload = await webhookHandler.waitForWebhook(node.id, timeout || 300000, workflowId);\n\n this.logger.log(`\u2705 Webhook received for workflow ${workflowId}, node ${node.id}`);\n\n // Execute the webhook trigger handler\n const triggerResult = await triggerHelper.executeWebhookTrigger(\n node.id,\n webhookPayload.payload,\n webhookPayload.headers,\n webhookPayload.query\n );\n\n if (triggerResult.success) {\n result.success = true;\n result.result = triggerResult.output?.[0] || webhookPayload;\n this.logger.log(`\u2705 Webhook trigger ${node.id} executed successfully`);\n } else {\n result.success = false;\n result.error = triggerResult.message || 'Webhook trigger execution failed';\n }\n\n } catch (error: any) {\n this.logger.error(`\u274C Webhook trigger ${node.id} failed: ${error.message}`);\n result.success = false;\n result.error = error.message;\n }\n\n result.duration = Date.now() - startTime;\n execution.results.push(result);\n\n return result;\n }\n\n /**\n * Build dependency map from workflow nodes and edges\n * Now includes detailed edge information for flow control\n */\n private buildDependencyMap(nodes: WorkflowNode[], edges: WorkflowEdge[]): Map<string, NodeDependencies> {\n const dependencyMap = new Map<string, NodeDependencies>();\n\n // Initialize dependency map for all nodes\n nodes.forEach(node => {\n dependencyMap.set(node.id, {\n nodeId: node.id,\n dependsOn: [],\n optionalDependsOn: [],\n dependencyFor: [],\n incomingEdges: [], // Track detailed edge info for flow control\n });\n });\n\n // Build dependency relationships from edges\n (edges || []).forEach(edge => {\n const sourceDeps = dependencyMap.get(edge.source);\n const targetDeps = dependencyMap.get(edge.target);\n\n if (sourceDeps && targetDeps) {\n // Target depends on source - check if optional\n if (edge.optional) {\n targetDeps.optionalDependsOn.push(edge.source);\n } else {\n targetDeps.dependsOn.push(edge.source);\n }\n // Source is a dependency for target\n sourceDeps.dependencyFor.push(edge.target);\n \n // Store detailed edge info for flow control\n targetDeps.incomingEdges!.push({\n sourceNodeId: edge.source,\n sourceHandle: edge.sourceHandle,\n targetHandle: edge.targetHandle,\n optional: edge.optional,\n });\n }\n });\n\n return dependencyMap;\n }\n\n /**\n * Check if there are any runnable nodes\n */\n private hasRunnableNodes(nodeStatuses: NodeExecutionStatus[], dependencies: Map<string, NodeDependencies>): boolean {\n return nodeStatuses.some(status =>\n status.status === 'pending' && this.areAllDependenciesSatisfied(status.nodeId, nodeStatuses, dependencies)\n );\n }\n\n /**\n * Find all nodes that can be executed (no pending dependencies)\n */\n private findRunnableNodes(nodeStatuses: NodeExecutionStatus[], dependencies: Map<string, NodeDependencies>): string[] {\n return nodeStatuses\n .filter(status =>\n status.status === 'pending' &&\n this.areAllDependenciesSatisfied(status.nodeId, nodeStatuses, dependencies)\n )\n .map(status => status.nodeId);\n }\n\n /**\n * Check if all dependencies for a node are satisfied (completed or skipped)\n * For required dependencies: ALL must be completed or skipped\n * For optional dependencies: ANY one being completed/skipped is sufficient (OR logic)\n * Note: 'skipped' nodes are treated as satisfied for dependency purposes\n */\n private areAllDependenciesSatisfied(nodeId: string, nodeStatuses: NodeExecutionStatus[], dependencies: Map<string, NodeDependencies>): boolean {\n const nodeDeps = dependencies.get(nodeId);\n if (!nodeDeps) {\n return true; // No dependencies info\n }\n \n const hasRequiredDeps = nodeDeps.dependsOn.length > 0;\n const hasOptionalDeps = nodeDeps.optionalDependsOn.length > 0;\n \n // Helper to check if a node status is \"done\" (completed or skipped)\n const isDone = (status: NodeExecutionStatus['status'] | undefined) => \n status === 'completed' || status === 'skipped';\n \n // If no dependencies at all, node can run\n if (!hasRequiredDeps) {\n return true;\n }\n\n // Check required dependencies - ALL must be completed or skipped\n const allRequiredSatisfied = nodeDeps.dependsOn.every(depNodeId => {\n const depStatus = nodeStatuses.find(s => s.nodeId === depNodeId);\n return isDone(depStatus?.status);\n });\n\n // If has required deps and they're not all satisfied, can't run\n if (hasRequiredDeps && !allRequiredSatisfied) {\n return false;\n }\n\n // Check optional dependencies - ANY one being completed/skipped is sufficient\n if (hasOptionalDeps) {\n const anyOptionalSatisfied = nodeDeps.optionalDependsOn.some(depNodeId => {\n const depStatus = nodeStatuses.find(s => s.nodeId === depNodeId);\n return isDone(depStatus?.status);\n });\n \n // If only optional deps exist, need at least one satisfied\n if (!hasRequiredDeps) {\n return anyOptionalSatisfied;\n }\n // If both required and optional exist, required must all be done, \n // and at least one optional must be done\n return allRequiredSatisfied && anyOptionalSatisfied;\n }\n\n // Only required deps, and they're all satisfied\n return allRequiredSatisfied;\n }\n\n /**\n * Check if a node should be skipped due to flow control from upstream nodes.\n * Flow control nodes (like bit-if) can specify which branches are activated.\n * Nodes connected via non-activated branches should be skipped.\n * \n * @returns 'execute' if the node should execute, 'skip' if it should be skipped\n */\n private checkFlowControl(\n nodeId: string,\n dependencies: Map<string, NodeDependencies>,\n context: Record<string, any>\n ): 'execute' | 'skip' {\n const nodeDeps = dependencies.get(nodeId);\n if (!nodeDeps || !nodeDeps.incomingEdges?.length) {\n return 'execute'; // No incoming edges, execute normally\n }\n\n // Check each incoming edge for flow control\n for (const edge of nodeDeps.incomingEdges) {\n const sourceResult = context[edge.sourceNodeId];\n if (!sourceResult) {\n continue; // Source hasn't executed yet or has no result\n }\n\n // Check if the source node returned flow control metadata\n // Can be in _flowControl field or directly in the result\n const flowControl: FlowControlMetadata | undefined = \n sourceResult._flowControl || \n (sourceResult.controlsFlow ? sourceResult : undefined);\n\n if (!flowControl?.controlsFlow) {\n continue; // Source doesn't control flow\n }\n\n // Source controls flow - check if this edge's sourceHandle is activated\n const { activeBranches, skipBranches } = flowControl;\n const edgeHandle = edge.sourceHandle || 'default';\n\n if (activeBranches && activeBranches.length > 0) {\n // If activeBranches is specified, only those branches execute\n if (!activeBranches.includes(edgeHandle)) {\n this.logger.log(`\u23ED\uFE0F Skipping node ${nodeId}: branch \"${edgeHandle}\" not in activeBranches [${activeBranches.join(', ')}]`);\n return 'skip';\n }\n } else if (skipBranches && skipBranches.length > 0) {\n // If skipBranches is specified, those branches are skipped\n if (skipBranches.includes(edgeHandle)) {\n this.logger.log(`\u23ED\uFE0F Skipping node ${nodeId}: branch \"${edgeHandle}\" in skipBranches [${skipBranches.join(', ')}]`);\n return 'skip';\n }\n }\n }\n\n return 'execute';\n }\n\n /**\n * Update node execution status\n */\n private updateNodeStatus(\n execution: WorkflowExecution,\n nodeId: string,\n status: NodeExecutionStatus['status'],\n additionalData?: Partial<NodeExecutionStatus>\n ): void {\n const nodeStatus = execution.nodeStatuses.find(s => s.nodeId === nodeId);\n if (nodeStatus) {\n nodeStatus.status = status;\n if (additionalData) {\n Object.assign(nodeStatus, additionalData);\n }\n }\n }\n\n /**\n * Execute a single workflow node\n */\n private async executeNode(\n node: WorkflowNode,\n context: Record<string, any>,\n execution: WorkflowExecution\n ): Promise<ExecutionResult> {\n const startTime = Date.now();\n const result: ExecutionResult = {\n nodeId: node.id,\n success: false,\n timestamp: new Date(),\n duration: 0,\n };\n let fullParams;\n try {\n \n // Resolve dynamic parameters using context\n const resolvedParams = this.resolveParameters(node.data.params || {}, context);\n // Resolve credentials as well (they may contain {{process.env.XXX}} templates)\n const resolvedCredentials = node.data.credentials\n ? this.resolveParameters(node.data.credentials, context)\n : undefined;\n\n \n // Add additional node data to params\n fullParams = {\n ...resolvedParams,\n ...(node.data.resource && { resource: node.data.resource }),\n ...(node.data.operation && { operation: node.data.operation }),\n ...(resolvedCredentials && { credentials: resolvedCredentials })\n };\n\n // Execute based on framework\n let nodeResult: any;\n switch (node.data.framework) {\n case 'activepieces':\n if (triggerHelper.isActivepiecesTrigger(node)) {\n const triggerResult = await triggerHelper.executeActivepiecesTrigger({\n moduleDefinition: {\n framework: node.data.framework,\n source: (node.data.source as 'github' | 'npm') || 'npm',\n repository: node.data.module || 'unknown',\n },\n triggerName: node.data.operation || 'unknown',\n input: fullParams,\n payload: context.triggerPayload || context.webhookPayload || {},\n webhookUrl: context.webhookUrl,\n });\n\n if (!triggerResult.success) {\n throw new Error(triggerResult.message || 'Trigger execution failed');\n }\n nodeResult = triggerResult.output;\n } else {\n // Regular action execution\n const output = await executeActivepiecesModule({ source: node.data.source!, framework: node.data.framework, moduleName: node.data.module || 'unknown', params: fullParams });\n nodeResult = output.result;\n }\n break;\n case 'n8n':\n // Pass full execution params including source\n nodeResult = await executeN8nModule({\n framework: 'n8n',\n source: node.data.source || 'npm',\n moduleName: node.data.module || 'unknown',\n params: fullParams\n });\n break;\n case 'script':\n nodeResult = await executeScriptModule({\n framework: 'script',\n source: (node.data.source as 'local' | 'hub' | 'inline') || 'local',\n moduleName: node.data.module || 'unknown',\n params: fullParams,\n script: {\n type: fullParams.type || 'script',\n language: fullParams.language || 'deno',\n content: fullParams.script,\n },\n });\n break;\n case 'bits':\n // Bits framework - independent of activepieces dependencies\n if (bitsTriggerHelper.isBitsTrigger(node)) {\n const triggerResult = await bitsTriggerHelper.executeBitsTrigger({\n moduleDefinition: {\n framework: node.data.framework,\n source: (node.data.source as 'github' | 'npm') || 'npm',\n repository: node.data.module || 'unknown',\n },\n triggerName: node.data.operation || 'unknown',\n input: fullParams,\n payload: context.triggerPayload || context.webhookPayload || {},\n webhookUrl: context.webhookUrl,\n });\n\n if (!triggerResult.success) {\n throw new Error(triggerResult.message || 'Trigger execution failed');\n }\n nodeResult = triggerResult.output;\n } else {\n // Regular action execution\n const output = await executeBitsModule({\n source: node.data.source!,\n framework: node.data.framework,\n moduleName: node.data.module || 'unknown',\n params: fullParams,\n logger: this.logger,\n workflowId: execution.workflowId,\n nodeId: node.id,\n executionId: execution.id,\n });\n nodeResult = output.result;\n }\n break;\n default:\n throw new Error(`Unsupported framework: ${node.data.framework}`);\n }\n\n result.success = true;\n result.result = nodeResult;\n\n this.logger.info(`Node ${node.id} executed successfully`);\n\n } catch (error: any) {\n this.logger.error(`Node ${node.id} failed`, { \n error: error.message, \n inputs: fullParams \n });\n result.success = false;\n result.error = error.message;\n }\n\n result.duration = Date.now() - startTime;\n execution.results.push(result);\n\n return result;\n }\n\n\n\n /**\n * Resolve dynamic parameters using context\n */\n private resolveParameters(params: Record<string, any>, context: Record<string, any>): Record<string, any> {\n const resolved: Record<string, any> = {};\n\n for (const [key, value] of Object.entries(params)) {\n if (typeof value === 'string' && value.startsWith('{{') && value.endsWith('}}')) {\n // Template variable like {{previous_result.id}}\n const expression = value.slice(2, -2).trim();\n resolved[key] = this.evaluateExpression(expression, context);\n } else if (typeof value === 'string' && value.includes('{{') && value.includes('}}')) {\n // Handle mixed templates like \"{{step_abc.value}}_suffix\"\n // If an object, serialize it\n let resolvedString = value;\n const templateRegex = /\\{\\{([^}]+)\\}\\}/g;\n let match;\n while ((match = templateRegex.exec(value)) !== null) {\n const expression = match[1].trim();\n const evaluatedValue = this.evaluateExpression(expression, context);\n if (typeof evaluatedValue === 'object') {\n // If the evaluated value is an object, serialize it to JSON\n this.logger.warn(`\u26A0\uFE0F Evaluated value for expression \"${expression}\" is an object, serializing to JSON string`);\n resolvedString = resolvedString.replace(match[0], JSON.stringify(evaluatedValue));\n continue;\n }\n resolvedString = resolvedString.replace(match[0], String(evaluatedValue));\n }\n resolved[key] = resolvedString;\n } else if (typeof value === 'object' && value !== null && !Array.isArray(value)) {\n resolved[key] = this.resolveParameters(value, context);\n } else if (Array.isArray(value)) {\n resolved[key] = value.map(item => {\n if (typeof item === 'string' && item.startsWith('{{') && item.endsWith('}}')) {\n // Template variable in array\n const expression = item.slice(2, -2).trim();\n return this.evaluateExpression(expression, context);\n } else if (typeof item === 'string' && item.includes('{{') && item.includes('}}')) {\n // Mixed template in array\n let resolvedString = item;\n const templateRegex = /\\{\\{([^}]+)\\}\\}/g;\n let match;\n while ((match = templateRegex.exec(item)) !== null) {\n const expression = match[1].trim();\n const evaluatedValue = this.evaluateExpression(expression, context);\n resolvedString = resolvedString.replace(match[0], String(evaluatedValue));\n }\n return resolvedString;\n } else if (typeof item === 'object' && item !== null) {\n return this.resolveParameters(item, context);\n }\n return item;\n });\n } else {\n resolved[key] = value;\n }\n }\n\n return resolved;\n }\n\n /**\n * Evaluate a JavaScript expression in the given context\n */\n private evaluateExpression(expression: string, context: Record<string, any>): any {\n try {\n\n // Handle habits.env. variables (special case for environment variables)\n // Allow access to any environment variable via habits.env.VAR_NAME\n if (expression.startsWith('habits.env.')) {\n // Strip 'habits.env.' prefix to get the actual env var name\n const envVar = expression.slice('habits.env.'.length);\n // Check this.env first (platform-agnostic), fall back to process.env for Node.js\n const value = this.env[envVar] ?? (typeof process !== 'undefined' ? process.env?.[envVar] : undefined);\n if (value === undefined) {\n this.logger.warn(`\u26A0\uFE0F Environment variable ${envVar} is not set`);\n }\n return value || '';\n }\n\n // Handle habits.function.* - utility functions\n if (expression.startsWith('habits.function.')) {\n const funcCall = expression.slice('habits.function.'.length);\n return this.evaluateHabitsFunction(funcCall);\n }\n\n // Handle habits.context.* - workflow execution context\n if (expression.startsWith('habits.context.')) {\n const contextKey = expression.slice('habits.context.'.length);\n const habitsContext = context.habits?.context || {};\n if (contextKey in habitsContext) {\n return habitsContext[contextKey];\n }\n this.logger.warn(`\u26A0\uFE0F Context key '${contextKey}' not found`);\n return '';\n }\n\n // Handle habits.header.* - HTTP request headers (alias for habits.headers.*)\n if (expression.startsWith('habits.header.')) {\n const headerName = expression.slice('habits.header.'.length).toLowerCase();\n const headers = context.habits?.headers || {};\n // Headers are case-insensitive, find the matching header\n for (const [key, value] of Object.entries(headers)) {\n if (key.toLowerCase() === headerName) {\n return value;\n }\n }\n this.logger.warn(`\u26A0\uFE0F Header '${headerName}' not found`);\n return '';\n }\n\n // Handle simple property access like habits.input.userId or step_abc.value\n // Also supports array indexing like result[0].base64\n if (expression.includes('.') || expression.includes('[')) {\n // Parse the expression to handle both dot notation and array indexing\n // e.g., \"text-to-speech.result[0].base64\" -> [\"text-to-speech\", \"result\", \"0\", \"base64\"]\n const parts: string[] = [];\n let current = '';\n let i = 0;\n while (i < expression.length) {\n const char = expression[i];\n if (char === '.') {\n if (current) parts.push(current);\n current = '';\n } else if (char === '[') {\n if (current) parts.push(current);\n current = '';\n // Find the closing bracket\n i++;\n while (i < expression.length && expression[i] !== ']') {\n current += expression[i];\n i++;\n }\n if (current) parts.push(current);\n current = '';\n } else {\n current += char;\n }\n i++;\n }\n if (current) parts.push(current);\n\n let result = context;\n for (const part of parts) {\n // Handle numeric indices for arrays\n const index = /^\\d+$/.test(part) ? parseInt(part, 10) : part;\n\n if (result && typeof result === 'object' && (Array.isArray(result) ? index in result : part in result)) {\n result = (result as any)[index];\n } else {\n throw new Error(`Property ${part} not found`);\n }\n }\n return result;\n }\n\n // Handle direct context access\n if (expression in context) {\n return context[expression];\n }\n\n // Fallback to Function evaluation\n const func = new Function(...Object.keys(context), `return ${expression}`);\n return func(...Object.values(context));\n } catch (error: any) {\n this.logger.warn(`\u26A0\uFE0F Failed to evaluate expression: ${expression} - ${error.message}`);\n return expression; // Return original if evaluation fails\n }\n }\n\n /**\n * Evaluate a condition expression\n */\n private evaluateCondition(condition: string, context: Record<string, any>): boolean {\n try {\n return Boolean(this.evaluateExpression(condition, context));\n } catch {\n return false;\n }\n }\n\n // TODO: Allow functions to use context and node outputs\n // TODO: Implement a way to register custom functions that can be used in habits.function.* expressions, with access to context and other utilities\n /**\n * Evaluate habits.function.* utility functions\n * Supported functions:\n * - date() - Returns current date in ISO format\n * - now() - Alias for date()\n * - timestamp() - Returns Unix timestamp in milliseconds\n * - uuid() - Generates a random UUID\n * - random(min, max) - Generates random number in range\n * - stringify(value) - Converts value to JSON string (value should be context path)\n */\n private evaluateHabitsFunction(funcCall: string): any {\n // Parse function name and arguments\n const funcMatch = funcCall.match(/^(\\w+)\\((.*)\\)$/);\n if (!funcMatch) {\n this.logger.warn(`\u26A0\uFE0F Invalid function call: ${funcCall}`);\n return '';\n }\n\n const [, funcName, argsStr] = funcMatch;\n const args = argsStr ? argsStr.split(',').map(a => a.trim()) : [];\n\n switch (funcName) {\n case 'date':\n case 'now':\n return new Date().toISOString();\n\n case 'timestamp':\n return Date.now();\n\n case 'uuid':\n return uuidv4();\n\n case 'random': {\n const min = args[0] ? parseFloat(args[0]) : 0;\n const max = args[1] ? parseFloat(args[1]) : 1;\n return Math.random() * (max - min) + min;\n }\n\n case 'randomInt': {\n const min = args[0] ? parseInt(args[0], 10) : 0;\n const max = args[1] ? parseInt(args[1], 10) : 100;\n return Math.floor(Math.random() * (max - min + 1)) + min;\n }\n\n case 'stringify':\n // For stringify, the arg should be a value in context, but without context here\n // we'll just return the stringified arg itself\n if (args[0]) {\n try {\n return JSON.stringify(args[0]);\n } catch {\n return String(args[0]);\n }\n }\n return '';\n\n default:\n this.logger.warn(`\u26A0\uFE0F Unknown function: ${funcName}`);\n return '';\n }\n }\n\n /**\n * Get execution status\n */\n getExecution(executionId: string): WorkflowExecution | undefined {\n return this.executions.get(executionId);\n }\n\n /**\n * List all executions\n */\n listExecutions(): WorkflowExecution[] {\n return Array.from(this.executions.values());\n }\n\n /**\n * Cancel a running execution\n */\n cancelExecution(executionId: string): boolean {\n const execution = this.executions.get(executionId);\n if (execution && execution.status === 'running') {\n execution.status = 'cancelled';\n execution.endTime = new Date();\n return true;\n }\n return false;\n }\n}\n", "/**\n * Runtime detection for platform bindings\n * \n * Detects whether we're running in a Tauri environment or Node.js\n */\n\ndeclare global {\n interface Window {\n __TAURI__?: {\n convertFileSrc?: (path: string) => string;\n [key: string]: unknown;\n };\n __TAURI_INTERNALS__?: unknown;\n }\n}\n\n/**\n * Check if we're running in a Tauri environment\n * \n * Detection strategy:\n * 1. Check for window.__TAURI__ object (Tauri v2)\n * 2. Check for window.__TAURI_INTERNALS__ (Tauri v2 internals)\n * \n * @returns true if running in Tauri, false if in Node.js or browser without Tauri\n */\nexport function isTauri(): boolean {\n // Check if we're in a browser environment\n if (typeof window === 'undefined') {\n return false;\n }\n \n // Check for Tauri v2 indicators\n return !!(window.__TAURI__ || window.__TAURI_INTERNALS__);\n}\n\n/**\n * Check if we're running in Node.js\n * \n * @returns true if running in Node.js environment\n */\nexport function isNode(): boolean {\n return typeof process !== 'undefined' && \n process.versions != null && \n process.versions.node != null;\n}\n\n/**\n * Check if we're running in a browser (without Tauri)\n * \n * @returns true if running in browser without Tauri\n */\nexport function isBrowser(): boolean {\n return typeof window !== 'undefined' && !isTauri();\n}\n\n/**\n * Get the current runtime environment\n * \n * @returns 'tauri' | 'node' | 'browser'\n */\nexport function getRuntime(): 'tauri' | 'node' | 'browser' {\n if (isTauri()) {\n return 'tauri';\n }\n if (isNode()) {\n return 'node';\n }\n return 'browser';\n}\n\n/**\n * Assert that we're running in a supported environment for the given feature\n * \n * @param feature - Name of the feature requiring this check\n * @param supportedRuntimes - List of supported runtimes\n * @throws Error if current runtime is not supported\n */\nexport function assertRuntime(feature: string, supportedRuntimes: ('tauri' | 'node' | 'browser')[]): void {\n const runtime = getRuntime();\n if (!supportedRuntimes.includes(runtime)) {\n throw new Error(\n `${feature} is not supported in ${runtime} environment. ` +\n `Supported environments: ${supportedRuntimes.join(', ')}`\n );\n }\n}\n", "/**\n * Filesystem binding\n * \n * Provides cross-platform filesystem operations that work in both Node.js and Tauri.\n * In Node.js, delegates to the native 'fs' module.\n * In Tauri, uses @tauri-apps/plugin-fs.\n */\n\nimport { isTauri, isNode, assertRuntime } from './runtime';\n\n// Types for Tauri fs plugin\ntype TauriFsModule = typeof import('@tauri-apps/plugin-fs');\n\n// Conditionally import modules\nlet nodeFs: typeof import('fs') | null = null;\nlet tauriFs: TauriFsModule | null = null;\n\n// Initialize Node.js fs if available\nif (isNode()) {\n // eslint-disable-next-line @typescript-eslint/no-var-requires\n nodeFs = require('fs');\n}\n\n/**\n * Lazily load Tauri fs module\n */\nasync function getTauriFs(): Promise<TauriFsModule> {\n if (!tauriFs) {\n tauriFs = await import('@tauri-apps/plugin-fs');\n }\n return tauriFs;\n}\n\n// ============================================================================\n// Async Operations\n// ============================================================================\n\n/**\n * Read a file as text\n * \n * @param path - Path to the file\n * @param encoding - Text encoding (default: 'utf-8')\n * @returns File contents as string\n */\nexport async function readFile(path: string, encoding: BufferEncoding = 'utf-8'): Promise<string> {\n if (isTauri()) {\n const fs = await getTauriFs();\n return await fs.readTextFile(path);\n }\n \n if (nodeFs) {\n return nodeFs.promises.readFile(path, { encoding });\n }\n \n throw new Error('readFile is not supported in this environment');\n}\n\n/**\n * Read a file as binary data\n * \n * @param path - Path to the file\n * @returns File contents as Uint8Array\n */\nexport async function readBinaryFile(path: string): Promise<Uint8Array> {\n if (isTauri()) {\n const fs = await getTauriFs();\n return await fs.readFile(path);\n }\n \n if (nodeFs) {\n const buffer = await nodeFs.promises.readFile(path);\n return new Uint8Array(buffer);\n }\n \n throw new Error('readBinaryFile is not supported in this environment');\n}\n\n/**\n * Write text to a file\n * \n * @param path - Path to the file\n * @param contents - Text content to write\n */\nexport async function writeFile(path: string, contents: string): Promise<void> {\n if (isTauri()) {\n const fs = await getTauriFs();\n await fs.writeTextFile(path, contents);\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.writeFile(path, contents, 'utf-8');\n return;\n }\n \n throw new Error('writeFile is not supported in this environment');\n}\n\n/**\n * Write binary data to a file\n * \n * @param path - Path to the file\n * @param contents - Binary content to write\n */\nexport async function writeBinaryFile(path: string, contents: Uint8Array): Promise<void> {\n if (isTauri()) {\n const fs = await getTauriFs();\n await fs.writeFile(path, contents);\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.writeFile(path, Buffer.from(contents));\n return;\n }\n \n throw new Error('writeBinaryFile is not supported in this environment');\n}\n\n/**\n * Check if a file or directory exists\n * \n * @param path - Path to check\n * @returns true if the path exists\n */\nexport async function exists(path: string): Promise<boolean> {\n if (isTauri()) {\n const fs = await getTauriFs();\n return await fs.exists(path);\n }\n \n if (nodeFs) {\n try {\n await nodeFs.promises.access(path);\n return true;\n } catch {\n return false;\n }\n }\n \n throw new Error('exists is not supported in this environment');\n}\n\n/**\n * Create a directory\n * \n * @param path - Path to create\n * @param options - Options for directory creation\n */\nexport async function mkdir(path: string, options?: { recursive?: boolean }): Promise<void> {\n if (isTauri()) {\n const fs = await getTauriFs();\n await fs.mkdir(path, { recursive: options?.recursive });\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.mkdir(path, { recursive: options?.recursive });\n return;\n }\n \n throw new Error('mkdir is not supported in this environment');\n}\n\n/**\n * Remove a file\n * \n * @param path - Path to remove\n */\nexport async function remove(path: string): Promise<void> {\n if (isTauri()) {\n const fs = await getTauriFs();\n await fs.remove(path);\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.unlink(path);\n return;\n }\n \n throw new Error('remove is not supported in this environment');\n}\n\n/**\n * Remove a directory\n * \n * @param path - Path to remove\n * @param options - Options for removal\n */\nexport async function rmdir(path: string, options?: { recursive?: boolean }): Promise<void> {\n if (isTauri()) {\n const fs = await getTauriFs();\n await fs.remove(path, { recursive: options?.recursive });\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.rm(path, { recursive: options?.recursive });\n return;\n }\n \n throw new Error('rmdir is not supported in this environment');\n}\n\n/**\n * Directory entry info\n */\nexport interface DirEntry {\n name: string;\n isDirectory: boolean;\n isFile: boolean;\n isSymlink: boolean;\n}\n\n/**\n * Read a directory\n * \n * @param path - Path to read\n * @returns Array of directory entries\n */\nexport async function readDir(path: string): Promise<DirEntry[]> {\n if (isTauri()) {\n const fs = await getTauriFs();\n const entries = await fs.readDir(path);\n return entries.map(entry => ({\n name: entry.name,\n isDirectory: entry.isDirectory,\n isFile: entry.isFile,\n isSymlink: entry.isSymlink,\n }));\n }\n \n if (nodeFs) {\n const entries = await nodeFs.promises.readdir(path, { withFileTypes: true });\n return entries.map(entry => ({\n name: entry.name,\n isDirectory: entry.isDirectory(),\n isFile: entry.isFile(),\n isSymlink: entry.isSymbolicLink(),\n }));\n }\n \n throw new Error('readDir is not supported in this environment');\n}\n\n/**\n * Copy a file\n * \n * @param src - Source path\n * @param dest - Destination path\n */\nexport async function copyFile(src: string, dest: string): Promise<void> {\n if (isTauri()) {\n const fs = await getTauriFs();\n await fs.copyFile(src, dest);\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.copyFile(src, dest);\n return;\n }\n \n throw new Error('copyFile is not supported in this environment');\n}\n\n/**\n * Rename/move a file or directory\n * \n * @param oldPath - Current path\n * @param newPath - New path\n */\nexport async function rename(oldPath: string, newPath: string): Promise<void> {\n if (isTauri()) {\n const fs = await getTauriFs();\n await fs.rename(oldPath, newPath);\n return;\n }\n \n if (nodeFs) {\n await nodeFs.promises.rename(oldPath, newPath);\n return;\n }\n \n throw new Error('rename is not supported in this environment');\n}\n\n/**\n * File/directory stats (Node.js-compatible interface with methods)\n */\nexport interface FileStats {\n /** Check if this is a regular file */\n isFile(): boolean;\n /** Check if this is a directory */\n isDirectory(): boolean;\n /** Check if this is a symbolic link */\n isSymbolicLink(): boolean;\n /** File size in bytes */\n size: number;\n /** Last modified time */\n mtime: Date | null;\n /** Last accessed time */\n atime: Date | null;\n /** Creation time */\n ctime: Date | null;\n}\n\n/**\n * Create a FileStats object with methods\n */\nfunction createFileStats(data: {\n isFile: boolean;\n isDirectory: boolean;\n isSymlink: boolean;\n size: number;\n mtime: Date | null;\n atime: Date | null;\n ctime: Date | null;\n}): FileStats {\n return {\n isFile: () => data.isFile,\n isDirectory: () => data.isDirectory,\n isSymbolicLink: () => data.isSymlink,\n size: data.size,\n mtime: data.mtime,\n atime: data.atime,\n ctime: data.ctime,\n };\n}\n\n/**\n * Get file/directory stats\n * \n * @param path - Path to stat\n * @returns File stats\n */\nexport async function stat(path: string): Promise<FileStats> {\n if (isTauri()) {\n const fs = await getTauriFs();\n const stats = await fs.stat(path);\n return createFileStats({\n isFile: stats.isFile,\n isDirectory: stats.isDirectory,\n isSymlink: stats.isSymlink,\n size: stats.size,\n mtime: stats.mtime ? new Date(stats.mtime) : null,\n atime: stats.atime ? new Date(stats.atime) : null,\n ctime: null, // Tauri doesn't provide ctime\n });\n }\n \n if (nodeFs) {\n const stats = await nodeFs.promises.stat(path);\n return createFileStats({\n isFile: stats.isFile(),\n isDirectory: stats.isDirectory(),\n isSymlink: stats.isSymbolicLink(),\n size: stats.size,\n mtime: stats.mtime,\n atime: stats.atime,\n ctime: stats.ctime,\n });\n }\n \n throw new Error('stat is not supported in this environment');\n}\n\n// ============================================================================\n// Sync Operations (Node.js only)\n// ============================================================================\n\n/**\n * Read a file synchronously (Node.js only)\n * \n * @param path - Path to the file\n * @param encoding - Text encoding (default: 'utf-8')\n * @returns File contents as string\n */\nexport function readFileSync(path: string, encoding: BufferEncoding = 'utf-8'): string {\n assertRuntime('readFileSync', ['node']);\n \n if (nodeFs) {\n return nodeFs.readFileSync(path, { encoding });\n }\n \n throw new Error('readFileSync is not supported in this environment');\n}\n\n/**\n * Write a file synchronously (Node.js only)\n * \n * @param path - Path to the file\n * @param contents - Text content to write\n * @param encoding - Text encoding (default: 'utf-8')\n */\nexport function writeFileSync(path: string, contents: string, encoding: BufferEncoding = 'utf-8'): void {\n assertRuntime('writeFileSync', ['node']);\n \n if (nodeFs) {\n nodeFs.writeFileSync(path, contents, encoding);\n return;\n }\n \n throw new Error('writeFileSync is not supported in this environment');\n}\n\n/**\n * Check if a file or directory exists synchronously (Node.js only)\n * \n * @param path - Path to check\n * @returns true if the path exists\n */\nexport function existsSync(path: string): boolean {\n assertRuntime('existsSync', ['node']);\n \n if (nodeFs) {\n return nodeFs.existsSync(path);\n }\n \n return false;\n}\n\n/**\n * Create a directory synchronously (Node.js only)\n * \n * @param path - Path to create\n * @param options - Options for directory creation\n */\nexport function mkdirSync(path: string, options?: { recursive?: boolean }): void {\n assertRuntime('mkdirSync', ['node']);\n \n if (nodeFs) {\n nodeFs.mkdirSync(path, { recursive: options?.recursive });\n return;\n }\n \n throw new Error('mkdirSync is not supported in this environment');\n}\n\n/**\n * Directory entry with file type methods (for Node.js compatibility)\n */\nexport interface DirentLike {\n name: string;\n isDirectory(): boolean;\n isFile(): boolean;\n isSymbolicLink(): boolean;\n}\n\n/**\n * Read directory synchronously (Node.js only) - returns string[]\n */\nexport function readdirSync(path: string): string[];\n/**\n * Read directory synchronously (Node.js only) - returns DirentLike[] when withFileTypes is true\n */\nexport function readdirSync(path: string, options: { withFileTypes: true }): DirentLike[];\n/**\n * Read directory synchronously (Node.js only) - returns string[] when withFileTypes is false/undefined\n */\nexport function readdirSync(path: string, options: { withFileTypes?: false }): string[];\n/**\n * Read directory synchronously (Node.js only)\n * \n * @param path - Path to read\n * @param options - Options (withFileTypes returns Dirent-like objects)\n * @returns Array of file names or Dirent-like objects\n */\nexport function readdirSync(path: string, options?: { withFileTypes?: boolean }): string[] | DirentLike[] {\n assertRuntime('readdirSync', ['node']);\n \n if (nodeFs) {\n if (options?.withFileTypes) {\n const entries = nodeFs.readdirSync(path, { withFileTypes: true });\n return entries.map(entry => ({\n name: entry.name,\n isDirectory: () => entry.isDirectory(),\n isFile: () => entry.isFile(),\n isSymbolicLink: () => entry.isSymbolicLink(),\n }));\n }\n return nodeFs.readdirSync(path);\n }\n \n throw new Error('readdirSync is not supported in this environment');\n}\n\n/**\n * Copy a file or directory synchronously (Node.js only)\n * \n * @param src - Source path\n * @param dest - Destination path\n * @param options - Copy options\n */\nexport function cpSync(src: string, dest: string, options?: { recursive?: boolean }): void {\n assertRuntime('cpSync', ['node']);\n \n if (nodeFs && typeof (nodeFs as any).cpSync === 'function') {\n (nodeFs as any).cpSync(src, dest, options);\n return;\n }\n \n throw new Error('cpSync is not supported in this environment (requires Node.js 16.7+)');\n}\n\n/**\n * Remove a file or directory synchronously (Node.js only)\n * \n * @param path - Path to remove\n * @param options - Removal options\n */\nexport function rmSync(path: string, options?: { recursive?: boolean; force?: boolean }): void {\n assertRuntime('rmSync', ['node']);\n \n if (nodeFs && typeof (nodeFs as any).rmSync === 'function') {\n (nodeFs as any).rmSync(path, options);\n return;\n }\n \n throw new Error('rmSync is not supported in this environment (requires Node.js 14.14+)');\n}\n\n/**\n * Create a symbolic link synchronously (Node.js only)\n * \n * @param target - Path the symlink points to\n * @param path - Path of the symlink itself\n * @param type - Type of symlink ('file', 'dir', or 'junction' on Windows)\n */\nexport function symlinkSync(target: string, path: string, type?: 'file' | 'dir' | 'junction'): void {\n assertRuntime('symlinkSync', ['node']);\n \n if (nodeFs) {\n nodeFs.symlinkSync(target, path, type);\n return;\n }\n \n throw new Error('symlinkSync is not supported in this environment');\n}\n\n/**\n * Get file stats synchronously without following symlinks (Node.js only)\n * \n * @param path - Path to stat\n * @returns File stats (isSymbolicLink() will return true for symlinks)\n */\nexport function lstatSync(path: string): FileStats {\n assertRuntime('lstatSync', ['node']);\n \n if (nodeFs) {\n const stats = nodeFs.lstatSync(path);\n return createFileStats({\n isFile: stats.isFile(),\n isDirectory: stats.isDirectory(),\n isSymlink: stats.isSymbolicLink(),\n size: stats.size,\n mtime: stats.mtime,\n atime: stats.atime,\n ctime: stats.ctime,\n });\n }\n \n throw new Error('lstatSync is not supported in this environment');\n}\n\n/**\n * Read the target of a symbolic link synchronously (Node.js only)\n * \n * @param path - Path of the symlink\n * @returns The path the symlink points to\n */\nexport function readlinkSync(path: string): string {\n assertRuntime('readlinkSync', ['node']);\n \n if (nodeFs) {\n return nodeFs.readlinkSync(path, 'utf-8');\n }\n \n throw new Error('readlinkSync is not supported in this environment');\n}\n\n/**\n * Get file stats synchronously (Node.js only)\n * \n * @param path - Path to stat\n * @returns File stats\n */\nexport function statSync(path: string): FileStats {\n assertRuntime('statSync', ['node']);\n \n if (nodeFs) {\n const stats = nodeFs.statSync(path);\n return createFileStats({\n isFile: stats.isFile(),\n isDirectory: stats.isDirectory(),\n isSymlink: stats.isSymbolicLink(),\n size: stats.size,\n mtime: stats.mtime,\n atime: stats.atime,\n ctime: stats.ctime,\n });\n }\n \n throw new Error('statSync is not supported in this environment');\n}\n\n// Default export\nexport default {\n readFile,\n readBinaryFile,\n writeFile,\n writeBinaryFile,\n exists,\n mkdir,\n remove,\n rmdir,\n readDir,\n copyFile,\n rename,\n stat,\n readFileSync,\n writeFileSync,\n existsSync,\n mkdirSync,\n readdirSync,\n cpSync,\n rmSync,\n symlinkSync,\n readlinkSync,\n lstatSync,\n statSync,\n};\n", "/**\n * Path utilities binding\n * \n * Provides cross-platform path manipulation that works in both Node.js and Tauri/browser.\n * In Node.js, delegates to the native 'path' module.\n * In Tauri/browser, provides a pure JavaScript implementation.\n */\n\nimport { isNode } from './runtime';\n\n// Conditionally import Node.js path module\nlet nodePath: typeof import('path') | null = null;\n\nif (isNode()) {\n // Dynamic import for Node.js environment\n // eslint-disable-next-line @typescript-eslint/no-var-requires\n nodePath = require('path');\n}\n\n/**\n * Platform-specific path separator\n */\nexport const sep = isNode() && nodePath ? nodePath.sep : '/';\n\n/**\n * Platform-specific path delimiter (for PATH environment variable)\n */\nexport const delimiter = isNode() && nodePath ? nodePath.delimiter : ':';\n\n/**\n * Join path segments together\n * \n * @param segments - Path segments to join\n * @returns Joined path\n */\nexport function join(...segments: string[]): string {\n if (nodePath) {\n return nodePath.join(...segments);\n }\n \n // Browser/Tauri implementation\n const parts: string[] = [];\n \n for (const segment of segments) {\n if (!segment) continue;\n \n // Split by both / and \\\n const segmentParts = segment.split(/[/\\\\]+/);\n \n for (const part of segmentParts) {\n if (part === '..') {\n parts.pop();\n } else if (part !== '.' && part !== '') {\n parts.push(part);\n }\n }\n }\n \n // Preserve leading slash if first segment had one\n const firstSegment = segments.find(s => s);\n const leadingSlash = firstSegment && firstSegment.startsWith('/') ? '/' : '';\n \n return leadingSlash + parts.join('/');\n}\n\n/**\n * Resolve path segments to an absolute path\n * \n * @param segments - Path segments to resolve\n * @returns Absolute path\n */\nexport function resolve(...segments: string[]): string {\n if (nodePath) {\n return nodePath.resolve(...segments);\n }\n \n // Browser/Tauri implementation - use join and ensure absolute\n let resolvedPath = join(...segments);\n \n // If not absolute, we can't really resolve in browser\n // Return as-is (would need cwd from process binding)\n if (!resolvedPath.startsWith('/')) {\n resolvedPath = '/' + resolvedPath;\n }\n \n return resolvedPath;\n}\n\n/**\n * Get the directory name of a path\n * \n * @param p - Path to get directory from\n * @returns Directory portion of the path\n */\nexport function dirname(p: string): string {\n if (nodePath) {\n return nodePath.dirname(p);\n }\n \n // Browser/Tauri implementation\n const normalized = p.replace(/\\\\/g, '/').replace(/\\/+$/, '');\n const lastSlash = normalized.lastIndexOf('/');\n \n if (lastSlash === -1) {\n return '.';\n }\n if (lastSlash === 0) {\n return '/';\n }\n \n return normalized.slice(0, lastSlash);\n}\n\n/**\n * Get the base name of a path\n * \n * @param p - Path to get base name from\n * @param ext - Optional extension to remove\n * @returns Base name of the path\n */\nexport function basename(p: string, ext?: string): string {\n if (nodePath) {\n return nodePath.basename(p, ext);\n }\n \n // Browser/Tauri implementation\n const normalized = p.replace(/\\\\/g, '/').replace(/\\/+$/, '');\n const lastSlash = normalized.lastIndexOf('/');\n let name = lastSlash === -1 ? normalized : normalized.slice(lastSlash + 1);\n \n if (ext && name.endsWith(ext)) {\n name = name.slice(0, -ext.length);\n }\n \n return name;\n}\n\n/**\n * Get the extension of a path\n * \n * @param p - Path to get extension from\n * @returns Extension of the path (including the dot)\n */\nexport function extname(p: string): string {\n if (nodePath) {\n return nodePath.extname(p);\n }\n \n // Browser/Tauri implementation\n const name = basename(p);\n const lastDot = name.lastIndexOf('.');\n \n if (lastDot <= 0) {\n return '';\n }\n \n return name.slice(lastDot);\n}\n\n/**\n * Check if a path is absolute\n * \n * @param p - Path to check\n * @returns true if the path is absolute\n */\nexport function isAbsolute(p: string): boolean {\n if (nodePath) {\n return nodePath.isAbsolute(p);\n }\n \n // Browser/Tauri implementation\n // Unix: starts with /\n // Windows: starts with drive letter or UNC\n return p.startsWith('/') || /^[a-zA-Z]:[\\\\/]/.test(p) || p.startsWith('\\\\\\\\');\n}\n\n/**\n * Normalize a path\n * \n * @param p - Path to normalize\n * @returns Normalized path\n */\nexport function normalize(p: string): string {\n if (nodePath) {\n return nodePath.normalize(p);\n }\n \n // Browser/Tauri implementation\n return join(p);\n}\n\n/**\n * Get relative path from one path to another\n * \n * @param from - Source path\n * @param to - Destination path\n * @returns Relative path\n */\nexport function relative(from: string, to: string): string {\n if (nodePath) {\n return nodePath.relative(from, to);\n }\n \n // Browser/Tauri implementation\n const fromParts = from.replace(/\\\\/g, '/').split('/').filter(Boolean);\n const toParts = to.replace(/\\\\/g, '/').split('/').filter(Boolean);\n \n // Find common base\n let commonLength = 0;\n while (\n commonLength < fromParts.length &&\n commonLength < toParts.length &&\n fromParts[commonLength] === toParts[commonLength]\n ) {\n commonLength++;\n }\n \n // Build relative path\n const upCount = fromParts.length - commonLength;\n const relativeParts = [\n ...Array(upCount).fill('..'),\n ...toParts.slice(commonLength)\n ];\n \n return relativeParts.join('/') || '.';\n}\n\n/**\n * Parse a path into its components\n * \n * @param p - Path to parse\n * @returns Parsed path object\n */\nexport function parse(p: string): {\n root: string;\n dir: string;\n base: string;\n ext: string;\n name: string;\n} {\n if (nodePath) {\n return nodePath.parse(p);\n }\n \n // Browser/Tauri implementation\n const dir = dirname(p);\n const base = basename(p);\n const ext = extname(p);\n const name = basename(p, ext);\n \n // Determine root\n let root = '';\n if (p.startsWith('/')) {\n root = '/';\n } else if (/^[a-zA-Z]:[\\\\/]/.test(p)) {\n root = p.slice(0, 3);\n }\n \n return { root, dir, base, ext, name };\n}\n\n/**\n * Format a path from its components\n * \n * @param pathObject - Object with path components\n * @returns Formatted path\n */\nexport function format(pathObject: {\n root?: string;\n dir?: string;\n base?: string;\n ext?: string;\n name?: string;\n}): string {\n if (nodePath) {\n return nodePath.format(pathObject);\n }\n \n // Browser/Tauri implementation\n const { dir, root, base, name, ext } = pathObject;\n const fileName = base || (name || '') + (ext || '');\n \n if (dir) {\n return dir + '/' + fileName;\n }\n if (root) {\n return root + fileName;\n }\n \n return fileName;\n}\n\n// Default export for compatibility\nexport default {\n sep,\n delimiter,\n join,\n resolve,\n dirname,\n basename,\n extname,\n isAbsolute,\n normalize,\n relative,\n parse,\n format,\n};\n", "/**\n * Shell/Process execution binding\n * \n * Provides cross-platform process execution that works in both Node.js and Tauri.\n * In Node.js, delegates to the native 'child_process' module.\n * In Tauri, uses @tauri-apps/plugin-shell.\n */\n\nimport { isTauri, isNode, assertRuntime } from './runtime';\n\n// Types for Tauri shell plugin\ntype TauriShellModule = typeof import('@tauri-apps/plugin-shell');\n\n// Conditionally import modules\nlet nodeChildProcess: typeof import('child_process') | null = null;\nlet nodeUtil: typeof import('util') | null = null;\nlet tauriShell: TauriShellModule | null = null;\n\n// Initialize Node.js modules if available\nif (isNode()) {\n // eslint-disable-next-line @typescript-eslint/no-var-requires\n nodeChildProcess = require('child_process');\n // eslint-disable-next-line @typescript-eslint/no-var-requires\n nodeUtil = require('util');\n}\n\n/**\n * Lazily load Tauri shell module\n */\nasync function getTauriShell(): Promise<TauriShellModule> {\n if (!tauriShell) {\n tauriShell = await import('@tauri-apps/plugin-shell');\n }\n return tauriShell;\n}\n\n/**\n * Filter out undefined values from env object (Tauri requires string values only)\n */\nfunction filterEnv(env?: Record<string, string | undefined>): Record<string, string> | undefined {\n if (!env) return undefined;\n const result: Record<string, string> = {};\n for (const [key, value] of Object.entries(env)) {\n if (value !== undefined) {\n result[key] = value;\n }\n }\n return result;\n}\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport interface ExecOptions {\n cwd?: string;\n env?: Record<string, string | undefined>;\n timeout?: number;\n maxBuffer?: number;\n encoding?: BufferEncoding;\n}\n\nexport interface ExecResult {\n stdout: string;\n stderr: string;\n code: number | null;\n}\n\nexport interface SpawnOptions {\n cwd?: string;\n env?: Record<string, string | undefined>;\n stdio?: 'pipe' | 'inherit' | 'ignore';\n}\n\nexport interface SpawnedProcess {\n pid?: number;\n kill: () => Promise<void>;\n write: (data: string) => Promise<void>;\n onStdout: (callback: (data: string) => void) => void;\n onStderr: (callback: (data: string) => void) => void;\n onClose: (callback: (code: number | null) => void) => void;\n onError: (callback: (error: Error) => void) => void;\n}\n\n// ============================================================================\n// Async Operations\n// ============================================================================\n\n/**\n * Execute a shell command and return the output\n * \n * @param command - Command to execute\n * @param options - Execution options\n * @returns Command output\n */\nexport async function exec(command: string, options: ExecOptions = {}): Promise<ExecResult> {\n if (isTauri()) {\n const shell = await getTauriShell();\n \n // Tauri shell uses Command class with args\n // For shell execution, we use the shell program with -c flag\n const shellProgram = process.platform === 'win32' ? 'cmd' : 'sh';\n const shellArgs = process.platform === 'win32' ? ['/c', command] : ['-c', command];\n \n const cmd = shell.Command.create(shellProgram, shellArgs, {\n cwd: options.cwd,\n env: filterEnv(options.env),\n });\n \n const output = await cmd.execute();\n \n return {\n stdout: output.stdout,\n stderr: output.stderr,\n code: output.code,\n };\n }\n \n if (nodeChildProcess && nodeUtil) {\n const execPromise = nodeUtil.promisify(nodeChildProcess.exec);\n \n try {\n const { stdout, stderr } = await execPromise(command, {\n cwd: options.cwd,\n env: options.env ? { ...process.env, ...options.env } : undefined,\n timeout: options.timeout,\n maxBuffer: options.maxBuffer || 50 * 1024 * 1024, // 50MB default\n encoding: options.encoding || 'utf-8',\n });\n \n return {\n stdout: stdout || '',\n stderr: stderr || '',\n code: 0,\n };\n } catch (error: any) {\n return {\n stdout: error.stdout || '',\n stderr: error.stderr || error.message,\n code: error.code || 1,\n };\n }\n }\n \n throw new Error('exec is not supported in this environment');\n}\n\n/**\n * Spawn a process\n * \n * @param program - Program to run\n * @param args - Arguments to pass\n * @param options - Spawn options\n * @returns Spawned process handle\n */\nexport async function spawn(\n program: string,\n args: string[] = [],\n options: SpawnOptions = {}\n): Promise<SpawnedProcess> {\n if (isTauri()) {\n const shell = await getTauriShell();\n \n const cmd = shell.Command.create(program, args, {\n cwd: options.cwd,\n env: filterEnv(options.env),\n });\n \n const childProcess = await cmd.spawn();\n \n let stdoutCallback: ((data: string) => void) | null = null;\n let stderrCallback: ((data: string) => void) | null = null;\n let closeCallback: ((code: number | null) => void) | null = null;\n let errorCallback: ((error: Error) => void) | null = null;\n \n // Note: Tauri's Child type uses different event handling\n // We cast to any to work around type differences between versions\n const child = childProcess as any;\n \n // Set up event handlers if available\n if (typeof child.on === 'function') {\n child.on('close', (data: any) => {\n if (closeCallback) {\n closeCallback(data?.code ?? null);\n }\n });\n \n child.on('error', (error: any) => {\n if (errorCallback) {\n errorCallback(new Error(String(error)));\n }\n });\n }\n \n return {\n pid: childProcess.pid,\n kill: async () => {\n await childProcess.kill();\n },\n write: async (data: string) => {\n await childProcess.write(new TextEncoder().encode(data));\n },\n onStdout: (callback) => {\n stdoutCallback = callback;\n if (typeof child.on === 'function') {\n child.on('data', (event: any) => {\n if (event?.type === 'Stdout' && stdoutCallback) {\n stdoutCallback(event.data);\n }\n });\n }\n },\n onStderr: (callback) => {\n stderrCallback = callback;\n if (typeof child.on === 'function') {\n child.on('data', (event: any) => {\n if (event?.type === 'Stderr' && stderrCallback) {\n stderrCallback(event.data);\n }\n });\n }\n },\n onClose: (callback) => {\n closeCallback = callback;\n },\n onError: (callback) => {\n errorCallback = callback;\n },\n };\n }\n \n if (nodeChildProcess) {\n const child = nodeChildProcess.spawn(program, args, {\n cwd: options.cwd,\n env: options.env ? { ...process.env, ...options.env } : undefined,\n stdio: ['pipe', 'pipe', 'pipe'],\n });\n \n let stdoutCallback: ((data: string) => void) | null = null;\n let stderrCallback: ((data: string) => void) | null = null;\n let closeCallback: ((code: number | null) => void) | null = null;\n let errorCallback: ((error: Error) => void) | null = null;\n \n child.stdout?.on('data', (data) => {\n if (stdoutCallback) {\n stdoutCallback(data.toString());\n }\n });\n \n child.stderr?.on('data', (data) => {\n if (stderrCallback) {\n stderrCallback(data.toString());\n }\n });\n \n child.on('close', (code) => {\n if (closeCallback) {\n closeCallback(code);\n }\n });\n \n child.on('error', (error) => {\n if (errorCallback) {\n errorCallback(error);\n }\n });\n \n return {\n pid: child.pid,\n kill: async () => {\n child.kill();\n },\n write: async (data: string) => {\n return new Promise((resolve, reject) => {\n if (child.stdin) {\n child.stdin.write(data, (err) => {\n if (err) reject(err);\n else resolve();\n });\n } else {\n reject(new Error('stdin not available'));\n }\n });\n },\n onStdout: (callback) => {\n stdoutCallback = callback;\n },\n onStderr: (callback) => {\n stderrCallback = callback;\n },\n onClose: (callback) => {\n closeCallback = callback;\n },\n onError: (callback) => {\n errorCallback = callback;\n },\n };\n }\n \n throw new Error('spawn is not supported in this environment');\n}\n\n// ============================================================================\n// Sync Operations (Node.js only)\n// ============================================================================\n\n/**\n * Execute a shell command synchronously (Node.js only)\n * \n * @param command - Command to execute\n * @param options - Execution options\n * @returns Command output\n */\nexport function execSync(command: string, options: ExecOptions = {}): ExecResult {\n assertRuntime('execSync', ['node']);\n \n if (nodeChildProcess) {\n try {\n const stdout = nodeChildProcess.execSync(command, {\n cwd: options.cwd,\n env: options.env ? { ...process.env, ...options.env } : undefined,\n timeout: options.timeout,\n maxBuffer: options.maxBuffer || 50 * 1024 * 1024,\n encoding: options.encoding || 'utf-8',\n stdio: ['pipe', 'pipe', 'pipe'],\n });\n \n return {\n stdout: stdout?.toString() || '',\n stderr: '',\n code: 0,\n };\n } catch (error: any) {\n return {\n stdout: error.stdout?.toString() || '',\n stderr: error.stderr?.toString() || error.message,\n code: error.status || 1,\n };\n }\n }\n \n throw new Error('execSync is not supported in this environment');\n}\n\n/**\n * Spawn a process synchronously (Node.js only)\n * \n * @param program - Program to run\n * @param args - Arguments to pass\n * @param options - Spawn options\n * @returns Exit code and output\n */\nexport function spawnSync(\n program: string,\n args: string[] = [],\n options: SpawnOptions = {}\n): ExecResult {\n assertRuntime('spawnSync', ['node']);\n \n if (nodeChildProcess) {\n const result = nodeChildProcess.spawnSync(program, args, {\n cwd: options.cwd,\n env: options.env ? { ...process.env, ...options.env } : undefined,\n encoding: 'utf-8',\n });\n \n return {\n stdout: result.stdout || '',\n stderr: result.stderr || '',\n code: result.status,\n };\n }\n \n throw new Error('spawnSync is not supported in this environment');\n}\n\n// ============================================================================\n// Utility Functions\n// ============================================================================\n\n/**\n * Promisified exec with async/await syntax\n * Alias for exec() for compatibility\n */\nexport const execAsync = exec;\n\n/**\n * Create a promisified version of exec (Node.js compatible API)\n */\nexport function promisifyExec(): (command: string, options?: ExecOptions) => Promise<{ stdout: string; stderr: string }> {\n return async (command: string, options?: ExecOptions) => {\n const result = await exec(command, options);\n if (result.code !== 0) {\n const error = new Error(`Command failed: ${command}`);\n (error as any).stdout = result.stdout;\n (error as any).stderr = result.stderr;\n (error as any).code = result.code;\n throw error;\n }\n return { stdout: result.stdout, stderr: result.stderr };\n };\n}\n\n// ============================================================================\n// Node.js Native Access (Node.js only)\n// ============================================================================\n\nexport interface NodeSpawnOptions {\n cwd?: string;\n env?: NodeJS.ProcessEnv;\n stdio?: 'pipe' | 'inherit' | 'ignore' | Array<'pipe' | 'inherit' | 'ignore' | 'ipc'>;\n detached?: boolean;\n shell?: boolean | string;\n}\n\n/**\n * Direct access to Node.js child_process.spawn (Node.js only)\n * \n * Use this when you need the full Node.js ChildProcess API with event emitters.\n * Returns the native ChildProcess object.\n * \n * @param command - Command to execute\n * @param args - Arguments to pass\n * @param options - Node.js spawn options\n * @returns Native Node.js ChildProcess\n */\nexport function nodeSpawn(\n command: string,\n args: string[] = [],\n options: NodeSpawnOptions = {}\n): import('child_process').ChildProcess {\n assertRuntime('nodeSpawn', ['node']);\n \n if (nodeChildProcess) {\n return nodeChildProcess.spawn(command, args, options as any);\n }\n \n throw new Error('nodeSpawn is not supported in this environment');\n}\n\n// Default export\nexport default {\n exec,\n execAsync,\n execSync,\n spawn,\n spawnSync,\n promisifyExec,\n nodeSpawn,\n};\n", "// Shared types for workflow execution system\n// This file consolidates DTOs from both frontend and backend\n\n// Core workflow execution types (from backend)\nexport interface WorkflowStep {\n id: string;\n type: 'trigger' | 'action';\n framework: 'activepieces' | 'n8n' | 'script';\n module: string;\n params: Record<string, any>;\n conditions?: {\n skipIf?: string;\n stopIf?: string;\n };\n retries?: number;\n timeout?: number;\n}\n\nexport interface ExecutionResult {\n nodeId: string;\n success: boolean;\n result?: any;\n error?: string;\n timestamp: Date;\n duration: number;\n}\n\nexport interface WorkflowExecution {\n id: string;\n workflowId: string;\n status: 'pending' | 'running' | 'completed' | 'failed' | 'cancelled';\n results: ExecutionResult[];\n nodeStatuses: NodeExecutionStatus[];\n startTime: Date;\n endTime?: Date;\n currentNode?: string;\n output?: any; // Resolved workflow output\n}\n\n// Backend workflow definition\nexport interface BackendWorkflow {\n id?: string;\n name: string;\n description?: string;\n steps: WorkflowStep[];\n variables?: Record<string, any>;\n metadata?: Record<string, any>;\n}\n\n// Frontend workflow UI types\nexport interface WorkflowNode {\n id: string;\n type: 'n8n' | 'activepieces' | 'script' | 'trigger' | 'action' | 'bits';\n position: { x: number; y: number };\n data: {\n label: string;\n framework: 'n8n' | 'activepieces' | 'script' | 'bits';\n source?: 'npm' | 'github' | 'local' | 'hub' | 'inline';\n module?: string;\n resource?: string;\n operation?: string;\n params?: Record<string, any>;\n credentials?: Record<string, any>;\n inputs?: string[];\n outputs?: string[];\n // Script-specific properties\n scriptPath?: string;\n language?: 'deno' | 'python3' | 'go' | 'bash' | 'sql' | 'typescript' | 'javascript';\n content?: string;\n inputTransforms?: Record<string, any>;\n stopAfterIf?: { expr: string; skipIfStopped?: boolean };\n // Script inline script\n script?: {\n type: 'script';\n language: 'deno' | 'python3' | 'go' | 'bash' | 'typescript' | 'javascript';\n content?: string;\n path?: string;\n };\n // Trigger-specific properties\n triggerType?: 'webhook' | 'polling' | 'schedule' | 'app_webhook';\n triggerSettings?: {\n authType?: 'none' | 'header' | 'query_param';\n authFields?: Record<string, any>;\n };\n };\n}\n\nexport interface WorkflowEdge {\n id: string;\n source: string;\n target: string;\n sourceHandle?: string;\n targetHandle?: string;\n optional?: boolean; // If true, target node can run when ANY optional edge is satisfied\n}\n\n// Generate all export files\nexport interface ExportBundle {\n id: string; // Stack UUID for build caching\n stackYaml: string;\n habitFiles: Array<{ filename: string; content: string }>;\n envFile: string;\n frontendHtml?: string;\n}\n\n// Frontend workflow definition (visual representation)\nexport interface FrontendWorkflow {\n id: string;\n name: string;\n description?: string;\n nodes: WorkflowNode[];\n edges: WorkflowEdge[];\n version: string;\n output?: Record<string, any>; // Template-based output definition\n}\n\n// Use frontend workflow format as the primary workflow type\nexport type Workflow = FrontendWorkflow;\n\n// ============================================================================\n// Visual Canvas Types - Structurally compatible with reactflow\n// ============================================================================\n\n/**\n * Visual canvas node type - structurally compatible with reactflow's Node<T>\n * Used by visual components for rendering workflow canvas\n */\nexport interface CanvasNode<T = any> {\n id: string;\n type?: string;\n position: { x: number; y: number };\n data: T;\n selected?: boolean;\n dragging?: boolean;\n}\n\n/**\n * Visual canvas edge type - structurally compatible with reactflow's Edge\n * Used by visual components for rendering workflow connections\n */\nexport interface CanvasEdge {\n id: string;\n source: string;\n target: string;\n sourceHandle?: string | null;\n targetHandle?: string | null;\n type?: string;\n animated?: boolean;\n label?: any; // Compatible with ReactNode from reactflow\n}\n\n// ============================================================================\n// Export Format Types - Used for YAML/JSON serialization\n// ============================================================================\n\n/**\n * Node format for habit YAML export files\n * Simplified format for serialization and sharing\n */\nexport interface HabitNode {\n id: string;\n type: string;\n position?: { x: number; y: number };\n data: {\n framework: 'n8n' | 'activepieces' | 'script' | 'bits';\n module?: string;\n label?: string;\n source?: string;\n operation?: string;\n params?: Record<string, any>;\n credentials?: Record<string, any>;\n script?: {\n type: string;\n language: string;\n content: string;\n };\n content?: string;\n language?: string;\n };\n}\n\n/**\n * Edge format for habit YAML export files\n */\nexport interface HabitEdge {\n id: string;\n source: string;\n target: string;\n sourceHandle?: string;\n targetHandle?: string;\n}\n\n/**\n * Complete habit definition for export/import\n */\nexport interface Habit {\n id: string;\n name: string;\n description: string;\n nodes: HabitNode[];\n edges: HabitEdge[];\n output?: Record<string, string>; // Habit-level output mappings\n version: string;\n createdAt: string;\n updatedAt: string;\n}\n\n// ============================================================================\n// Flow Control Types - Allow nodes to control downstream execution\n// ============================================================================\n\n/**\n * Flow control metadata returned by nodes that control branching.\n * This allows nodes like bit-if, switch, router to specify which downstream\n * branches should be executed and which should be skipped.\n */\nexport interface FlowControlMetadata {\n /**\n * Array of sourceHandle identifiers that should be activated.\n * Downstream nodes connected via these handles will execute.\n * e.g., [\"branch-0\"] to only activate the first branch\n */\n activeBranches?: string[];\n \n /**\n * Array of sourceHandle identifiers that should be skipped.\n * Downstream nodes connected via these handles will be marked as skipped.\n * If activeBranches is provided, skipBranches is ignored.\n */\n skipBranches?: string[];\n \n /**\n * If true, only connections from activeBranches will execute.\n * If false or undefined, flow control is not applied.\n */\n controlsFlow?: boolean;\n}\n\n/**\n * Edge information for dependency tracking\n */\nexport interface EdgeInfo {\n sourceNodeId: string;\n sourceHandle?: string; // e.g., \"branch-0\", \"branch-1\"\n targetHandle?: string;\n optional?: boolean;\n}\n\n// Node dependency tracking for execution\nexport interface NodeDependencies {\n nodeId: string;\n dependsOn: string[]; // Node IDs this node depends on (incoming edges) - required\n optionalDependsOn: string[]; // Optional dependencies - node runs when ANY is satisfied\n dependencyFor: string[]; // Node IDs that depend on this node (outgoing edges)\n /**\n * Detailed edge information for flow control.\n * Maps source node ID to edge info including sourceHandle.\n */\n incomingEdges?: EdgeInfo[];\n}\n\n// Execution context for tracking node execution status\nexport interface NodeExecutionStatus {\n nodeId: string;\n status: 'pending' | 'running' | 'completed' | 'failed' | 'skipped';\n result?: any;\n error?: string;\n startTime?: Date;\n endTime?: Date;\n duration?: number;\n}\n\n// Module management types\nexport interface AvailableModuleDefinition {\n framework: string;\n name: string;\n package: string;\n version: string;\n description: string;\n license: string;\n repository?: string;\n cloned?: boolean;\n built?: boolean;\n installed?: boolean;\n /** Icon URL or Lucide icon reference (e.g., \"lucide:Database\") */\n logoUrl?: string;\n displayName?: string;\n}\n\n// Script-specific types\nexport interface ScriptModule {\n id: string;\n summary?: string;\n value: {\n type: 'script' | 'forloopflow' | 'branchone' | 'branchall';\n path?: string;\n content?: string;\n language?: 'deno' | 'python3' | 'go' | 'bash' | 'sql' | 'typescript' | 'javascript';\n lock?: string;\n inputTransforms?: Record<string, any>;\n modules?: ScriptModule[]; // For flow types\n iterator?: { expr: string; type: string }; // For forloopflow\n branches?: { expr: string; modules: ScriptModule[] }[]; // For branches\n parallel?: boolean;\n skipFailures?: boolean;\n };\n stopAfterIf?: {\n expr: string;\n skipIfStopped?: boolean;\n };\n}\n\nexport interface ScriptWorkflow {\n summary: string;\n description?: string;\n value: {\n modules: ScriptModule[];\n failureModule?: ScriptModule;\n };\n schema: {\n type: string;\n $schema: string;\n required?: string[];\n properties: Record<string, any>;\n };\n}\n\n// Node templates for UI\nexport interface NodeTemplate {\n id: string;\n label: string;\n framework: 'n8n' | 'activepieces' | 'script' | 'bits';\n module: string;\n icon?: string;\n color: string;\n description?: string;\n resources?: {\n name: string;\n operations: string[];\n }[];\n // Script-specific template properties\n scriptType?: 'script' | 'flow';\n language?: 'deno' | 'python3' | 'go' | 'bash' | 'sql' | 'typescript';\n}\n\n// Execution API types\nexport interface ExecutionRequest {\n framework: string;\n module: string;\n async?: boolean;\n params: Record<string, any>;\n}\n\n// Webhook trigger types\nexport interface WebhookTriggerInfo {\n nodeId: string;\n path: string;\n method?: string;\n authType?: 'none' | 'header' | 'query_param';\n authFields?: Record<string, any>;\n}\n\nexport interface WebhookPayload {\n nodeId: string;\n payload: any;\n headers?: Record<string, string>;\n query?: Record<string, string>;\n}\n\n// Multi-workflow configuration types\nexport interface WorkflowReference {\n id?: string; // Optional - if not provided, uses the id from the workflow JSON file\n path: string; // Path to workflow JSON file (relative to config.json or absolute)\n enabled?: boolean; // Whether this workflow is enabled (default: true)\n webhookTimeout?: number; // Optional per-workflow webhook timeout\n}\n\n/**\n * Modules operation mode:\n * - 'restricted': Only allows using modules already defined in modules.json\n * - 'open': Allows adding any module and appends it to modules.json if it doesn't exist\n */\nexport type ModulesMode = 'restricted' | 'open';\n\nexport interface WorkflowConfig {\n version?: string;\n workflows: WorkflowReference[];\n server?: {\n port?: number;\n host?: string;\n webhookPort?: number; // Deprecated: webhooks now served on same port under /webhook\n webhookHost?: string; // Deprecated: webhooks now served on same port under /webhook\n frontend?: string; // Path to static frontend folder to serve at \"/\" (relative to config.json or absolute)\n openapi?: boolean; // Enable OpenAPI/Swagger documentation at /api/docs (default: false)\n };\n modules?: {\n mode?: ModulesMode; // 'restricted' (default) or 'open' - can also be set via HABITS_MODULES_MODE env var\n };\n defaults?: {\n webhookTimeout?: number;\n };\n /**\n * Logging configuration\n * Can be overridden by environment variables (HABITS_LOG_*)\n */\n logging?: {\n /** Default log level: trace, debug, info, warn, error, fatal, none */\n level?: 'trace' | 'debug' | 'info' | 'warn' | 'error' | 'fatal' | 'none';\n /** Output destinations */\n outputs?: ('console' | 'file' | 'json')[];\n /** File output configuration */\n file?: {\n path?: string;\n maxSize?: string; // e.g., '10mb'\n maxFiles?: number;\n };\n /** Output format for console/file */\n format?: 'text' | 'json';\n /** Enable colors in console output */\n colorize?: boolean;\n /** Per-bit log level overrides (e.g., { 'bit-http': 'debug' }) */\n bitOverrides?: Record<string, 'trace' | 'debug' | 'info' | 'warn' | 'error' | 'fatal' | 'none'>;\n };\n}\n\nexport interface LoadedWorkflow {\n reference: WorkflowReference;\n workflow: Workflow;\n}\n\nexport function isFrontendWorkflow(workflow: Workflow): workflow is FrontendWorkflow {\n return 'nodes' in workflow && 'edges' in workflow && Array.isArray(workflow.nodes) && Array.isArray(workflow.edges);\n}\n\n// ============================================================================\n// Execution Response Types (shared between streaming and non-streaming)\n// ============================================================================\n\n/**\n * Base execution context - common fields for all responses\n */\nexport interface ExecutionContext {\n executionId: string;\n workflowId: string;\n}\n\n/**\n * Node result - emitted when a node completes or fails\n * Used in both streaming (per-node) and non-streaming (in nodeResults array)\n */\nexport interface NodeResult extends ExecutionContext {\n nodeId: string;\n nodeName: string;\n status: 'completed' | 'failed';\n output?: any;\n error?: string;\n duration?: number;\n}\n\n/**\n * Execution summary - final execution status\n * Used in both streaming (final event) and non-streaming (response)\n */\nexport interface ExecutionSummary extends ExecutionContext {\n status: 'completed' | 'failed' | 'cancelled';\n output?: any;\n error?: string;\n startTime: string;\n endTime: string;\n}\n\n/**\n * Full execution response (non-streaming mode)\n * Contains summary plus optional node results\n */\nexport interface ExecutionResponse extends ExecutionSummary {\n nodeResults?: NodeResult[];\n}\n\n// ============================================================================\n// Streaming Types\n// ============================================================================\n\nexport type StreamEventType = 'execution_started' | 'node_started' | 'node_completed' | 'node_failed' | 'execution_completed' | 'execution_failed';\n\n/**\n * Minimal node stream event (non-debug mode)\n * Mirrors NodeResult structure for consistency\n */\nexport interface StreamNodeEvent extends NodeResult {\n type?: 'node_completed' | 'node_failed';\n}\n\n/**\n * Minimal execution stream event (non-debug mode) \n * Mirrors ExecutionSummary structure for consistency\n */\nexport interface StreamExecutionEvent extends ExecutionContext {\n type: 'execution_completed' | 'execution_failed';\n status: 'completed' | 'failed';\n output?: any;\n error?: string;\n}\n\n/**\n * Verbose stream event - contains all fields (used in debug mode)\n */\nexport interface StreamEvent extends ExecutionContext {\n type: StreamEventType;\n timestamp: string;\n nodeId?: string;\n nodeName?: string;\n status?: 'pending' | 'running' | 'completed' | 'failed' | 'skipped';\n result?: any; // Alias for output in verbose mode\n output?: any; // Final workflow output (only in execution_completed)\n error?: string;\n duration?: number;\n progress?: {\n completed: number;\n total: number;\n percentage: number;\n };\n}\n\nexport type StreamCallback = (event: StreamEvent) => void;\n\n// Common framework types\nexport type Framework = 'activepieces' | 'n8n' | 'script' | 'bits';\nexport type StepType = 'trigger' | 'action';\nexport type ExecutionStatus = 'pending' | 'running' | 'completed' | 'failed' | 'cancelled';\nexport type ScriptLanguage = 'deno' | 'python3' | 'go' | 'bash' | 'sql' | 'typescript';\nexport type ScriptModuleType = 'script' | 'forloopflow' | 'branchone' | 'branchall';", "/**\n * Habits Logger - Type Definitions\n * \n * A multilevel logging system with hierarchical config resolution:\n * .env (highest) > stack.yaml > habit.yaml > defaults (lowest)\n */\n\n/**\n * Log levels ordered by severity (trace=0 is most verbose, fatal=5 is most severe)\n */\nexport type LogLevel = 'trace' | 'debug' | 'info' | 'warn' | 'error' | 'fatal' | 'none';\n\n/**\n * Priority map for log level comparison\n * Lower number = more verbose, higher number = more severe\n */\nexport const LOG_LEVEL_PRIORITY: Record<LogLevel, number> = {\n trace: 0,\n debug: 1,\n info: 2,\n warn: 3,\n error: 4,\n fatal: 5,\n none: 6, // Disables all logging\n};\n\n/**\n * A single log entry with all metadata\n */\nexport interface LogEntry {\n /** When the log was created */\n timestamp: Date;\n /** Severity level */\n level: LogLevel;\n /** The log message */\n message: string;\n /** Contextual information about where this log originated */\n context: LogContext;\n /** Optional structured data to include with the log */\n data?: Record<string, unknown>;\n}\n\n/**\n * Context information attached to each log entry\n * Enables filtering and tracing across workflows and bits\n */\nexport interface LogContext {\n /** ID of the workflow being executed */\n workflowId?: string;\n /** ID of the current node in the workflow */\n nodeId?: string;\n /** Name of the bit (e.g., 'bit-http', 'bit-openai') */\n bitName?: string;\n /** Name of the action within the bit */\n actionName?: string;\n /** Unique ID for this execution instance */\n executionId?: string;\n}\n\n/**\n * Configuration for console output\n */\nexport interface ConsoleOutputConfig {\n type: 'console';\n /** Enable ANSI colors in output (auto-detected if not specified) */\n colorize?: boolean;\n /** Output format */\n format?: 'text' | 'json';\n}\n\n/**\n * Configuration for file output with rotation support\n */\nexport interface FileOutputConfig {\n type: 'file';\n /** Path to the log file */\n path: string;\n /** Maximum file size before rotation (e.g., '10mb', '1gb') */\n maxSize?: string;\n /** Maximum number of rotated files to keep */\n maxFiles?: number;\n /** Output format */\n format?: 'text' | 'json';\n}\n\n/**\n * Configuration for JSON output (NDJSON format)\n */\nexport interface JsonOutputConfig {\n type: 'json';\n /** Custom writable stream (defaults to stdout) */\n stream?: NodeJS.WritableStream;\n}\n\n/**\n * Union type for all output configurations\n */\nexport type OutputConfig = ConsoleOutputConfig | FileOutputConfig | JsonOutputConfig;\n\n/**\n * Complete logger configuration\n */\nexport interface LoggerConfig {\n /** Default log level for all loggers */\n level: LogLevel;\n /** Output destinations */\n outputs: OutputConfig[];\n /** Per-bit log level overrides (e.g., { 'bit-http': 'debug' }) */\n bitOverrides?: Record<string, LogLevel>;\n}\n\n/**\n * Logger interface that all logger implementations must satisfy\n */\nexport interface ILogger {\n /** Alias for info() - for console.log compatibility */\n log(message: string, data?: Record<string, unknown>): void;\n /** Log at trace level (most verbose, for detailed debugging) */\n trace(message: string, data?: Record<string, unknown>): void;\n /** Log at debug level (debugging information) */\n debug(message: string, data?: Record<string, unknown>): void;\n /** Log at info level (general information) */\n info(message: string, data?: Record<string, unknown>): void;\n /** Log at warn level (warnings, potential issues) */\n warn(message: string, data?: Record<string, unknown>): void;\n /** Log at error level (errors, failures) */\n error(message: string, data?: Record<string, unknown>): void;\n /** Log at fatal level (critical errors, system failures) */\n fatal(message: string, data?: Record<string, unknown>): void;\n \n /** Create a child logger with additional context */\n child(context: Partial<LogContext>): ILogger;\n \n /** Dynamically change the log level */\n setLevel(level: LogLevel): void;\n /** Get the current log level */\n getLevel(): LogLevel;\n}\n\n/**\n * Logging configuration as it appears in habit.yaml\n */\nexport interface HabitLoggingConfig {\n level?: LogLevel;\n outputs?: ('console' | 'file' | 'json')[];\n bitOverrides?: Record<string, LogLevel>;\n}\n\n/**\n * Logging configuration as it appears in stack.yaml\n * Extends habit config with additional server-level options\n */\nexport interface StackLoggingConfig extends HabitLoggingConfig {\n file?: {\n path?: string;\n maxSize?: string;\n maxFiles?: number;\n };\n format?: 'text' | 'json';\n colorize?: boolean;\n}\n\n/**\n * Environment variable names for logging configuration\n */\nexport const LOG_ENV_VARS = {\n /** Global log level override */\n LEVEL: 'HABITS_LOG_LEVEL',\n /** Comma-separated output types (console,file,json) */\n OUTPUT: 'HABITS_LOG_OUTPUT',\n /** File output path */\n FILE_PATH: 'HABITS_LOG_FILE_PATH',\n /** File max size */\n FILE_MAX_SIZE: 'HABITS_LOG_FILE_MAX_SIZE',\n /** File max rotation count */\n FILE_MAX_FILES: 'HABITS_LOG_FILE_MAX_FILES',\n /** Enable/disable colors */\n COLORIZE: 'HABITS_LOG_COLORIZE',\n /** Output format */\n FORMAT: 'HABITS_LOG_FORMAT',\n /** Pattern for per-bit level overrides: HABITS_LOG_BIT_{BITNAME}_LEVEL */\n BIT_LEVEL_PATTERN: /^HABITS_LOG_BIT_(.+)_LEVEL$/,\n} as const;\n", "/**\n * Logger - Main logger class\n * \n * A hierarchical, OOP-based logger with support for:\n * - 6 log levels (trace, debug, info, warn, error, fatal)\n * - Multiple transports (console, file, JSON)\n * - Per-bit log level overrides\n * - Child loggers with inherited configuration\n */\n\nimport { \n ILogger, \n LogLevel, \n LogEntry, \n LogContext, \n LoggerConfig,\n LOG_LEVEL_PRIORITY \n} from './types';\nimport { Transport } from './transports/Transport';\n\nexport interface LoggerOptions {\n /** Logger configuration */\n config: LoggerConfig;\n /** Transports to output to */\n transports: Transport[];\n /** Initial context */\n context?: LogContext;\n}\n\nexport class Logger implements ILogger {\n private level: LogLevel;\n private context: LogContext;\n private transports: Transport[];\n private bitOverrides: Record<string, LogLevel>;\n private closed: boolean = false;\n\n constructor(options: LoggerOptions) {\n this.level = options.config.level;\n this.transports = options.transports;\n this.context = options.context || {};\n this.bitOverrides = options.config.bitOverrides || {};\n }\n\n /**\n * Determine if a message at the given level should be logged\n */\n private shouldLog(level: LogLevel): boolean {\n if (this.closed) return false;\n const effectiveLevel = this.getEffectiveLevel();\n return LOG_LEVEL_PRIORITY[level] >= LOG_LEVEL_PRIORITY[effectiveLevel];\n }\n\n /**\n * Get the effective log level, accounting for bit-specific overrides\n */\n private getEffectiveLevel(): LogLevel {\n // Check for bit-specific override\n if (this.context.bitName) {\n const override = this.bitOverrides[this.context.bitName];\n if (override) return override;\n }\n return this.level;\n }\n\n /**\n * Core logging method - routes to all transports\n */\n private logInternal(level: LogLevel, message: string, data?: Record<string, unknown>): void {\n if (!this.shouldLog(level)) return;\n\n const entry: LogEntry = {\n timestamp: new Date(),\n level,\n message,\n context: { ...this.context },\n data,\n };\n\n for (const transport of this.transports) {\n try {\n transport.log(entry);\n } catch (err) {\n // Don't let transport errors break the application\n console.error(`[Logger] Transport error: ${err}`);\n }\n }\n }\n\n // ---------- Public logging methods ----------\n\n /** Alias for info() - for console.log compatibility */\n log(message: string, data?: Record<string, unknown>): void {\n this.logInternal('info', message, data);\n }\n\n trace(message: string, data?: Record<string, unknown>): void {\n this.logInternal('trace', message, data);\n }\n\n debug(message: string, data?: Record<string, unknown>): void {\n this.logInternal('debug', message, data);\n }\n\n info(message: string, data?: Record<string, unknown>): void {\n this.logInternal('info', message, data);\n }\n\n warn(message: string, data?: Record<string, unknown>): void {\n this.logInternal('warn', message, data);\n }\n\n error(message: string, data?: Record<string, unknown>): void {\n this.logInternal('error', message, data);\n }\n\n fatal(message: string, data?: Record<string, unknown>): void {\n this.logInternal('fatal', message, data);\n }\n\n // ---------- Configuration methods ----------\n\n /**\n * Create a child logger that inherits this logger's configuration\n * but with additional context fields\n */\n child(additionalContext: Partial<LogContext>): ILogger {\n return new Logger({\n config: {\n level: this.level,\n outputs: [],\n bitOverrides: this.bitOverrides,\n },\n transports: this.transports, // Share transports with parent\n context: { ...this.context, ...additionalContext },\n });\n }\n\n /**\n * Dynamically change the log level\n */\n setLevel(level: LogLevel): void {\n this.level = level;\n }\n\n /**\n * Get the current log level\n */\n getLevel(): LogLevel {\n return this.level;\n }\n\n /**\n * Get the current context\n */\n getContext(): LogContext {\n return { ...this.context };\n }\n\n /**\n * Update context fields\n */\n setContext(context: Partial<LogContext>): void {\n this.context = { ...this.context, ...context };\n }\n\n /**\n * Set a bit-specific log level override\n */\n setBitOverride(bitName: string, level: LogLevel): void {\n this.bitOverrides[bitName] = level;\n }\n\n /**\n * Remove a bit-specific log level override\n */\n removeBitOverride(bitName: string): void {\n delete this.bitOverrides[bitName];\n }\n\n /**\n * Get all bit overrides\n */\n getBitOverrides(): Record<string, LogLevel> {\n return { ...this.bitOverrides };\n }\n\n // ---------- Lifecycle methods ----------\n\n /**\n * Flush all transports\n */\n async flush(): Promise<void> {\n await Promise.all(this.transports.map(t => t.flush()));\n }\n\n /**\n * Close all transports and prevent further logging\n */\n async close(): Promise<void> {\n this.closed = true;\n await Promise.all(this.transports.map(t => t.close()));\n }\n\n /**\n * Check if the logger is closed\n */\n isClosed(): boolean {\n return this.closed;\n }\n}\n\n/**\n * No-op logger that discards all log messages\n * Useful for testing or when logging should be disabled\n */\nexport class NullLogger implements ILogger {\n log(_message: string, _data?: Record<string, unknown>): void {}\n trace(_message: string, _data?: Record<string, unknown>): void {}\n debug(_message: string, _data?: Record<string, unknown>): void {}\n info(_message: string, _data?: Record<string, unknown>): void {}\n warn(_message: string, _data?: Record<string, unknown>): void {}\n error(_message: string, _data?: Record<string, unknown>): void {}\n fatal(_message: string, _data?: Record<string, unknown>): void {}\n child(_context: Partial<LogContext>): ILogger { return this; }\n setLevel(_level: LogLevel): void {}\n getLevel(): LogLevel { return 'none'; }\n}\n", "/**\n * ConfigResolver - Resolves logger configuration from multiple sources\n * \n * Priority (highest to lowest):\n * 1. Environment variables (.env)\n * 2. Stack configuration (stack.yaml)\n * 3. Habit configuration (habit.yaml)\n * 4. Default values\n */\n\nimport { \n LoggerConfig, \n LogLevel, \n OutputConfig,\n HabitLoggingConfig,\n StackLoggingConfig,\n LOG_ENV_VARS,\n LOG_LEVEL_PRIORITY\n} from './types';\n\n/**\n * Default logger configuration\n */\nconst DEFAULT_CONFIG: LoggerConfig = {\n level: 'info',\n outputs: [{ type: 'console', colorize: true, format: 'text' }],\n bitOverrides: {},\n};\n\n/**\n * Valid log levels for validation\n */\nconst VALID_LOG_LEVELS = new Set<LogLevel>(Object.keys(LOG_LEVEL_PRIORITY) as LogLevel[]);\n\nexport class ConfigResolver {\n /**\n * Resolve logger configuration from all sources\n * \n * @param habitConfig - Configuration from habit.yaml (lowest priority)\n * @param stackConfig - Configuration from stack.yaml\n * @param env - Environment variables (highest priority)\n * @returns Merged LoggerConfig\n */\n static resolve(\n habitConfig?: HabitLoggingConfig,\n stackConfig?: StackLoggingConfig,\n env: Record<string, string | undefined> = process.env\n ): LoggerConfig {\n // Start with defaults\n let config: LoggerConfig = this.deepClone(DEFAULT_CONFIG);\n\n // Layer 1: Apply habit.yaml config\n if (habitConfig) {\n config = this.mergeHabitConfig(config, habitConfig);\n }\n\n // Layer 2: Apply stack.yaml config (overrides habit)\n if (stackConfig) {\n config = this.mergeStackConfig(config, stackConfig);\n }\n\n // Layer 3: Apply environment variables (highest priority)\n config = this.applyEnvOverrides(config, env);\n\n return config;\n }\n\n /**\n * Merge habit-level config into base config\n */\n private static mergeHabitConfig(\n base: LoggerConfig,\n habit: HabitLoggingConfig\n ): LoggerConfig {\n const result = this.deepClone(base);\n\n if (habit.level && this.isValidLogLevel(habit.level)) {\n result.level = habit.level;\n }\n\n if (habit.outputs && Array.isArray(habit.outputs)) {\n result.outputs = habit.outputs\n .filter(o => ['console', 'file', 'json'].includes(o))\n .map(o => this.createOutputConfig(o));\n }\n\n if (habit.bitOverrides) {\n result.bitOverrides = {\n ...result.bitOverrides,\n ...this.filterValidBitOverrides(habit.bitOverrides),\n };\n }\n\n return result;\n }\n\n /**\n * Merge stack-level config into base config\n */\n private static mergeStackConfig(\n base: LoggerConfig,\n stack: StackLoggingConfig\n ): LoggerConfig {\n let result = this.mergeHabitConfig(base, stack);\n\n // Handle file configuration\n if (stack.file?.path) {\n const fileOutput: OutputConfig = {\n type: 'file',\n path: stack.file.path,\n maxSize: stack.file.maxSize,\n maxFiles: stack.file.maxFiles,\n format: stack.format,\n };\n\n // Add file output if not already present\n const hasFileOutput = result.outputs.some(o => o.type === 'file');\n if (!hasFileOutput) {\n result.outputs.push(fileOutput);\n } else {\n // Update existing file output\n result.outputs = result.outputs.map(o =>\n o.type === 'file' ? fileOutput : o\n );\n }\n }\n\n // Apply format to console outputs\n if (stack.format) {\n result.outputs = result.outputs.map(o =>\n o.type === 'console' ? { ...o, format: stack.format } : o\n );\n }\n\n // Apply colorize to console outputs\n if (stack.colorize !== undefined) {\n result.outputs = result.outputs.map(o =>\n o.type === 'console' ? { ...o, colorize: stack.colorize } : o\n );\n }\n\n return result;\n }\n\n /**\n * Apply environment variable overrides\n */\n private static applyEnvOverrides(\n config: LoggerConfig,\n env: Record<string, string | undefined>\n ): LoggerConfig {\n const result = this.deepClone(config);\n\n // HABITS_LOG_LEVEL\n const levelEnv = env[LOG_ENV_VARS.LEVEL];\n if (levelEnv && this.isValidLogLevel(levelEnv as LogLevel)) {\n result.level = levelEnv as LogLevel;\n }\n\n // HABITS_LOG_OUTPUT (comma-separated: console,file,json)\n const outputEnv = env[LOG_ENV_VARS.OUTPUT];\n if (outputEnv) {\n const outputs = outputEnv.split(',').map(o => o.trim().toLowerCase());\n result.outputs = outputs\n .filter(o => ['console', 'file', 'json'].includes(o))\n .map(type => this.createOutputConfigFromEnv(type, env));\n }\n\n // HABITS_LOG_FILE_PATH\n const filePathEnv = env[LOG_ENV_VARS.FILE_PATH];\n if (filePathEnv) {\n const existingFile = result.outputs.find(o => o.type === 'file');\n if (existingFile && existingFile.type === 'file') {\n existingFile.path = filePathEnv;\n } else {\n result.outputs.push(this.createOutputConfigFromEnv('file', env));\n }\n }\n\n // HABITS_LOG_COLORIZE\n const colorizeEnv = env[LOG_ENV_VARS.COLORIZE];\n if (colorizeEnv !== undefined) {\n const colorize = colorizeEnv.toLowerCase() !== 'false';\n result.outputs = result.outputs.map(o =>\n o.type === 'console' ? { ...o, colorize } : o\n );\n }\n\n // HABITS_LOG_FORMAT\n const formatEnv = env[LOG_ENV_VARS.FORMAT];\n if (formatEnv && ['text', 'json'].includes(formatEnv.toLowerCase())) {\n const format = formatEnv.toLowerCase() as 'text' | 'json';\n result.outputs = result.outputs.map(o =>\n o.type === 'console' || o.type === 'file' ? { ...o, format } : o\n );\n }\n\n // Per-bit level overrides: HABITS_LOG_BIT_{BITNAME}_LEVEL\n for (const [key, value] of Object.entries(env)) {\n const match = key.match(LOG_ENV_VARS.BIT_LEVEL_PATTERN);\n if (match && value && this.isValidLogLevel(value as LogLevel)) {\n // Convert BITNAME to bit-name format (e.g., HTTP -> bit-http)\n const bitName = `bit-${match[1].toLowerCase().replace(/_/g, '-')}`;\n result.bitOverrides![bitName] = value as LogLevel;\n }\n }\n\n return result;\n }\n\n /**\n * Create a basic output config from type string\n */\n private static createOutputConfig(type: string): OutputConfig {\n switch (type) {\n case 'file':\n return { type: 'file', path: './logs/habits.log' };\n case 'json':\n return { type: 'json' };\n case 'console':\n default:\n return { type: 'console', colorize: true, format: 'text' };\n }\n }\n\n /**\n * Create output config from env vars\n */\n private static createOutputConfigFromEnv(\n type: string,\n env: Record<string, string | undefined>\n ): OutputConfig {\n switch (type) {\n case 'file':\n const maxFilesEnv = env[LOG_ENV_VARS.FILE_MAX_FILES];\n return {\n type: 'file',\n path: env[LOG_ENV_VARS.FILE_PATH] || './logs/habits.log',\n maxSize: env[LOG_ENV_VARS.FILE_MAX_SIZE],\n maxFiles: maxFilesEnv ? parseInt(maxFilesEnv, 10) : undefined,\n };\n case 'json':\n return { type: 'json' };\n case 'console':\n default:\n return {\n type: 'console',\n colorize: env[LOG_ENV_VARS.COLORIZE]?.toLowerCase() !== 'false',\n format: (env[LOG_ENV_VARS.FORMAT] as 'text' | 'json') || 'text',\n };\n }\n }\n\n /**\n * Filter and validate bit overrides\n */\n private static filterValidBitOverrides(\n overrides: Record<string, LogLevel>\n ): Record<string, LogLevel> {\n const result: Record<string, LogLevel> = {};\n for (const [bit, level] of Object.entries(overrides)) {\n if (this.isValidLogLevel(level)) {\n result[bit] = level;\n }\n }\n return result;\n }\n\n /**\n * Check if a value is a valid log level\n */\n private static isValidLogLevel(level: string): level is LogLevel {\n return VALID_LOG_LEVELS.has(level as LogLevel);\n }\n\n /**\n * Deep clone an object\n */\n private static deepClone<T>(obj: T): T {\n return JSON.parse(JSON.stringify(obj));\n }\n\n /**\n * Parse size string to bytes (e.g., \"10mb\" -> 10485760)\n */\n static parseSize(size?: string): number | undefined {\n if (!size) return undefined;\n\n const match = size.toLowerCase().match(/^(\\d+(?:\\.\\d+)?)\\s*(b|kb|mb|gb)?$/);\n if (!match) return undefined;\n\n const value = parseFloat(match[1]);\n const unit = match[2] || 'b';\n\n const multipliers: Record<string, number> = {\n b: 1,\n kb: 1024,\n mb: 1024 * 1024,\n gb: 1024 * 1024 * 1024,\n };\n\n return Math.floor(value * multipliers[unit]);\n }\n}\n", "/**\n * Abstract base class for log transports\n * Transports are responsible for delivering formatted log entries to their destination\n */\n\nimport { LogEntry } from '../types';\nimport { Formatter } from '../formatters/Formatter';\n\nexport abstract class Transport {\n protected formatter: Formatter;\n\n constructor(formatter: Formatter) {\n this.formatter = formatter;\n }\n\n /**\n * Log an entry to this transport's destination\n * @param entry The log entry to write\n */\n abstract log(entry: LogEntry): void;\n\n /**\n * Flush any buffered output\n * @returns Promise that resolves when flush is complete\n */\n abstract flush(): Promise<void>;\n\n /**\n * Close the transport and release resources\n * @returns Promise that resolves when closed\n */\n abstract close(): Promise<void>;\n\n /**\n * Replace the formatter used by this transport\n * @param formatter New formatter to use\n */\n setFormatter(formatter: Formatter): void {\n this.formatter = formatter;\n }\n\n /**\n * Get the current formatter\n */\n getFormatter(): Formatter {\n return this.formatter;\n }\n}\n", "/**\n * Console transport - writes logs to stdout/stderr with optional colors\n */\n\nimport { Transport } from './Transport';\nimport { LogEntry, LogLevel } from '../types';\nimport { Formatter } from '../formatters/Formatter';\n\n/**\n * ANSI color codes for each log level\n */\nconst LEVEL_COLORS: Record<LogLevel, string> = {\n trace: '\\x1b[90m', // Gray\n debug: '\\x1b[36m', // Cyan\n info: '\\x1b[32m', // Green\n warn: '\\x1b[33m', // Yellow\n error: '\\x1b[31m', // Red\n fatal: '\\x1b[35m', // Magenta (bold)\n none: '',\n};\n\nconst RESET = '\\x1b[0m';\nconst BOLD = '\\x1b[1m';\n\nexport interface ConsoleTransportOptions {\n /** Enable ANSI color codes. Auto-detected from TTY if not specified */\n colorize?: boolean;\n /** Use stderr for error and fatal levels. Default: true */\n useStderr?: boolean;\n}\n\nexport class ConsoleTransport extends Transport {\n private colorize: boolean;\n private useStderr: boolean;\n\n constructor(formatter: Formatter, options: ConsoleTransportOptions = {}) {\n super(formatter);\n // Auto-detect TTY for colorize if not explicitly set\n this.colorize = options.colorize ?? (process.stdout.isTTY ?? false);\n this.useStderr = options.useStderr ?? true;\n }\n\n log(entry: LogEntry): void {\n const formatted = this.formatter.format(entry);\n let output: string;\n\n if (this.colorize) {\n const color = LEVEL_COLORS[entry.level];\n const bold = entry.level === 'fatal' ? BOLD : '';\n output = `${bold}${color}${formatted}${RESET}`;\n } else {\n output = formatted;\n }\n\n // Route error/fatal to stderr\n const stream = this.useStderr && (entry.level === 'error' || entry.level === 'fatal')\n ? process.stderr\n : process.stdout;\n\n stream.write(output + '\\n');\n }\n\n async flush(): Promise<void> {\n // Console is synchronous, but we handle any pending writes\n return new Promise((resolve) => {\n if (process.stdout.writableLength === 0 && process.stderr.writableLength === 0) {\n resolve();\n } else {\n // Wait for drain event\n const checkDrain = () => {\n if (process.stdout.writableLength === 0 && process.stderr.writableLength === 0) {\n resolve();\n } else {\n setImmediate(checkDrain);\n }\n };\n checkDrain();\n }\n });\n }\n\n async close(): Promise<void> {\n await this.flush();\n // Nothing to close for console\n }\n\n /**\n * Enable or disable colorization at runtime\n */\n setColorize(enabled: boolean): void {\n this.colorize = enabled;\n }\n\n /**\n * Check if colorization is enabled\n */\n isColorized(): boolean {\n return this.colorize;\n }\n}\n", "/**\n * File transport - writes logs to a file with rotation support\n */\n\nimport * as fs from 'fs';\nimport * as path from 'path';\nimport { Transport } from './Transport';\nimport { LogEntry } from '../types';\nimport { Formatter } from '../formatters/Formatter';\n\nexport interface FileTransportOptions {\n /** Path to the log file */\n path: string;\n /** Maximum file size in bytes before rotation. Default: 10MB */\n maxSize?: number;\n /** Maximum number of rotated files to keep. Default: 5 */\n maxFiles?: number;\n /** File mode (permissions). Default: 0o644 */\n mode?: number;\n}\n\nexport class FileTransport extends Transport {\n private filePath: string;\n private maxSize: number;\n private maxFiles: number;\n private mode: number;\n private stream: fs.WriteStream | null = null;\n private currentSize: number = 0;\n private writeQueue: Promise<void> = Promise.resolve();\n\n constructor(formatter: Formatter, options: FileTransportOptions) {\n super(formatter);\n this.filePath = path.resolve(options.path);\n this.maxSize = options.maxSize || 10 * 1024 * 1024; // 10MB default\n this.maxFiles = options.maxFiles || 5;\n this.mode = options.mode || 0o644;\n this.initStream();\n }\n\n private initStream(): void {\n // Ensure directory exists\n const dir = path.dirname(this.filePath);\n if (!fs.existsSync(dir)) {\n fs.mkdirSync(dir, { recursive: true });\n }\n\n // Get current file size if file exists\n if (fs.existsSync(this.filePath)) {\n try {\n this.currentSize = fs.statSync(this.filePath).size;\n } catch {\n this.currentSize = 0;\n }\n }\n\n // Create write stream in append mode\n this.stream = fs.createWriteStream(this.filePath, {\n flags: 'a',\n mode: this.mode,\n encoding: 'utf8',\n });\n\n // Handle stream errors\n this.stream.on('error', (err) => {\n console.error(`[Logger] File transport error: ${err.message}`);\n });\n }\n\n private async rotate(): Promise<void> {\n if (!this.stream) return;\n\n // Close current stream\n await new Promise<void>((resolve) => {\n this.stream?.end(() => resolve());\n });\n this.stream = null;\n\n // Rotate existing files: .log.4 -> .log.5, .log.3 -> .log.4, etc.\n for (let i = this.maxFiles - 1; i >= 1; i--) {\n const oldPath = `${this.filePath}.${i}`;\n const newPath = `${this.filePath}.${i + 1}`;\n\n if (fs.existsSync(oldPath)) {\n if (i === this.maxFiles - 1) {\n // Delete oldest file\n try {\n fs.unlinkSync(oldPath);\n } catch {\n // Ignore deletion errors\n }\n } else {\n // Rename to next number\n try {\n fs.renameSync(oldPath, newPath);\n } catch {\n // Ignore rename errors\n }\n }\n }\n }\n\n // Rename current file to .1\n try {\n fs.renameSync(this.filePath, `${this.filePath}.1`);\n } catch {\n // If rename fails, we'll just append to the file\n }\n\n // Reset size and create new stream\n this.currentSize = 0;\n this.initStream();\n }\n\n log(entry: LogEntry): void {\n const formatted = this.formatter.format(entry) + '\\n';\n const bytes = Buffer.byteLength(formatted, 'utf8');\n\n // Queue the write to ensure sequential execution\n this.writeQueue = this.writeQueue.then(async () => {\n // Check if rotation needed\n if (this.currentSize + bytes > this.maxSize) {\n await this.rotate();\n }\n\n // Write to stream\n if (this.stream && !this.stream.destroyed) {\n this.stream.write(formatted);\n this.currentSize += bytes;\n }\n });\n }\n\n async flush(): Promise<void> {\n // Wait for write queue to complete\n await this.writeQueue;\n\n // Ensure stream is drained\n return new Promise((resolve) => {\n if (!this.stream || this.stream.writableLength === 0) {\n resolve();\n } else {\n this.stream.once('drain', () => resolve());\n }\n });\n }\n\n async close(): Promise<void> {\n await this.flush();\n \n return new Promise((resolve) => {\n if (!this.stream) {\n resolve();\n return;\n }\n\n this.stream.end(() => {\n this.stream = null;\n resolve();\n });\n });\n }\n\n /**\n * Get the current log file path\n */\n getFilePath(): string {\n return this.filePath;\n }\n\n /**\n * Get the current file size\n */\n getCurrentSize(): number {\n return this.currentSize;\n }\n}\n", "/**\n * Abstract base class for log formatters\n * Formatters transform LogEntry objects into string representations\n */\n\nimport { LogEntry } from '../types';\n\nexport abstract class Formatter {\n /**\n * Format a log entry into a string\n * @param entry The log entry to format\n * @returns Formatted string representation\n */\n abstract format(entry: LogEntry): string;\n}\n", "/**\n * JSON formatter for structured log output\n * Outputs NDJSON (newline-delimited JSON) format suitable for log aggregation\n */\n\nimport { Formatter } from './Formatter';\nimport { LogEntry } from '../types';\n\nexport interface JsonFormatterOptions {\n /** Include stack trace for error objects in data */\n includeStackTrace?: boolean;\n /** Pretty print JSON (adds indentation) - not recommended for production */\n prettyPrint?: boolean;\n}\n\nexport class JsonFormatter extends Formatter {\n private includeStackTrace: boolean;\n private prettyPrint: boolean;\n\n constructor(options: JsonFormatterOptions = {}) {\n super();\n this.includeStackTrace = options.includeStackTrace ?? true;\n this.prettyPrint = options.prettyPrint ?? false;\n }\n\n format(entry: LogEntry): string {\n const output: Record<string, unknown> = {\n timestamp: entry.timestamp.toISOString(),\n level: entry.level,\n message: entry.message,\n };\n\n // Add context fields if present\n if (entry.context.workflowId) output.workflowId = entry.context.workflowId;\n if (entry.context.nodeId) output.nodeId = entry.context.nodeId;\n if (entry.context.bitName) output.bitName = entry.context.bitName;\n if (entry.context.actionName) output.actionName = entry.context.actionName;\n if (entry.context.executionId) output.executionId = entry.context.executionId;\n\n // Add data if present, handling Error objects specially\n if (entry.data && Object.keys(entry.data).length > 0) {\n output.data = this.serializeData(entry.data);\n }\n\n return this.prettyPrint \n ? JSON.stringify(output, null, 2) \n : JSON.stringify(output);\n }\n\n private serializeData(data: Record<string, unknown>): Record<string, unknown> {\n const result: Record<string, unknown> = {};\n \n for (const [key, value] of Object.entries(data)) {\n if (value instanceof Error) {\n result[key] = {\n name: value.name,\n message: value.message,\n ...(this.includeStackTrace && value.stack ? { stack: value.stack } : {}),\n };\n } else if (value !== undefined) {\n result[key] = value;\n }\n }\n \n return result;\n }\n}\n", "/**\n * JSON transport - writes NDJSON (newline-delimited JSON) to a stream\n * Useful for log aggregation systems like ELK, Datadog, etc.\n */\n\nimport { Transport } from './Transport';\nimport { LogEntry } from '../types';\nimport { JsonFormatter } from '../formatters/JsonFormatter';\n\nexport interface JsonTransportOptions {\n /** Writable stream to output to. Default: process.stdout */\n stream?: NodeJS.WritableStream;\n}\n\nexport class JsonTransport extends Transport {\n private stream: NodeJS.WritableStream;\n\n constructor(options: JsonTransportOptions = {}) {\n // Always use JsonFormatter for this transport\n super(new JsonFormatter());\n this.stream = options.stream || process.stdout;\n }\n\n log(entry: LogEntry): void {\n const formatted = this.formatter.format(entry);\n this.stream.write(formatted + '\\n');\n }\n\n async flush(): Promise<void> {\n return new Promise((resolve) => {\n const writable = this.stream as NodeJS.WriteStream;\n if (writable.writableLength === 0) {\n resolve();\n } else {\n writable.once('drain', () => resolve());\n }\n });\n }\n\n async close(): Promise<void> {\n await this.flush();\n // Don't close process.stdout/stderr\n if (this.stream !== process.stdout && this.stream !== process.stderr) {\n return new Promise((resolve) => {\n (this.stream as any).end?.(() => resolve()) || resolve();\n });\n }\n }\n\n /**\n * Get the output stream\n */\n getStream(): NodeJS.WritableStream {\n return this.stream;\n }\n}\n", "/**\n * Text formatter for human-readable log output\n * \n * Output format: [timestamp] [LEVEL] [context] message {data}\n * Example: [2026-02-15T10:30:00.123Z] [INFO ] [wf:my-workflow/bit-http] Request completed {\"status\":200}\n */\n\nimport { Formatter } from './Formatter';\nimport { LogEntry, LogContext } from '../types';\n\nexport interface TextFormatterOptions {\n /** Timestamp format: 'iso' (full), 'unix' (milliseconds), 'short' (time only) */\n timestampFormat?: 'iso' | 'unix' | 'short';\n /** Include milliseconds in short format */\n includeMs?: boolean;\n}\n\nexport class TextFormatter extends Formatter {\n private timestampFormat: 'iso' | 'unix' | 'short';\n private includeMs: boolean;\n\n constructor(options: TextFormatterOptions = {}) {\n super();\n this.timestampFormat = options.timestampFormat || 'iso';\n this.includeMs = options.includeMs ?? true;\n }\n\n format(entry: LogEntry): string {\n const ts = this.formatTimestamp(entry.timestamp);\n const level = entry.level.toUpperCase().padEnd(5);\n const ctx = this.formatContext(entry.context);\n const data = entry.data && Object.keys(entry.data).length > 0 \n ? ` ${JSON.stringify(entry.data)}` \n : '';\n \n return `[${ts}] [${level}]${ctx} ${entry.message}${data}`;\n }\n\n private formatTimestamp(date: Date): string {\n switch (this.timestampFormat) {\n case 'unix':\n return String(date.getTime());\n case 'short':\n // HH:MM:SS.mmm or HH:MM:SS\n const time = date.toISOString().slice(11, this.includeMs ? 23 : 19);\n return time;\n case 'iso':\n default:\n return date.toISOString();\n }\n }\n\n private formatContext(ctx: LogContext): string {\n const parts: string[] = [];\n \n if (ctx.workflowId) {\n parts.push(`wf:${ctx.workflowId}`);\n }\n if (ctx.nodeId) {\n parts.push(`node:${ctx.nodeId}`);\n }\n if (ctx.bitName) {\n parts.push(ctx.bitName);\n }\n if (ctx.actionName) {\n parts.push(ctx.actionName);\n }\n if (ctx.executionId) {\n parts.push(`exec:${ctx.executionId.slice(0, 8)}`);\n }\n \n return parts.length > 0 ? ` [${parts.join('/')}]` : '';\n }\n}\n", "/**\n * LoggerFactory - Factory for creating configured logger instances\n * \n * Handles:\n * - Creating loggers from merged configuration sources\n * - Managing the root logger singleton\n * - Creating child loggers for specific bits/workflows\n * - Building appropriate transports based on configuration\n */\n\nimport { Logger, NullLogger } from './Logger';\nimport { \n LoggerConfig, \n OutputConfig, \n LogContext, \n ILogger,\n HabitLoggingConfig,\n StackLoggingConfig \n} from './types';\nimport { ConfigResolver } from './ConfigResolver';\nimport { Transport } from './transports/Transport';\nimport { ConsoleTransport } from './transports/ConsoleTransport';\nimport { FileTransport } from './transports/FileTransport';\nimport { JsonTransport } from './transports/JsonTransport';\nimport { TextFormatter } from './formatters/TextFormatter';\nimport { JsonFormatter } from './formatters/JsonFormatter';\nimport { Formatter } from './formatters/Formatter';\n\n/**\n * Global root logger instance\n */\nlet rootLogger: Logger | null = null;\n\nexport class LoggerFactory {\n /**\n * Create a new logger from configuration sources\n * \n * @param habitConfig - Per-workflow logging config from habit.yaml\n * @param stackConfig - Stack-level logging config from stack.yaml\n * @param context - Initial context for this logger\n * @returns Configured logger instance\n */\n static create(\n habitConfig?: HabitLoggingConfig,\n stackConfig?: StackLoggingConfig,\n context?: LogContext\n ): ILogger {\n const config = ConfigResolver.resolve(\n habitConfig,\n stackConfig,\n process.env\n );\n\n const transports = this.createTransports(config);\n \n return new Logger({\n config,\n transports,\n context,\n });\n }\n\n /**\n * Create a logger directly from a LoggerConfig\n */\n static createFromConfig(config: LoggerConfig, context?: LogContext): ILogger {\n const transports = this.createTransports(config);\n return new Logger({ config, transports, context });\n }\n\n /**\n * Initialize the root logger (called once at server startup)\n * \n * @param stackConfig - Stack-level logging configuration\n * @returns The root logger instance\n */\n static initRoot(stackConfig?: StackLoggingConfig): ILogger {\n if (rootLogger) {\n // Close existing root logger\n rootLogger.close().catch(() => {});\n }\n\n rootLogger = this.create(undefined, stackConfig) as Logger;\n return rootLogger;\n }\n\n /**\n * Get the current root logger, or create a default one\n */\n static getRoot(): ILogger {\n if (!rootLogger) {\n rootLogger = this.create() as Logger;\n }\n return rootLogger;\n }\n\n /**\n * Create a child logger for a specific bit execution\n * Inherits from the root logger with bit-specific context\n * \n * @param bitName - Name of the bit (e.g., 'bit-http')\n * @param actionName - Name of the action being executed\n * @param workflowId - ID of the workflow\n * @param nodeId - ID of the current node\n * @param executionId - Unique execution ID\n */\n static forBit(\n bitName: string,\n actionName: string,\n workflowId?: string,\n nodeId?: string,\n executionId?: string\n ): ILogger {\n const root = this.getRoot();\n \n return root.child({\n bitName,\n actionName,\n workflowId,\n nodeId,\n executionId,\n });\n }\n\n /**\n * Create a child logger for workflow execution\n */\n static forWorkflow(workflowId: string, executionId?: string): ILogger {\n const root = this.getRoot();\n \n return root.child({\n workflowId,\n executionId,\n });\n }\n\n /**\n * Create a null logger that discards all messages\n * Useful for testing or when logging should be disabled\n */\n static createNull(): ILogger {\n return new NullLogger();\n }\n\n /**\n * Shutdown the root logger and release resources\n */\n static async shutdown(): Promise<void> {\n if (rootLogger) {\n await rootLogger.close();\n rootLogger = null;\n }\n }\n\n // ---------- Internal methods ----------\n\n /**\n * Create transports based on configuration\n */\n private static createTransports(config: LoggerConfig): Transport[] {\n return config.outputs.map(output => this.createTransport(output));\n }\n\n /**\n * Create a single transport from output configuration\n */\n private static createTransport(output: OutputConfig): Transport {\n switch (output.type) {\n case 'file':\n return new FileTransport(\n this.createFormatter(output.format || 'text'),\n {\n path: output.path,\n maxSize: ConfigResolver.parseSize(output.maxSize),\n maxFiles: output.maxFiles,\n }\n );\n\n case 'json':\n return new JsonTransport({\n stream: output.stream,\n });\n\n case 'console':\n default:\n return new ConsoleTransport(\n this.createFormatter(output.format || 'text'),\n { colorize: output.colorize }\n );\n }\n }\n\n /**\n * Create a formatter based on format type\n */\n private static createFormatter(format: 'text' | 'json'): Formatter {\n return format === 'json' \n ? new JsonFormatter() \n : new TextFormatter();\n }\n}\n", "import * as fs from '@ha-bits/bindings/fs';\nimport * as path from '@ha-bits/bindings/path';\nimport { exec as execAsync } from '@ha-bits/bindings/shell';\nimport { LoggerFactory } from '@ha-bits/core';\n\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// npm Install Utilities\n// ============================================================================\n\n/**\n * Options for npm install commands\n */\nexport interface NpmInstallOptions {\n cwd?: string;\n timeout?: number;\n legacyPeerDeps?: boolean;\n includePeer?: boolean;\n production?: boolean;\n noSave?: boolean;\n prefix?: string;\n saveOptional?: boolean;\n global?: boolean;\n /** Custom npm registry URL */\n registry?: string;\n}\n\n/**\n * Builds the npm install command with the given options\n */\nfunction buildNpmInstallCommand(packageSpec?: string, options: NpmInstallOptions = {}): string {\n const parts = ['npm', 'install'];\n \n // Always ignore engine requirements to allow n8n modules that require newer Node versions\n parts.push('--engine-strict=false');\n // Ignore scripts to reduce memory usage and speed up installs\n parts.push('--ignore-scripts');\n\n if (packageSpec) {\n parts.push(packageSpec);\n }\n \n if (options.global) {\n parts.push('-g');\n }\n if (options.legacyPeerDeps) {\n parts.push('--legacy-peer-deps');\n }\n if (options.includePeer) {\n parts.push('--include=peer');\n }\n if (options.production) {\n parts.push('--omit=dev');\n }\n if (options.noSave) {\n // parts.push('--no-save');\n }\n if (options.prefix) {\n parts.push(`--prefix ${options.prefix}`);\n }\n if (options.saveOptional) {\n parts.push('--save-optional');\n }\n if (options.registry) {\n parts.push(`--registry ${options.registry}`);\n }\n \n return parts.join(' ');\n}\n\n/**\n * Run package install asynchronously with the given options\n * Uses npm with increased memory for heavy packages\n */\nexport async function npmInstall(packageSpec?: string, options: NpmInstallOptions = {}): Promise<{ stdout: string; stderr: string }> {\n const command = buildNpmInstallCommand(packageSpec, options);\n \n const execOptions: { cwd?: string; timeout?: number; env?: NodeJS.ProcessEnv; maxBuffer?: number } = {\n // Increase max buffer for large outputs\n maxBuffer: 500 * 1024 * 1024, // 500MB\n // Set NODE_OPTIONS to increase heap memory and optimize GC for heavy installs\n env: {\n ...process.env,\n NODE_OPTIONS: '--max-old-space-size=16384',\n },\n };\n if (options.cwd) {\n execOptions.cwd = options.cwd;\n }\n if (options.timeout) {\n execOptions.timeout = options.timeout;\n }\n\n // Check if package is already installed, skip if yes\n if (packageSpec) {\n // Parse package name (handle @scope/name@version format)\n const packageName = packageSpec.replace(/@[\\d.]+(-[\\w.]+)?$/, ''); // Remove version suffix\n const nodeModulesBase = options.prefix || options.cwd || process.cwd();\n const packagePath = path.join(nodeModulesBase, 'node_modules', packageName);\n \n if (fs.existsSync(packagePath)) {\n logger.log(`Package ${packageName} already installed at ${packagePath}, skipping install`);\n return { stdout: `Skipped: ${packageName} already installed`, stderr: '' };\n }\n }\n\n logger.log(`Executing npm install command: ${command}`);\n return execAsync(command, execOptions);\n}\n\n// ============================================================================\n// Path Utilities\n// ============================================================================\n\n/**\n * Environment variable name for the nodes base path without the /nodes suffix\n */\nconst NODES_BASE_PATH_ENV = 'HABITS_NODES_PATH';\n\n/**\n * Environment variable name for local nodes directory in the workspace\n */\nconst LOCAL_NODES_PATH_ENV = 'HABITS_LOCAL_NODES_PATH';\n\n/**\n * Default base path for nodes when not specified in environment\n */\nconst DEFAULT_NODES_BASE_PATH = '/tmp/habits-nodes';\n\n/**\n * Cache the base path to avoid repeated file reads\n */\nlet cachedNodesBasePath: string | null = null;\n\n/**\n * Get the base path for nodes from environment variable or .env file.\n * Falls back to /tmp/habits-nodes if not specified.\n * \n * Priority:\n * 1. Environment variable HABITS_NODES_PATH\n * 2. .env file in current working directory\n * 3. Default: /tmp/habits-nodes\n * \n * @returns The base path for nodes\n */\nexport function getNodesBasePath(): string {\n if (cachedNodesBasePath !== null) {\n return cachedNodesBasePath;\n }\n\n // First, check environment variable\n if (process.env[NODES_BASE_PATH_ENV]) {\n cachedNodesBasePath = process.env[NODES_BASE_PATH_ENV];\n return cachedNodesBasePath;\n }\n\n // Default to /tmp/habits-nodes\n cachedNodesBasePath = DEFAULT_NODES_BASE_PATH;\n return cachedNodesBasePath;\n}\n\n/**\n * Get the full path to the nodes directory for a specific framework.\n * \n * @param framework - The framework name (e.g., 'activepieces', 'n8n', 'script')\n * @returns The full path to the framework's nodes directory\n */\nexport function getNodesPath(framework: string): string {\n return path.join(getNodesBasePath(), 'node_modules');\n}\n\n/**\n * Get the full path to a specific module within a framework.\n * \n * @param framework - The framework name (e.g., 'activepieces', 'n8n', 'script')\n * @param moduleName - The module name (e.g., '@ha-bits/piece-intersect')\n * @returns The full path to the module\n */\nexport function getModuleFullPath(framework: string, moduleName: string): string {\n return path.join(getNodesBasePath(), 'node_modules', moduleName);\n}\n\n/**\n * Get the local nodes path from the workspace for local module sources.\n * This is where modules in the 'nodes/' directory of the workspace are located.\n * \n * Priority:\n * 1. Environment variable HABITS_LOCAL_NODES_PATH\n * 2. 'nodes' directory relative to process.cwd()\n * 3. Search up from __dirname for a 'nodes' directory\n * \n * @param framework - The framework name (e.g., 'activepieces', 'n8n')\n * @returns The path to local nodes, or null if not found\n */\nexport function getLocalModulePath(framework: string, moduleName: string): string | null {\n // For bits modules, strip @ha-bits/ prefix for path construction when path already includes @ha-bits\n const strippedModuleName = moduleName.startsWith('@ha-bits/') ? moduleName.slice('@ha-bits/'.length) : moduleName;\n const pathModuleName = moduleName;\n \n // Check environment variable first\n if (process.env[LOCAL_NODES_PATH_ENV]) {\n const localPath = path.join(process.env[LOCAL_NODES_PATH_ENV], framework, pathModuleName);\n if (fs.existsSync(localPath)) {\n return localPath;\n }\n // Also check @ha-bits subdirectory for bits framework\n if (framework === 'bits') {\n const haBitsPath = path.join(process.env[LOCAL_NODES_PATH_ENV], framework, '@ha-bits', strippedModuleName);\n if (fs.existsSync(haBitsPath)) {\n return haBitsPath;\n }\n }\n }\n \n // Try relative to cwd()\n const cwdNodesPath = path.join(process.cwd(), 'nodes', framework, pathModuleName);\n if (fs.existsSync(cwdNodesPath)) {\n return cwdNodesPath;\n }\n \n // For bits framework, also check nodes/bits/@ha-bits/ path\n if (framework === 'bits') { // Try relative to cwd()\n const bitsCreatorPath = path.join(process.cwd(), 'nodes', 'bits', '@ha-bits', strippedModuleName);\n \n if (fs.existsSync(bitsCreatorPath)) {\n return bitsCreatorPath;\n }\n // Search up from __dirname path\n let currentDir = __dirname;\n for (let i = 0; i < 10; i++) { \n const bitsPath = path.join(currentDir, 'nodes', 'bits', '@ha-bits', strippedModuleName);\n if (fs.existsSync(bitsPath)) {\n return bitsPath;\n }\n const parent = path.dirname(currentDir);\n if (parent === currentDir) break;\n currentDir = parent;\n }\n }\n \n // Search up from __dirname\n let currentDir = __dirname;\n for (let i = 0; i < 10; i++) {\n const nodesPath = path.join(currentDir, 'nodes', framework, pathModuleName);\n if (fs.existsSync(nodesPath)) {\n return nodesPath;\n }\n const parent = path.dirname(currentDir);\n if (parent === currentDir) break;\n currentDir = parent;\n }\n \n return null;\n}\n\n/**\n * Clear the cached nodes base path.\n * Useful for testing or when the environment changes.\n */\nexport function clearNodesBasePathCache(): void {\n cachedNodesBasePath = null;\n}\n", "import Module, { createRequire } from 'module';\nimport path from 'path';\nimport * as fs from 'fs';\n\n// ============================================================================\n// Cortex Module Registration\n// ============================================================================\n\n/**\n * Path to the cortex package root (where package.json is).\n * This is determined at module load time.\n */\nlet cortexPackagePath: string | null = null;\n\n/**\n * Flag to track if the cortex module hook is already installed.\n */\nlet cortexModuleHookInstalled = false;\n\n/**\n * Get the path to the cortex package root.\n * Searches up from the current file to find the package.json with name \"@ha-bits/cortex\".\n */\nfunction getCortexPackagePath(): string {\n if (cortexPackagePath) {\n return cortexPackagePath;\n }\n \n // Start from this file's directory and search up for package.json\n let dir = __dirname;\n for (let i = 0; i < 10; i++) {\n const pkgPath = path.join(dir, 'package.json');\n if (fs.existsSync(pkgPath)) {\n try {\n const pkg = JSON.parse(fs.readFileSync(pkgPath, 'utf-8'));\n if (pkg.name === '@ha-bits/cortex') {\n cortexPackagePath = dir;\n return dir;\n }\n } catch (e) {\n // Continue searching\n }\n }\n const parent = path.dirname(dir);\n if (parent === dir) break;\n dir = parent;\n }\n \n // Fallback: assume we're 2 levels deep in src/utils\n cortexPackagePath = path.resolve(__dirname, '..', '..');\n return cortexPackagePath;\n}\n\n/**\n * Register @ha-bits/cortex in Node's module resolution system.\n * This allows bits modules to `require('@ha-bits/cortex')` without needing\n * symlinks or the package to be installed in node_modules.\n * \n * The hook intercepts resolution requests for '@ha-bits/cortex' and redirects\n * them to the current cortex package.\n */\nexport function registerCortexModule(): void {\n if (cortexModuleHookInstalled) {\n return; // Already installed\n }\n \n const cortexPath = getCortexPackagePath();\n console.log(`\uD83D\uDD17 Registering @ha-bits/cortex module resolution hook (path: ${cortexPath})`);\n \n // IMPORTANT: Capture the current _resolveFilename NOW, not at module load time.\n // This ensures we wrap around tsx's version (or any other loader's version) \n // rather than the original Node.js version.\n const currentResolveFilename = (Module as any)._resolveFilename;\n \n // Patch Module._resolveFilename to intercept @ha-bits/cortex requests\n (Module as any)._resolveFilename = function(request: string, parent: NodeModule, isMain: boolean, options?: any) {\n // Intercept requests for @ha-bits/cortex\n if (request === '@ha-bits/cortex' || request.startsWith('@ha-bits/cortex/')) {\n // For the main package, resolve to the package's main entry\n if (request === '@ha-bits/cortex') {\n const mainPath = path.join(cortexPath, 'src', 'index.ts');\n // When running from dist/pack, use the compiled entry\n if (fs.existsSync(mainPath)) {\n return mainPath;\n }\n const distPath = path.join(cortexPath, 'pack', 'index.cjs');\n if (fs.existsSync(distPath)) {\n return distPath;\n }\n // Fallback to index.js\n const jsPath = path.join(cortexPath, 'index.js');\n if (fs.existsSync(jsPath)) {\n return jsPath;\n }\n }\n \n // For subpath imports like '@ha-bits/cortex/bits/framework'\n const subPath = request.replace('@ha-bits/cortex/', '');\n const possiblePaths = [\n path.join(cortexPath, 'src', subPath + '.ts'),\n path.join(cortexPath, 'src', subPath, 'index.ts'),\n path.join(cortexPath, 'pack', subPath + '.cjs'),\n path.join(cortexPath, subPath + '.js'),\n path.join(cortexPath, subPath, 'index.js'),\n ];\n \n for (const p of possiblePaths) {\n if (fs.existsSync(p)) {\n return p;\n }\n }\n }\n \n // Fall through to the previous resolver (could be tsx's or Node's original)\n return currentResolveFilename.call(this, request, parent, isMain, options);\n };\n \n cortexModuleHookInstalled = true;\n console.log(`\u2713 @ha-bits/cortex module resolution hook installed`);\n}\n\n// ============================================================================\n// Patched Require Functions\n// ============================================================================\n\n/**\n * Creates a patched require function that includes additional search paths for module resolution.\n * This is used to load n8n/activepieces modules with their actual runtime dependencies.\n */\nexport function createPatchedRequire(basePath: string, additionalPaths: string[]): NodeRequire {\n const baseRequire = createRequire(path.join(basePath, 'package.json'));\n \n const originalResolvePaths = (Module as any)._resolveLookupPaths;\n\n console.log(`[customRequire] Creating patched require with paths:`, additionalPaths);\n \n return function patchedRequire(id: string): any {\n (Module as any)._resolveLookupPaths = function(request: string, parent: NodeModule) {\n const result = originalResolvePaths.call(this, request, parent);\n if (result && Array.isArray(result)) {\n for (const p of [...additionalPaths].reverse()) {\n if (!result.includes(p)) result.unshift(p);\n }\n }\n return result;\n };\n \n try {\n delete baseRequire.cache[id];\n return baseRequire(id);\n } finally {\n (Module as any)._resolveLookupPaths = originalResolvePaths;\n }\n } as NodeRequire;\n}\n\n\n/**\n * Require code from `pathToCode` while resolving dependencies from `searchPaths`.\n * Uses the actual n8n/activepieces runtime dependencies from node_modules.\n */\nexport function patchedRequire(pathToCode: string, searchPaths: string[]): unknown {\n const originalResolvePaths = (Module as any)._resolveLookupPaths;\n \n // Patch to inject our search paths\n (Module as any)._resolveLookupPaths = function(request: string, parent: NodeModule) {\n const result = originalResolvePaths.call(this, request, parent);\n if (result && Array.isArray(result)) {\n for (const p of [...searchPaths].reverse()) {\n if (!result.includes(p)) result.unshift(p);\n }\n }\n return result;\n };\n\n try {\n // Create require from the first search path\n const customRequire = createRequire(path.join(searchPaths[0], 'package.json'));\n delete customRequire.cache[pathToCode];\n return customRequire(pathToCode);\n } finally {\n // Restore\n (Module as any)._resolveLookupPaths = originalResolvePaths;\n }\n}\n\n\n/**\n * Simple require using createRequire from a specific search path.\n * Creates require from the module's directory so it can resolve its dependencies.\n */\nexport function simpleRequire(pathToCode: string, searchPath: string) {\n const dynamicRequire = createRequire(path.join(searchPath, \"package.json\"));\n delete dynamicRequire.cache[pathToCode];\n const nodeModule = dynamicRequire(pathToCode);\n return nodeModule;\n}\n\n/**\n * Custom require that loads modules from a specific search path.\n * Uses createRequire to create a require function rooted at the module's directory,\n * ensuring all dependencies resolve consistently from a single location.\n * \n * This avoids patching global Module._resolveLookupPaths which can cause issues\n * when the same dependency (e.g., semver) gets required from different paths\n * during the module loading chain.\n */\nexport function customRequire(pathToCode: string, searchPath: string) {\n console.log(`Custom requiring ${pathToCode} with search path ${searchPath}`);\n const flatMethod = true;\n // Use createRequire rooted at the search path - this ensures all dependencies\n // resolve relative to the module's location without patching global resolution\n if(flatMethod){\n const dynamicRequire = createRequire(path.join(searchPath, 'package.json'));\n \n // Clear cache to ensure fresh load\n delete dynamicRequire.cache[pathToCode];\n \n // Also clear any cached versions of the module by full path\n const resolvedPath = dynamicRequire.resolve(pathToCode);\n delete dynamicRequire.cache[resolvedPath];\n \n return dynamicRequire(pathToCode);\n }\n\n else {\n // Build list of search paths:\n // 1. The provided searchPath (e.g., module's src directory)\n // 2. The parent node_modules directory for resolving peer dependencies\n const searchPaths = [searchPath];\n \n // Find node_modules in the path hierarchy\n let currentPath = searchPath;\n while (currentPath && currentPath !== path.dirname(currentPath)) {\n const nodeModulesPath = path.join(currentPath, 'node_modules');\n if (fs.existsSync(nodeModulesPath)) {\n searchPaths.push(nodeModulesPath);\n }\n // Also check if currentPath itself is within node_modules\n if (path.basename(path.dirname(currentPath)) === 'node_modules' || \n path.basename(path.dirname(path.dirname(currentPath))) === 'node_modules') {\n // Find the root node_modules\n let nmPath = currentPath;\n while (nmPath && !nmPath.endsWith('/node_modules') && !nmPath.endsWith('\\\\node_modules')) {\n nmPath = path.dirname(nmPath);\n }\n if (nmPath && nmPath.endsWith('node_modules')) {\n if (!searchPaths.includes(nmPath)) {\n searchPaths.push(nmPath);\n }\n }\n }\n currentPath = path.dirname(currentPath);\n }\n \n const patchedReq = createPatchedRequire(pathToCode, searchPaths);\n return patchedReq(pathToCode);\n}\n}\n", "import * as fs from '@ha-bits/bindings/fs';\nimport * as path from '@ha-bits/bindings/path';\nimport { exec as execAsync } from '@ha-bits/bindings/shell';\nimport { getModuleName } from './moduleLoader';\nimport { getNodesPath, getModuleFullPath, getNodesBasePath, getLocalModulePath, npmInstall } from './utils';\nimport { registerCortexModule } from './customRequire';\n\n// ============================================================================\n// ActivePieces Dependency Linking\n// ============================================================================\n\n/**\n * ActivePieces peer dependencies that should be linked from cortex's node_modules.\n * These packages are already bundled in cortex and should be shared with pieces.\n */\nconst ACTIVEPIECES_PEER_DEPS = [\n '@activepieces/pieces-common',\n '@activepieces/pieces-framework',\n '@activepieces/shared'\n];\n\n/**\n * n8n peer dependencies that should be linked from the base node_modules.\n * These packages are required by n8n community nodes.\n */\nconst N8N_PEER_DEPS = [\n 'n8n-workflow',\n 'n8n-core',\n 'moment-timezone', // Often required by community nodes\n // Note: n8n-nodes-base is too large (300+ nodes, crashes npm with OOM)\n // Individual nodes should be installed separately if needed\n //'n8n-nodes-base'\n];\n\n/**\n * Get the path to base node_modules where ActivePieces packages should be installed.\n */\nfunction getActivepiecesPackagesPath(): string | null {\n const basePath = path.join(getNodesBasePath(), 'node_modules');\n const testPath = path.join(basePath, '@activepieces', 'pieces-framework');\n if (fs.existsSync(testPath)) {\n return basePath;\n }\n return null;\n}\n\n/**\n * Ensure ActivePieces peer dependencies are installed in the base node_modules.\n * Similar to ensureN8nDepsInstalled but for ActivePieces packages.\n */\nasync function ensureActivepiecesDepsInstalled(): Promise<string | null> {\n const basePath = getNodesBasePath();\n const baseNodeModules = path.join(basePath, 'node_modules');\n \n // Check if @activepieces/pieces-framework is already installed\n const piecesFrameworkPath = path.join(baseNodeModules, '@activepieces', 'pieces-framework');\n if (fs.existsSync(piecesFrameworkPath)) {\n console.log(`\u2713 @activepieces/pieces-framework already installed at ${baseNodeModules}`);\n return baseNodeModules;\n }\n \n console.log(`\uD83D\uDCE6 Installing ActivePieces peer dependencies to ${basePath}...`);\n \n // ============================================================================\n // \u2139\uFE0F LICENSE INFO - ActivePieces has mixed licensing!\n // ============================================================================\n // ActivePieces framework (@activepieces/pieces-framework, etc.) is MIT licensed.\n // However, some pieces may have different licenses:\n // \n // \u2705 OPEN SOURCE (MIT) - Safe to use and redistribute:\n // - Community pieces in @activepieces/piece-* packages\n // - Most integrations (OpenAI, Slack, Google, etc.)\n // \n // \u26A0\uFE0F CLOSED SOURCE / PREMIUM - Check before using:\n // - Some enterprise pieces may have restricted licenses\n // - Pieces marked as \"premium\" in the ActivePieces platform\n // - Custom pieces from third parties\n // \n // Always verify the license of each piece you use:\n // - Check the piece's package.json for license field\n // - Review https://github.com/activepieces/activepieces\n // ============================================================================\n console.log(`\\n${'='.repeat(80)}`);\n console.log(`\u2139\uFE0F LICENSE INFO: ActivePieces has MIXED licensing!`);\n console.log(`${'='.repeat(80)}`);\n console.log(`ActivePieces framework (@activepieces/pieces-framework) is MIT licensed.`);\n console.log(`However, SOME PIECES may have DIFFERENT or RESTRICTED licenses!`);\n console.log(``);\n console.log(`\u2705 OPEN SOURCE (MIT) - Safe to redistribute:`);\n console.log(` - Community pieces in @activepieces/piece-* packages`);\n console.log(` - Most integrations (OpenAI, Slack, Google, etc.)`);\n console.log(``);\n console.log(`\u26A0\uFE0F CLOSED SOURCE / PREMIUM / EE - Check before using:`);\n console.log(` - Some enterprise pieces have restricted licenses`);\n console.log(` - Pieces marked as \"premium\" in ActivePieces platform`);\n console.log(` - Custom pieces from third parties`);\n console.log(``);\n console.log(`Always verify the license of EACH piece before redistribution!`);\n console.log(`${'='.repeat(80)}\\n`);\n\n try {\n // Install all activepieces peer deps to the base path\n // Using specific versions for compatibility\n const depsToInstall = [\n '@activepieces/pieces-common@^0.11.0',\n '@activepieces/pieces-framework@^0.23.0',\n '@activepieces/shared@^0.30.4'\n ].join(' ');\n \n await npmInstall(depsToInstall, { \n prefix: basePath, \n legacyPeerDeps: true, \n production: true,\n timeout: 300000\n });\n console.log(`\u2713 ActivePieces peer dependencies installed`);\n return baseNodeModules;\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Failed to install ActivePieces peer dependencies: ${error.message}`);\n return null;\n }\n}\n\n/**\n * Link ActivePieces peer dependencies from base node_modules to a piece module.\n * This resolves the peer dependency issue where pieces need @activepieces/* packages.\n * \n * @param modulePath - Path to the module where peer deps should be linked\n * @param moduleName - Name of the module (for logging)\n */\nasync function linkActivepiecesDeps(modulePath: string, moduleName: string): Promise<void> {\n // First ensure ActivePieces deps are installed (like n8n pattern)\n const baseNodeModules = await ensureActivepiecesDepsInstalled();\n \n if (!baseNodeModules) {\n console.warn(`\u26A0\uFE0F Could not find or install ActivePieces peer dependencies`);\n return;\n }\n \n const cortexNodeModules = baseNodeModules;\n\n console.log(`\uD83D\uDD17 Linking ActivePieces peer dependencies for ${moduleName}...`);\n \n // Link at module's own node_modules level\n const moduleNodeModules = path.join(modulePath, 'node_modules');\n await linkDepsToDirectory(moduleNodeModules, cortexNodeModules, moduleName);\n \n // Also link at parent node_modules level (where npm hoists dependencies)\n // This handles the case where the module is in node_modules/@scope/package\n // and Node.js looks in the parent node_modules first\n const parentNodeModules = path.dirname(path.dirname(modulePath));\n if (parentNodeModules.endsWith('node_modules')) {\n console.log(`\uD83D\uDD17 Also linking at parent node_modules: ${parentNodeModules}`);\n await linkDepsToDirectory(parentNodeModules, cortexNodeModules, moduleName);\n }\n}\n\n\n// ============================================================================\n// Bits Dependency Resolution\n// ============================================================================\n\n/**\n * Ensure @ha-bits/cortex is resolvable by bits modules.\n * \n * Instead of creating symlinks, this uses Node's module resolution hook\n * to intercept requests for '@ha-bits/cortex' and resolve them to the\n * currently running cortex package. This is cleaner because:\n * - No filesystem operations needed\n * - Works immediately without race conditions\n * - No cleanup required\n * - Works regardless of where modules are installed\n * \n * @param modulePath - Path to the module (for logging only)\n * @param moduleName - Name of the module (for logging)\n */\nasync function linkBitsDeps(modulePath: string, moduleName: string): Promise<void> {\n // Register the cortex module resolution hook (idempotent - safe to call multiple times)\n registerCortexModule();\n console.log(`\u2713 Bits module ${moduleName} can now resolve @ha-bits/cortex`);\n}\n\n/**\n * Link ActivePieces peer dependencies to a specific node_modules directory.\n */\nasync function linkDepsToDirectory(targetNodeModules: string, sourceNodeModules: string, moduleName: string): Promise<void> {\n // Skip if source and target are the same (would create self-referencing symlinks)\n if (path.resolve(targetNodeModules) === path.resolve(sourceNodeModules)) {\n console.log(`\u2713 Source and target are same, no linking needed at ${targetNodeModules}`);\n return;\n }\n \n const activepiecesDir = path.join(targetNodeModules, '@activepieces');\n \n // Create node_modules/@activepieces directory if it doesn't exist\n if (!fs.existsSync(activepiecesDir)) {\n fs.mkdirSync(activepiecesDir, { recursive: true });\n }\n \n for (const dep of ACTIVEPIECES_PEER_DEPS) {\n const [scope, pkgName] = dep.split('/');\n const sourcePackagePath = path.join(sourceNodeModules, scope, pkgName);\n const targetPackagePath = path.join(targetNodeModules, scope, pkgName);\n \n if (!fs.existsSync(sourcePackagePath)) {\n console.warn(`\u26A0\uFE0F Source package not found: ${sourcePackagePath}`);\n continue;\n }\n \n // Check if source has actual content (not just node_modules folder)\n const sourcePackageJson = path.join(sourcePackagePath, 'package.json');\n if (!fs.existsSync(sourcePackageJson)) {\n console.warn(`\u26A0\uFE0F Source package incomplete (no package.json): ${sourcePackagePath}`);\n continue;\n }\n \n // Remove existing package if present (might be a symlink, incomplete install, or real install)\n if (fs.existsSync(targetPackagePath)) {\n try {\n const stats = fs.lstatSync(targetPackagePath);\n if (stats.isSymbolicLink()) {\n // Already linked, check if it points to correct location\n const linkTarget = fs.readlinkSync(targetPackagePath);\n if (linkTarget === sourcePackagePath || linkTarget.endsWith(path.join(scope, pkgName))) {\n console.log(`\u2713 ${dep} already linked at ${targetNodeModules}`);\n continue;\n }\n }\n // Check if it's an incomplete install (has node_modules but no package.json)\n const targetPackageJson = path.join(targetPackagePath, 'package.json');\n if (!fs.existsSync(targetPackageJson)) {\n console.log(`\uD83D\uDD04 Replacing incomplete ${dep} at ${targetPackagePath}`);\n }\n fs.rmSync(targetPackagePath, { recursive: true, force: true });\n } catch (e) {\n // Ignore errors when removing\n }\n }\n \n // Create symlink to the cortex node_modules package\n try {\n fs.symlinkSync(sourcePackagePath, targetPackagePath, 'dir');\n console.log(`\u2713 Linked ${dep} to ${targetNodeModules}`);\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Failed to link ${dep}: ${error.message}`);\n }\n }\n}\n\n/**\n * Ensures ActivePieces peer dependencies are linked after npm install.\n * This should be called AFTER npm install to override any installed peer deps.\n * \n * @param modulePath - Path to the module\n * @param moduleName - Name of the module (for logging)\n */\nasync function ensureActivepiecesDepsLinked(modulePath: string, moduleName: string): Promise<void> {\n await linkActivepiecesDeps(modulePath, moduleName);\n}\n\n// Bits\nasync function ensureBitsDepsLinked(modulePath: string, moduleName: string): Promise<void> {\n await linkBitsDeps(modulePath, moduleName);\n}\n\n\n\n/**\n * Public function to ensure ActivePieces dependencies are installed.\n * This should be called before dynamically importing @activepieces/* modules.\n */\nexport async function ensureActivepiecesReady(): Promise<string | null> {\n return await ensureActivepiecesDepsInstalled();\n}\n\n// ============================================================================\n// n8n Dependency Linking\n// ============================================================================\n\n/**\n * Get the path to base node_modules where n8n packages should be installed.\n */\nfunction getN8nPackagesPath(): string | null {\n const basePath = path.join(getNodesBasePath(), 'node_modules');\n const testPath = path.join(basePath, 'n8n-workflow');\n if (fs.existsSync(testPath)) {\n return basePath;\n }\n return null;\n}\n\n/**\n * Ensure n8n peer dependencies are installed in the base node_modules.\n */\nasync function ensureN8nDepsInstalled(): Promise<string | null> {\n const basePath = getNodesBasePath();\n const baseNodeModules = path.join(basePath, 'node_modules');\n \n // Check if n8n-workflow is already installed\n const n8nWorkflowPath = path.join(baseNodeModules, 'n8n-workflow');\n if (fs.existsSync(n8nWorkflowPath)) {\n console.log(`\u2713 n8n-workflow already installed at ${baseNodeModules}`);\n return baseNodeModules;\n }\n \n console.log(`\uD83D\uDCE6 Installing n8n peer dependencies to ${basePath}...`);\n \n // ============================================================================\n // \u26A0\uFE0F LICENSE WARNING - n8n is NOT open source!\n // ============================================================================\n // n8n and its packages (n8n-workflow, n8n-core, n8n-nodes-base) are licensed\n // under the Sustainable Use License (SUL), which is NOT an open source license.\n // \n // You CANNOT:\n // - Redistribute n8n packages in commercial products without a license\n // - Offer n8n as a service without explicit permission\n // - Use n8n-nodes-base in production without proper licensing\n // \n // If you do not have a valid n8n license for your use case, you should:\n // 1. Use only Apache 2.0 / MIT licensed modules (ActivePieces pieces, Habits bits)\n // 2. Purchase an n8n license from https://n8n.io/pricing\n // 3. Remove n8n dependencies from your workflow\n // \n // See: https://github.com/n8n-io/n8n/blob/master/LICENSE.md\n // ============================================================================\n console.log(`\\n${'='.repeat(80)}`);\n console.log(`\u26A0\uFE0F LICENSE WARNING: n8n is NOT open source!`);\n console.log(`${'='.repeat(80)}`);\n console.log(`n8n packages are licensed under the Sustainable Use License (SUL).`);\n console.log(`You CANNOT redistribute or use n8n commercially without a license.`);\n console.log(`If you don't have a valid n8n license, you can't use this habit for non-personal usage.`);\n console.log(`Use Apache 2.0/MIT licensed alternatives: ActivePieces pieces or Habits bits.`);\n console.log(`${'='.repeat(80)}\\n`);\n\n try {\n // Install n8n-workflow, n8n-core, and moment-timezone to the base path\n await npmInstall('n8n-workflow n8n-core moment-timezone', { \n prefix: basePath, \n legacyPeerDeps: true, \n production: true,\n timeout: 300000\n });\n console.log(`\u2713 n8n peer dependencies installed`);\n return baseNodeModules;\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Failed to install n8n peer dependencies: ${error.message}`);\n return null;\n }\n}\n\n/**\n * Link n8n peer dependencies from base node_modules to a module.\n */\nasync function linkN8nDeps(modulePath: string, moduleName: string): Promise<void> {\n // First ensure n8n deps are installed\n const baseNodeModules = await ensureN8nDepsInstalled();\n \n if (!baseNodeModules) {\n console.warn(`\u26A0\uFE0F Could not find or install n8n peer dependencies`);\n return;\n }\n\n console.log(`\uD83D\uDD17 Linking n8n peer dependencies for ${moduleName}...`);\n \n // Link at module's own node_modules level\n const moduleNodeModules = path.join(modulePath, 'node_modules');\n if (!fs.existsSync(moduleNodeModules)) {\n fs.mkdirSync(moduleNodeModules, { recursive: true });\n }\n \n for (const dep of N8N_PEER_DEPS) {\n const sourcePackagePath = path.join(baseNodeModules, dep);\n const targetPackagePath = path.join(moduleNodeModules, dep);\n \n if (!fs.existsSync(sourcePackagePath)) {\n console.warn(`\u26A0\uFE0F Source package not found: ${sourcePackagePath}`);\n continue;\n }\n \n // Check if already linked or exists\n if (fs.existsSync(targetPackagePath)) {\n try {\n const stats = fs.lstatSync(targetPackagePath);\n if (stats.isSymbolicLink()) {\n console.log(`\u2713 ${dep} already linked`);\n continue;\n }\n // Remove existing if not a symlink\n fs.rmSync(targetPackagePath, { recursive: true, force: true });\n } catch (e) {\n // Ignore\n }\n }\n \n // Create symlink\n try {\n fs.symlinkSync(sourcePackagePath, targetPackagePath, 'dir');\n console.log(`\u2713 Linked ${dep}`);\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Failed to link ${dep}: ${error.message}`);\n }\n }\n}\n\n/**\n * Ensures n8n peer dependencies are linked after npm install.\n */\nasync function ensureN8nDepsLinked(modulePath: string, moduleName: string): Promise<void> {\n await linkN8nDeps(modulePath, moduleName);\n}\n\n\nexport interface ModuleDefinition {\n framework: string;\n source: 'github' | 'npm' | 'local' | 'link';\n repository: string; // GitHub URL for 'github' source, package name for 'npm'/'link' source, module name for 'local' source\n /** \n * Optional custom npm registry URL for 'npm' source.\n * If not provided, uses HABITS_NPM_REGISTRY_URL environment variable,\n * or falls back to https://registry.npmjs.org\n */\n registry?: string;\n}\n\nexport async function cloneModule(\n moduleDefinition: ModuleDefinition,\n targetDir: string\n): Promise<string> {\n const { repository, source } = moduleDefinition;\n const name = getModuleName(moduleDefinition);\n\n if (source !== 'github') {\n throw new Error(`cloneModule only supports GitHub sources, got: ${source}`);\n }\n\n if (!repository) {\n throw new Error(`Module ${name} has no repository URL`);\n }\n\n const modulePath = path.join(targetDir, name);\n\n // Check if already cloned\n if (fs.existsSync(modulePath)) {\n console.log(`\u2713 Module ${name} already cloned at ${modulePath}`);\n return modulePath;\n }\n\n console.log(`\uD83D\uDCE6 Cloning ${name} from ${repository}...`);\n\n try {\n // Create target directory if it doesn't exist\n if (!fs.existsSync(targetDir)) {\n fs.mkdirSync(targetDir, { recursive: true });\n }\n\n // Clone the repository\n const { stdout, stderr } = await execAsync(\n `git clone ${repository} ${modulePath}`,\n { cwd: targetDir }\n );\n\n if (stderr && !stderr.includes('Cloning into')) {\n console.warn(`Clone warnings: ${stderr}`);\n }\n\n console.log(`\u2713 Successfully cloned ${name}`);\n\n // Install dependencies if package.json exists\n if (fs.existsSync(path.join(modulePath, 'package.json'))) {\n console.log(`\uD83D\uDCE6 Installing dependencies for ${name}...`);\n try {\n // To get around \"zod\" related version-issues in activepieces, legacy peer deps is used\n await npmInstall(undefined, { cwd: modulePath, legacyPeerDeps: true, includePeer: true, timeout: 180000 });\n console.log(`\u2713 Dependencies installed for ${name}`);\n \n // Link ActivePieces peer dependencies if this is an activepieces or bits module\n if (moduleDefinition.framework === 'activepieces' ) {\n await ensureActivepiecesDepsLinked(modulePath, name);\n }\n if(moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(modulePath, name);\n }\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Warning: Failed to install dependencies for ${name}: ${error.message}`);\n // Don't fail the entire process, module might still work\n }\n }\n\n // Auto-detect subPath if needed (for activepieces modules)\n const subPath = await detectSubPath(modulePath, moduleDefinition.framework);\n const workingDir = subPath ? path.join(modulePath, subPath) : modulePath;\n\n return workingDir;\n } catch (error: any) {\n throw new Error(`Failed to clone ${name}: ${error.message}`);\n }\n}\n\nexport async function buildModule(\n moduleDefinition: ModuleDefinition,\n modulePath: string\n): Promise<void> {\n const name = getModuleName(moduleDefinition);\n\n // Run npm install --production\n console.log(`\uD83D\uDCE6 Installing production dependencies for ${name}...`)\n try {\n await npmInstall(undefined, { cwd: modulePath, legacyPeerDeps: true, includePeer: true, production: true, timeout: 120000 });\n \n // Link peer dependencies based on framework\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(modulePath, name);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(modulePath, name);\n }\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Warning: Failed to install production dependencies for ${name}: ${error.message}`);\n // Don't fail the entire process, module might still work\n }\n // Auto-detect build command\n const buildCommand = await detectBuildCommand(modulePath);\n \n if (!buildCommand) {\n console.log(`\u26A0\uFE0F No build command detected for ${name}, skipping build`);\n return;\n }\n\n // Check if already built by looking for common build outputs\n if (await isAlreadyBuilt(modulePath)) {\n console.log(`\u2713 Module ${name} already built`);\n return;\n }\n\n console.log(`\uD83D\uDD28 Building ${name} with command: ${buildCommand}`);\n\n try {\n const { stdout, stderr } = await execAsync(buildCommand, {\n cwd: modulePath,\n maxBuffer: 1024 * 1024 * 10, // 10MB buffer\n });\n\n if (stderr && !stderr.includes('npm warn')) {\n console.warn(`Build warnings for ${name}:`, stderr.substring(0, 500));\n }\n\n console.log(`\u2713 Successfully built ${name}`);\n } catch (error: any) {\n throw new Error(`Failed to build ${name}: ${error.message}`);\n }\n}\n\nexport async function ensureModuleReady(\n moduleDefinition: ModuleDefinition\n): Promise<string> {\n const moduleName = getModuleName(moduleDefinition);\n \n console.log(`\\n\uD83D\uDD0D ensureModuleReady called:`);\n console.log(` Module: ${moduleName}`);\n console.log(` Source: ${moduleDefinition.source}`);\n console.log(` Repository: ${moduleDefinition.repository}`);\n console.log(` Framework: ${moduleDefinition.framework}`);\n \n if (moduleDefinition.source === 'github') {\n console.log(`\\n\uD83D\uDCC2 Processing GitHub module: ${moduleName}`);\n // Clone the module from GitHub to framework directory\n const baseDir = getNodesPath(moduleDefinition.framework);\n const modulePath = path.join(baseDir, moduleName);\n console.log(` Base directory: ${baseDir}`);\n console.log(` Module path: ${modulePath}`);\n \n // Check if already exists\n if (fs.existsSync(modulePath)) {\n console.log(`\u2713 GitHub module ${moduleName} already exists at ${modulePath}`);\n // Still check if built\n if (!await isAlreadyBuilt(modulePath)) {\n await buildModule(moduleDefinition, modulePath);\n }\n return modulePath;\n }\n \n const clonedPath = await cloneModule(moduleDefinition, baseDir);\n \n // Build the module\n await buildModule(moduleDefinition, clonedPath);\n \n return clonedPath;\n } else if (moduleDefinition.source === 'npm') {\n console.log(`\\n\uD83D\uDCE6 Processing npm module: ${moduleName}`);\n // Install the module from npm to nodes/{framework} directory\n const baseDir = getNodesPath(moduleDefinition.framework);\n const modulePath = path.join(baseDir, moduleName);\n console.log(` Base directory: ${baseDir}`);\n console.log(` Module path: ${modulePath}`);\n \n // Check if already exists\n if (fs.existsSync(modulePath)) {\n console.log(`\u2713 npm module ${moduleName} already exists at ${modulePath}`);\n // Ensure peer dependencies are linked even for existing modules\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(modulePath, moduleName);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(modulePath, moduleName);\n } else if (moduleDefinition.framework === 'n8n') {\n await ensureN8nDepsLinked(modulePath, moduleName);\n }\n return modulePath;\n }\n \n const installedPath = await installNpmModule(moduleDefinition, baseDir);\n \n return installedPath;\n } else if (moduleDefinition.source === 'local') {\n // Local modules are in the workspace's nodes/{framework} directory\n // We need to find them and install them to the nodes base path\n const targetModulePath = getModuleFullPath(moduleDefinition.framework, moduleName);\n \n // Check if already installed in target location\n if (fs.existsSync(targetModulePath)) {\n console.log(`\u2713 Local module ${moduleName} already installed at ${targetModulePath}`);\n // Ensure peer dependencies are available even for existing modules\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(targetModulePath, moduleName);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(targetModulePath, moduleName);\n } else if (moduleDefinition.framework === 'n8n') {\n await ensureN8nDepsLinked(targetModulePath, moduleName);\n }\n return targetModulePath;\n }\n \n // Find the local module in the workspace\n const localSourcePath = getLocalModulePath(moduleDefinition.framework, moduleName);\n \n if (!localSourcePath) {\n throw new Error(\n `Local module not found: ${moduleName}. ` +\n `Searched in nodes/${moduleDefinition.framework}/ directory. ` +\n `You can also set HABITS_LOCAL_NODES_PATH environment variable.`\n );\n }\n \n console.log(`\\n\uD83D\uDCE6 Installing local module: ${moduleName}`);\n console.log(` Source: ${localSourcePath}`);\n console.log(` Target: ${targetModulePath}`);\n \n // Ensure target parent directory exists\n const targetParentDir = path.dirname(targetModulePath);\n if (!fs.existsSync(targetParentDir)) {\n fs.mkdirSync(targetParentDir, { recursive: true });\n }\n \n // Copy the local module to the target location\n fs.cpSync(localSourcePath, targetModulePath, { recursive: true });\n \n // Install dependencies for the module\n if (fs.existsSync(path.join(targetModulePath, 'package.json'))) {\n console.log(`\uD83D\uDCE6 Installing dependencies for ${moduleName}...`);\n try {\n await npmInstall(undefined, { cwd: targetModulePath, legacyPeerDeps: true, includePeer: true, timeout: 120000 });\n console.log(`\u2713 Dependencies installed for ${moduleName}`);\n \n // Link peer dependencies based on framework\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(targetModulePath, moduleName);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(targetModulePath, moduleName);\n }\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Warning: Failed to install dependencies for ${moduleName}: ${error.message}`);\n // Still try to link peer dependencies\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(targetModulePath, moduleName);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(targetModulePath, moduleName);\n }\n }\n } else {\n // No package.json, but still try to link peer deps\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(targetModulePath, moduleName);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(targetModulePath, moduleName);\n }\n }\n \n console.log(`\u2713 Local module ${moduleName} installed at ${targetModulePath}`);\n return targetModulePath;\n } else if (moduleDefinition.source === 'link') {\n console.log(`\\n\uD83D\uDD17 Processing linked module: ${moduleName}`);\n // Use npm link to use a globally linked package\n const baseDir = getNodesPath(moduleDefinition.framework);\n const modulePath = path.join(baseDir, moduleName);\n console.log(` Base directory: ${baseDir}`);\n console.log(` Module path: ${modulePath}`);\n \n // Check if already linked/exists\n if (fs.existsSync(modulePath)) {\n console.log(`\u2713 Linked module ${moduleName} already exists at ${modulePath}`);\n // Ensure peer dependencies are linked even for existing modules\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(modulePath, moduleName);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(modulePath, moduleName);\n } else if (moduleDefinition.framework === 'n8n') {\n await ensureN8nDepsLinked(modulePath, moduleName);\n }\n return modulePath;\n }\n \n const linkedPath = await linkNpmModule(moduleDefinition, baseDir);\n \n return linkedPath;\n } else {\n throw new Error(`Unknown source type: ${moduleDefinition.source}`);\n }\n}\n\n// Helper function to detect subPath for frameworks like activepieces\nasync function detectSubPath(modulePath: string, framework: string): Promise<string | null> {\n if (framework === 'activepieces' || framework === 'bits') {\n // Check for common activepieces structure\n const possibleSubPaths = [\n 'packages/pieces/community',\n 'packages/pieces',\n 'pieces/community',\n 'pieces'\n ];\n \n for (const subPath of possibleSubPaths) {\n const fullPath = path.join(modulePath, subPath);\n if (fs.existsSync(fullPath)) {\n // Check if there are piece folders in this path\n try {\n const items = fs.readdirSync(fullPath);\n if (items.length > 0) {\n return subPath;\n }\n } catch (error) {\n continue;\n }\n }\n }\n }\n return null;\n}\n\n// Helper function to detect build command from package.json\nasync function detectBuildCommand(modulePath: string): Promise<string | null> {\n const packageJsonPath = path.join(modulePath, 'package.json');\n \n if (!fs.existsSync(packageJsonPath)) {\n return null;\n }\n\n try {\n const packageJson = JSON.parse(fs.readFileSync(packageJsonPath, 'utf-8'));\n const scripts = packageJson.scripts || {};\n\n // Try common build script names in order of preference\n const buildScriptNames = ['build', 'compile', 'tsc', 'webpack', 'rollup'];\n \n for (const scriptName of buildScriptNames) {\n if (scripts[scriptName]) {\n return `npm run ${scriptName}`;\n }\n }\n\n // Fallback: if no build script, run install only\n return 'npm install';\n } catch (error) {\n return 'npm install';\n }\n}\n\n// Helper function to check if module is already built\nasync function isAlreadyBuilt(modulePath: string): Promise<boolean> {\n const commonBuildDirs = ['dist', 'build', 'lib', 'out'];\n const commonMainFiles = [\n 'dist/index.js',\n 'dist/main.js', \n 'dist/nodes',\n 'build/index.js',\n 'lib/index.js',\n 'out/index.js'\n ];\n\n // Check for build directories with content\n for (const buildDir of commonBuildDirs) {\n const buildDirPath = path.join(modulePath, buildDir);\n if (fs.existsSync(buildDirPath)) {\n try {\n const items = fs.readdirSync(buildDirPath);\n if (items.length > 0) {\n return true;\n }\n } catch (error) {\n continue;\n }\n }\n }\n\n // Check for main files\n for (const mainFile of commonMainFiles) {\n const mainFilePath = path.join(modulePath, mainFile);\n if (fs.existsSync(mainFilePath)) {\n return true;\n }\n }\n\n return false;\n}\n\n/**\n * Fix package.json main entry if it points to .ts but .js exists.\n * This handles packages that were incorrectly published with TypeScript as main entry.\n */\nasync function fixPackageJsonMainEntry(modulePath: string): Promise<void> {\n const packageJsonPath = path.join(modulePath, 'package.json');\n if (!fs.existsSync(packageJsonPath)) {\n return;\n }\n \n try {\n const packageJson = JSON.parse(fs.readFileSync(packageJsonPath, 'utf-8'));\n const mainEntry = packageJson.main;\n \n if (mainEntry && mainEntry.endsWith('.ts')) {\n const tsPath = path.join(modulePath, mainEntry);\n const jsPath = tsPath.replace(/\\.ts$/, '.js');\n \n // If .ts doesn't exist but .js does, fix the main entry\n if (!fs.existsSync(tsPath) && fs.existsSync(jsPath)) {\n const newMain = mainEntry.replace(/\\.ts$/, '.js');\n packageJson.main = newMain;\n if (packageJson.types && packageJson.types.endsWith('.ts')) {\n packageJson.types = packageJson.types.replace(/\\.ts$/, '.d.ts');\n }\n fs.writeFileSync(packageJsonPath, JSON.stringify(packageJson, null, 2));\n console.log(`\uD83D\uDD27 Fixed package.json main entry: ${mainEntry} -> ${newMain}`);\n }\n }\n } catch (error: any) {\n console.warn(`\u26A0\uFE0F Failed to fix package.json main entry: ${error.message}`);\n }\n}\n\n// Install npm module to local directory\nasync function installNpmModule(\n moduleDefinition: ModuleDefinition,\n targetDir: string\n): Promise<string> {\n const { repository: packageName, registry: definedRegistry } = moduleDefinition;\n const name = getModuleName(moduleDefinition);\n \n // Determine registry URL: module definition > environment variable > default (npmjs)\n const registry = definedRegistry || process.env.HABITS_NPM_REGISTRY_URL || undefined;\n \n console.log(`\\n\uD83D\uDCE6 installNpmModule called:`);\n console.log(` Package name: ${packageName}`);\n console.log(` Module name: ${name}`);\n console.log(` Target dir: ${targetDir}`);\n console.log(` Registry: ${registry || 'https://registry.npmjs.org (default)'}`);\n \n if (!packageName) {\n throw new Error(`Module ${name} has no package name`);\n }\n \n // Validate that this is not a GitHub URL being passed as npm package\n if (packageName.includes('github.com') || packageName.startsWith('git@') || packageName.startsWith('https://')) {\n throw new Error(`Invalid npm package name: ${packageName}. This looks like a GitHub URL. Use source: 'github' instead.`);\n }\n\n const modulePath = path.join(targetDir, name);\n console.log(` Full module path: ${modulePath}`);\n\n // Check if already installed\n if (fs.existsSync(modulePath)) {\n console.log(`\u2713 Module ${name} already installed at ${modulePath}`);\n return modulePath;\n }\n const prefix = getNodesBasePath();\n console.log(`\uD83D\uDCE6 Installing ${name} from npm registry (${packageName}) to ${prefix}...`);\n\n try {\n // Create target directory if it doesn't exist\n if (!fs.existsSync(targetDir)) {\n fs.mkdirSync(targetDir, { recursive: true });\n }\n\n // Ensure prefix directory has a package.json (required for npm install)\n const prefixPackageJson = path.join(prefix, 'package.json');\n if (!fs.existsSync(prefixPackageJson)) {\n fs.mkdirSync(prefix, { recursive: true });\n fs.writeFileSync(prefixPackageJson, JSON.stringify({ \n name: 'habits-nodes', \n version: '1.0.0', \n private: true\n }, null, 2));\n }\n\n // Install directly to prefix with legacyPeerDeps and production mode to minimize dependencies\n const { stdout, stderr } = await npmInstall(packageName, { \n prefix, \n legacyPeerDeps: true, \n production: true,\n timeout: 300000, // 5 minute timeout\n registry // Use custom registry if provided\n });\n\n if (stderr && !stderr.includes('npm warn')) {\n console.warn(`Install warnings: ${stderr}`);\n }\n\n // Package is now installed directly at prefix/node_modules/package-name\n // Verify installation\n if (!fs.existsSync(modulePath)) {\n throw new Error(`Package ${packageName} was not installed correctly at ${modulePath}`);\n }\n\n // Fix package.json if main entry points to .ts but .js exists\n await fixPackageJsonMainEntry(modulePath);\n\n // Link peer dependencies based on framework\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(modulePath, name);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(modulePath, name);\n } else if (moduleDefinition.framework === 'n8n') {\n await ensureN8nDepsLinked(modulePath, name);\n }\n\n console.log(`\u2713 Successfully installed ${name} from npm at ${modulePath}`);\n return modulePath;\n } catch (error: any) {\n throw new Error(`Failed to install ${name}: ${error.message}`);\n }\n}\n\n// Link a globally linked npm module to local directory\nasync function linkNpmModule(\n moduleDefinition: ModuleDefinition,\n targetDir: string\n): Promise<string> {\n const { repository: packageName } = moduleDefinition;\n const name = getModuleName(moduleDefinition);\n \n console.log(`\\n\uD83D\uDD17 linkNpmModule called:`);\n console.log(` Package name: ${packageName}`);\n console.log(` Module name: ${name}`);\n console.log(` Target dir: ${targetDir}`);\n \n if (!packageName) {\n throw new Error(`Module ${name} has no package name`);\n }\n\n const modulePath = path.join(targetDir, name);\n console.log(` Full module path: ${modulePath}`);\n\n // Check if already linked\n if (fs.existsSync(modulePath)) {\n console.log(`\u2713 Module ${name} already linked at ${modulePath}`);\n return modulePath;\n }\n\n const prefix = getNodesBasePath();\n console.log(`\uD83D\uDD17 Linking ${name} from global npm link (${packageName}) to ${prefix}...`);\n\n try {\n // Create target directory if it doesn't exist\n if (!fs.existsSync(targetDir)) {\n fs.mkdirSync(targetDir, { recursive: true });\n }\n\n // Ensure prefix directory has a package.json (required for npm link)\n const prefixPackageJson = path.join(prefix, 'package.json');\n if (!fs.existsSync(prefixPackageJson)) {\n fs.mkdirSync(prefix, { recursive: true });\n fs.writeFileSync(prefixPackageJson, JSON.stringify({ \n name: 'habits-nodes', \n version: '1.0.0', \n private: true\n }, null, 2));\n }\n\n // Use npm link to link the globally linked package\n const linkCommand = `npm link ${packageName}`;\n console.log(`Executing link command: ${linkCommand}`);\n \n const { stdout, stderr } = await execAsync(linkCommand, {\n cwd: prefix,\n timeout: 60000 // 1 minute timeout\n });\n\n if (stderr && !stderr.includes('npm warn') && !stderr.includes('added')) {\n console.warn(`Link warnings: ${stderr}`);\n }\n\n // Verify the link was created\n if (!fs.existsSync(modulePath)) {\n throw new Error(`Package ${packageName} was not linked correctly at ${modulePath}`);\n }\n\n // Fix package.json if main entry points to .ts but .js exists\n await fixPackageJsonMainEntry(modulePath);\n\n // Link peer dependencies based on framework\n if (moduleDefinition.framework === 'activepieces') {\n await ensureActivepiecesDepsLinked(modulePath, name);\n } else if (moduleDefinition.framework === 'bits') {\n await ensureBitsDepsLinked(modulePath, name);\n } else if (moduleDefinition.framework === 'n8n') {\n await ensureN8nDepsLinked(modulePath, name);\n }\n\n console.log(`\u2713 Successfully linked ${name} at ${modulePath}`);\n return modulePath;\n } catch (error: any) {\n throw new Error(`Failed to link ${name}: ${error.message}`);\n }\n}\n\nexport function getModulePath(moduleDefinition: ModuleDefinition): string {\n // Return the correct path based on source type\n const moduleName = getModuleName(moduleDefinition);\n \n // Get the target path (where modules are installed)\n const targetPath = getModuleFullPath(moduleDefinition.framework, moduleName);\n \n // For local or link source, if target doesn't exist, return the source path\n if ((moduleDefinition.source === 'local' || moduleDefinition.source === 'link') && !fs.existsSync(targetPath)) {\n const localPath = getLocalModulePath(moduleDefinition.framework, moduleName);\n if (localPath && fs.existsSync(localPath)) {\n return localPath;\n }\n }\n \n // Check if package.json exists at the target path\n // If not, this might be a content-addressable store structure where the actual package\n // is in a hidden directory like .piece-name-hash\n const packageJsonPath = path.join(targetPath, 'package.json');\n if (!fs.existsSync(packageJsonPath) && fs.existsSync(targetPath)) {\n const pnpmStorePath = findPnpmStorePath(targetPath, moduleName);\n if (pnpmStorePath) {\n return pnpmStorePath;\n }\n }\n \n return targetPath;\n}\n\n/**\n * Find the actual module path in a content-addressable store.\n * Some package managers create hidden directories like `.piece-name-hash` that contain the actual package.\n * \n * @param expectedPath - The expected module path (e.g., /tmp/habits-nodes/node_modules/@activepieces/piece-openai)\n * @param moduleName - The module name (e.g., @activepieces/piece-openai)\n * @returns The actual path with package.json, or null if not found\n */\nfunction findPnpmStorePath(expectedPath: string, moduleName: string): string | null {\n const parentDir = path.dirname(expectedPath);\n \n if (!fs.existsSync(parentDir)) {\n return null;\n }\n \n // Extract the base package name without scope\n // e.g., \"@activepieces/piece-openai\" -> \"piece-openai\"\n const baseName = moduleName.includes('/') ? moduleName.split('/').pop()! : moduleName;\n \n try {\n const entries = fs.readdirSync(parentDir, { withFileTypes: true });\n \n // Look for hidden directories that start with the package name\n // Some package managers create directories like \".piece-openai-kB47Gs6C\"\n for (const entry of entries) {\n if (entry.isDirectory() && entry.name.startsWith(`.${baseName}`)) {\n const candidatePath = path.join(parentDir, entry.name);\n const candidatePackageJson = path.join(candidatePath, 'package.json');\n \n if (fs.existsSync(candidatePackageJson)) {\n console.log(`\uD83D\uDCE6 Found store path for ${moduleName}: ${candidatePath}`);\n return candidatePath;\n }\n }\n }\n } catch (error) {\n // Ignore errors reading directory\n }\n \n return null;\n}\n\nexport function getModuleMainFile(\n moduleDefinition: ModuleDefinition\n): string | null {\n const modulePath = getModulePath(moduleDefinition);\n\n // First, try to read the main entry from package.json\n const packageJsonPath = path.join(modulePath, 'package.json');\n if (fs.existsSync(packageJsonPath)) {\n try {\n const packageJson = JSON.parse(fs.readFileSync(packageJsonPath, 'utf-8'));\n \n // Try \"main\" field first, then \"module\", then \"exports\"\n let mainEntry = packageJson.main || packageJson.module;\n \n // Handle exports field (common in modern packages)\n if (!mainEntry && packageJson.exports) {\n if (typeof packageJson.exports === 'string') {\n mainEntry = packageJson.exports;\n } else if (packageJson.exports['.']) {\n const dotExport = packageJson.exports['.'];\n if (typeof dotExport === 'string') {\n mainEntry = dotExport;\n } else if (dotExport.require) {\n mainEntry = dotExport.require;\n } else if (dotExport.import) {\n mainEntry = dotExport.import;\n } else if (dotExport.default) {\n mainEntry = dotExport.default;\n }\n }\n }\n \n if (mainEntry) {\n // Remove leading ./ if present\n mainEntry = mainEntry.replace(/^\\.\\//, '');\n let mainPath = path.join(modulePath, mainEntry);\n \n // If main entry is a .ts file but .js exists, use .js instead\n // (handles packages with incorrect main entry pointing to TypeScript)\n if (mainEntry.endsWith('.ts') && !fs.existsSync(mainPath)) {\n const jsPath = mainPath.replace(/\\.ts$/, '.js');\n if (fs.existsSync(jsPath)) {\n console.log(`\u26A0\uFE0F Package.json main points to .ts but .js exists, using .js: ${jsPath}`);\n mainPath = jsPath;\n }\n }\n \n if (fs.existsSync(mainPath)) {\n console.log(`\u2713 Found main file from package.json for module: ${moduleDefinition.repository} at path: ${mainPath}`);\n return mainPath;\n }\n }\n } catch (error) {\n console.warn(`\u26A0\uFE0F Failed to parse package.json for ${moduleDefinition.repository}`);\n }\n }\n\n // Fallback: Try common patterns (including TypeScript sources for ts-node/tsx execution)\n const commonPaths = [\n 'dist/index.js',\n 'dist/main.js',\n 'dist/nodes',\n 'build/index.js',\n 'lib/index.js',\n 'out/index.js',\n // That's where activepieces modules are usually stored\n 'src/index.js',\n 'index.js',\n 'main.js',\n ];\n\n for (const commonPath of commonPaths) {\n const fullPath = path.join(modulePath, commonPath);\n if (fs.existsSync(fullPath)) {\n console.log(`\u2713 Detected main file for module: ${moduleDefinition.repository} at path: ${fullPath}`);\n return fullPath;\n }\n }\n console.log(`\u26A0\uFE0F Could not determine main file for module: ${moduleDefinition.repository} at path: ${modulePath}`);\n return null;\n}\n", "import * as fs from '@ha-bits/bindings/fs';\nimport * as path from '@ha-bits/bindings/path';\nimport { ensureModuleReady, getModuleMainFile, getModulePath } from './moduleCloner';\nimport { npmInstall, getLocalModulePath } from './utils';\nimport { LoggerFactory } from '@ha-bits/core';\n\nconst logger = LoggerFactory.getRoot();\n\ninterface ModuleDefinition {\n framework: string;\n source: 'github' | 'npm' | 'local' | 'link';\n repository: string; // GitHub URL for 'github' source, package name for 'npm'/'link' source, module name for 'local' source\n}\n\ninterface ModulesConfig {\n modules: ModuleDefinition[];\n}\n\n/**\n * Infers the module name from the repository URL or npm package name.\n * For GitHub: extracts the last part of the URL (e.g., https://github.com/user/repo.git -> repo)\n * For npm: uses the whole package name as the ID/Name\n */\nexport function getModuleName(moduleDefinition: ModuleDefinition): string {\n if (moduleDefinition.source === 'github') {\n // Extract repository name from GitHub URL\n // Handle formats like:\n // - https://github.com/user/repo.git\n // - https://github.com/user/repo\n // - git@github.com:user/repo.git\n const url = moduleDefinition.repository;\n \n // Remove .git suffix if present\n let repoName = url.replace(/\\.git$/, '');\n \n // Extract the last part after the last slash\n const parts = repoName.split('/');\n repoName = parts[parts.length - 1];\n \n return repoName;\n } else if (moduleDefinition.source === 'npm' || moduleDefinition.source === 'link') {\n // For npm and link, use the whole package name as the ID/Name\n return moduleDefinition.repository;\n } else if (moduleDefinition.source === 'local') {\n // For local, use the module name as-is\n return moduleDefinition.repository;\n } else {\n throw new Error(`Unknown source type: ${moduleDefinition.source}`);\n }\n}\n\nconst MODULES_CONFIG_PATH = path.join(process.cwd(), 'modules.json');\n\n/**\n * Modules operation mode:\n * - 'restricted': Only allows using modules already defined in modules.json\n * - 'open': Allows adding any module and appends it to modules.json if it doesn't exist\n */\nexport type ModulesMode = 'restricted' | 'open';\n\n/**\n * Get the current modules mode from environment variable.\n * Default is 'restricted' for security.\n * Set HABITS_MODULES_MODE=open to allow adding new modules.\n */\nexport function getModulesMode(): ModulesMode {\n const mode = process.env.HABITS_MODULES_MODE?.toLowerCase();\n if (mode === 'open') {\n return 'open';\n }\n return 'restricted';\n}\n\n/**\n * Check if a module exists in modules.json\n */\nexport function moduleExists(moduleDefinition: ModuleDefinition): boolean {\n const config = loadModulesConfig();\n const moduleName = getModuleName(moduleDefinition);\n \n return config.modules.some(\n m => m.framework === moduleDefinition.framework && getModuleName(m) === moduleName\n );\n}\n\n/**\n * Get a module from modules.json by framework and name\n */\nexport function getModuleFromConfig(framework: string, moduleName: string): ModuleDefinition | undefined {\n const config = loadModulesConfig();\n return config.modules.find(\n m => m.framework === framework && getModuleName(m) === moduleName\n );\n}\n\nexport function loadModulesConfig(): ModulesConfig {\n try {\n const configData = fs.readFileSync(MODULES_CONFIG_PATH, 'utf-8');\n return JSON.parse(configData);\n } catch (error: any) {\n throw new Error(`Failed to load modules.json: ${error.message}`);\n }\n}\n\nexport function saveModulesConfig(config: ModulesConfig): void {\n try {\n const configData = JSON.stringify(config, null, 2);\n fs.writeFileSync(MODULES_CONFIG_PATH, configData, 'utf-8');\n } catch (error: any) {\n throw new Error(`Failed to save modules.json: ${error.message}`);\n }\n}\n\nexport interface AddModuleOptions {\n /** Override the mode check - allows forcing addition even in restricted mode */\n force?: boolean;\n /** Skip saving to modules.json (useful for temporary modules) */\n skipSave?: boolean;\n}\n\n/**\n * Add a module to modules.json.\n * \n * Behavior depends on the modules mode (HABITS_MODULES_MODE env var):\n * - 'restricted' (default): Will throw an error. Modules must be pre-defined in modules.json.\n * - 'open': Will add the module to modules.json if it doesn't exist.\n * \n * @param moduleDefinition - The module definition to add\n * @param options - Optional settings for the add operation\n * @throws Error if in restricted mode and force is not set\n * @throws Error if module already exists\n */\nexport function addModule(moduleDefinition: ModuleDefinition, options: AddModuleOptions = {}): void {\n const mode = getModulesMode();\n const moduleName = getModuleName(moduleDefinition);\n \n // Check mode restrictions\n if (mode === 'restricted' && !options.force) {\n throw new Error(\n `Cannot add module '${moduleName}' in restricted mode. ` +\n `Either add it manually to modules.json or set HABITS_MODULES_MODE=open`\n );\n }\n \n const config = loadModulesConfig();\n \n // Check if module already exists (by repository to prevent duplicates)\n const existingModule = config.modules.find(\n m => m.repository === moduleDefinition.repository\n );\n \n if (existingModule) {\n logger.log(`\u23ED\uFE0F Module '${moduleName}' already exists in modules.json, skipping`);\n return;\n }\n \n // Validate source type\n if (!['github', 'npm', 'local'].includes(moduleDefinition.source)) {\n throw new Error(`Invalid source type: ${moduleDefinition.source}. Must be 'github', 'npm', or 'local'`);\n }\n \n if (!options.skipSave) {\n config.modules.push(moduleDefinition);\n saveModulesConfig(config);\n logger.log(`\u2705 Module '${moduleName}' added to modules.json`);\n }\n}\n\n/**\n * Ensure a module is available for use.\n * In restricted mode: module must already exist in modules.json\n * In open mode: adds the module to modules.json if it doesn't exist\n * \n * @param moduleDefinition - The module definition to ensure\n * @returns The module definition (either existing or newly added)\n */\nexport function ensureModuleInConfig(moduleDefinition: ModuleDefinition): ModuleDefinition {\n const mode = getModulesMode();\n const moduleName = getModuleName(moduleDefinition);\n \n // Check if module exists\n const existingModule = getModuleFromConfig(moduleDefinition.framework, moduleName);\n \n if (existingModule) {\n return existingModule;\n }\n \n // Module doesn't exist\n if (mode === 'restricted') {\n throw new Error(\n `Module '${moduleName}' not found in modules.json. ` +\n `In restricted mode, only pre-defined modules can be used. ` +\n `Add it to modules.json or set HABITS_MODULES_MODE=open`\n );\n }\n \n // Open mode: add the module\n addModule(moduleDefinition);\n return moduleDefinition;\n}\n\nexport function getModuleByPath(modulePath: string): ModuleDefinition | undefined {\n const config = loadModulesConfig();\n const [framework, ...nameParts] = modulePath.split('/');\n const name = nameParts.join('/');\n\n return config.modules.find(\n (m) => m.framework === framework && getModuleName(m) === name\n );\n}\n\nexport function isModuleCloned(moduleDefinition: ModuleDefinition): boolean {\n const modulePath = getModulePath(moduleDefinition);\n \n // Check if installed in target location\n if (fs.existsSync(modulePath)) {\n return true;\n }\n \n // For local or link source, also check if it exists at the source location\n if (moduleDefinition.source === 'local' || moduleDefinition.source === 'link') {\n const moduleName = getModuleName(moduleDefinition);\n const localPath = getLocalModulePath(moduleDefinition.framework, moduleName);\n if (localPath && fs.existsSync(localPath)) {\n return true;\n }\n }\n \n return false;\n}\n\nexport function isModuleBuilt(moduleDefinition: ModuleDefinition): boolean {\n // Determine which path to check\n let modulePath = getModulePath(moduleDefinition);\n \n // For local or link source, check source location if target doesn't exist\n if ((moduleDefinition.source === 'local' || moduleDefinition.source === 'link') && !fs.existsSync(modulePath)) {\n const moduleName = getModuleName(moduleDefinition);\n const localPath = getLocalModulePath(moduleDefinition.framework, moduleName);\n if (localPath) {\n modulePath = localPath;\n }\n }\n \n if (!fs.existsSync(modulePath)) {\n return false;\n }\n\n // Check for common build outputs\n const commonBuildDirs = ['dist', 'build', 'lib', 'out'];\n const commonMainFiles = [\n 'dist/index.js',\n 'dist/main.js', \n 'dist/nodes',\n 'build/index.js',\n 'lib/index.js',\n 'out/index.js',\n 'src/index.js',\n ];\n\n // Check for build directories with content\n for (const buildDir of commonBuildDirs) {\n const buildDirPath = path.join(modulePath, buildDir);\n const exists = fs.existsSync(buildDirPath);\n if (exists) {\n try {\n const items = fs.readdirSync(buildDirPath);\n if (items.length > 0) {\n return true;\n }\n } catch (error) {\n continue;\n }\n }\n }\n\n // Check for main files\n for (const mainFile of commonMainFiles) {\n const mainFilePath = path.join(modulePath, mainFile);\n if (fs.existsSync(mainFilePath)) {\n return true;\n }\n }\n\n return false;\n}\n\nexport async function ensureModuleInstalled(\n moduleDefinition: ModuleDefinition\n): Promise<string> {\n const moduleName = getModuleName(moduleDefinition);\n console.log(`\\n\uD83D\uDD0D ensureModuleInstalled called:`);\n console.log(` Module name: ${moduleName}`);\n console.log(` Source: ${moduleDefinition.source}`);\n console.log(` Repository: ${moduleDefinition.repository}`);\n console.log(` Framework: ${moduleDefinition.framework}`);\n\n try {\n // Use the cloner to ensure module is ready\n const modulePath = await ensureModuleReady(moduleDefinition);\n console.log(`\u2713 Module ${moduleName} is ready at: ${modulePath}\\n`);\n return modulePath;\n } catch (error: any) {\n console.error(`\u2717 Failed to prepare module ${moduleName}: ${error.message}\\n`);\n throw error;\n }\n}\n\nexport async function installModule(packageName: string, version: string = 'latest'): Promise<void> {\n const packageSpec = version === 'latest' ? packageName : `${packageName}@${version}`;\n\n try {\n console.log(`Installing ${packageSpec} via npm...`);\n const { stdout, stderr } = await npmInstall(packageSpec, { saveOptional: true });\n\n if (stderr && !stderr.includes('npm warn')) {\n console.error(`Installation warnings: ${stderr}`);\n }\n\n console.log(`Successfully installed ${packageSpec}`);\n } catch (error: any) {\n throw new Error(`Failed to install ${packageSpec}: ${error.message}`);\n }\n}\n\nexport async function listAvailableModules(framework?: string): Promise<any[]> {\n const config = loadModulesConfig();\n let modules = config.modules;\n\n if (framework) {\n modules = modules.filter((m) => m.framework === framework);\n }\n\n return modules.map((m) => {\n const moduleName = getModuleName(m);\n return {\n framework: m.framework,\n name: moduleName,\n source: m.source,\n path: `${m.framework}/${moduleName}`,\n repository: m.repository,\n cloned: isModuleCloned(m),\n built: isModuleBuilt(m),\n installed: isModuleCloned(m) && isModuleBuilt(m),\n };\n });\n}\n", "/**\n * Execution Context Factory for n8n nodes\n * Creates the IExecuteFunctions context that n8n nodes expect\n */\n\nimport * as path from 'path';\nimport {\n INodeType,\n INodeExecutionData,\n IExecuteFunctions,\n IHttpRequestOptions,\n INode,\n IDataObject,\n ICredentialType,\n} from './types';\nimport { ModuleDefinition } from '../utils/moduleCloner';\nimport { httpRequest } from './httpRequest';\nimport { loadCredentialType, applyCredentialAuthentication, applyFallbackAuthentication } from './credentialLoader';\nimport { LoggerFactory } from '@ha-bits/core';\n\nconst logger = LoggerFactory.getRoot();\n\nexport interface N8nNodeExecutionOptions {\n inputData?: INodeExecutionData[];\n credentials?: Record<string, any>;\n}\n\n/**\n * Create a real execution context for n8n nodes\n * This provides all the methods that nodes expect to have access to\n */\nexport function createExecutionContext(\n node: INodeType,\n params: Record<string, any>,\n options?: N8nNodeExecutionOptions\n): IExecuteFunctions {\n const inputData: INodeExecutionData[] = options?.inputData || params.inputData || [{ json: params }];\n const credentials = options?.credentials || params.credentials || {};\n\n // Create the node configuration object\n const version = node.description?.version;\n const typeVersion = Array.isArray(version) ? version[0] : (version || 1);\n \n const nodeConfig: INode = {\n id: params.nodeId || 'node-1',\n name: node.description?.name || 'unknown',\n type: node.description?.name || 'unknown',\n typeVersion,\n position: [0, 0],\n parameters: params,\n credentials: {},\n };\n\n // Build the execution context with real implementations\n const context: IExecuteFunctions = {\n // Get input data from previous nodes\n getInputData: (inputIndex: number = 0): INodeExecutionData[] => {\n return inputData;\n },\n\n // Get node parameter value\n getNodeParameter: (\n parameterName: string,\n itemIndex: number = 0,\n fallbackValue?: any,\n options?: any\n ): any => {\n // Handle nested parameters like 'options.timeout'\n const parts = parameterName.split('.');\n let value: any = params;\n \n for (const part of parts) {\n if (value && typeof value === 'object' && part in value) {\n value = value[part];\n } else {\n value = undefined;\n break;\n }\n }\n\n if (value !== undefined) {\n return value;\n }\n\n if (fallbackValue !== undefined) {\n return fallbackValue;\n }\n\n // For some parameters, return sensible defaults\n const defaultValues: Record<string, any> = {\n 'options': {},\n 'authentication': 'none',\n 'sendHeaders': false,\n 'sendQuery': false,\n 'sendBody': false,\n 'specifyHeaders': 'keypair',\n 'specifyQuery': 'keypair',\n 'specifyBody': 'keypair',\n 'headerParameters': { parameters: [] },\n 'queryParameters': { parameters: [] },\n 'bodyParameters': { parameters: [] },\n };\n\n return defaultValues[parameterName] ?? null;\n },\n\n // Get the current node\n getNode: (): INode => nodeConfig,\n\n // Get workflow data\n getWorkflow: () => ({\n id: 'workflow-1',\n name: 'Habits Workflow',\n active: true,\n }),\n\n // Get execution mode\n getMode: () => 'manual' as any,\n\n // Get execution ID\n getExecutionId: () => `exec-${Date.now()}`,\n\n // Continue on fail check\n continueOnFail: () => false,\n\n // Get credentials\n getCredentials: async <T extends object = any>(type: string): Promise<T> => {\n const creds = credentials[type];\n if (!creds) {\n throw new Error(`No credentials found for type: ${type}`);\n }\n return creds as T;\n },\n\n // Helpers object with HTTP request and other utilities\n helpers: {\n // HTTP request function (real implementation)\n httpRequest: async (opts: IHttpRequestOptions): Promise<any> => {\n return await httpRequest(opts);\n },\n\n // HTTP request with authentication\n httpRequestWithAuthentication: async (\n credentialsType: string,\n requestOptions: IHttpRequestOptions,\n additionalCredentialOptions?: any\n ): Promise<any> => {\n // Get credentials\n const creds = credentials[credentialsType] || {};\n \n // Try to load credential type and apply authentication generically\n const credentialType = loadCredentialType(\n (params as any).__moduleDefinition,\n credentialsType\n );\n \n if (credentialType) {\n applyCredentialAuthentication(requestOptions, credentialType, creds);\n } else {\n // Fallback to common patterns\n applyFallbackAuthentication(\n requestOptions.headers as Record<string, string> || {},\n creds\n );\n }\n\n return await httpRequest(requestOptions);\n },\n\n // Convert JSON to array format\n returnJsonArray: (jsonData: any): INodeExecutionData[] => {\n const data = Array.isArray(jsonData) ? jsonData : [jsonData];\n return data.map(item => ({ json: item }));\n },\n\n // Copy input items\n copyInputItems: (items: INodeExecutionData[], properties: string[]): IDataObject[] => {\n return items.map(item => {\n const newItem: IDataObject = {};\n for (const property of properties) {\n if (item.json.hasOwnProperty(property)) {\n newItem[property] = item.json[property] as any;\n }\n }\n return newItem;\n });\n },\n\n // Normalize items\n normalizeItems: (items: INodeExecutionData[]): INodeExecutionData[] => {\n return items.map(item => ({\n json: item.json || {},\n binary: item.binary,\n pairedItem: item.pairedItem,\n }));\n },\n\n // Construct execution metadata\n constructExecutionMetaData: (\n items: INodeExecutionData[],\n options: { itemData: { item: number } }\n ): INodeExecutionData[] => {\n return items.map((item, index) => ({\n ...item,\n pairedItem: { item: options.itemData.item },\n }));\n },\n\n // Request function (legacy)\n request: async (uriOrObject: string | any, options?: any): Promise<any> => {\n let requestOpts: IHttpRequestOptions;\n \n if (typeof uriOrObject === 'string') {\n requestOpts = {\n url: uriOrObject,\n method: options?.method || 'GET',\n body: options?.body,\n qs: options?.qs,\n headers: options?.headers,\n };\n } else {\n requestOpts = {\n url: uriOrObject.uri || uriOrObject.url,\n method: uriOrObject.method || 'GET',\n body: uriOrObject.body,\n qs: uriOrObject.qs,\n headers: uriOrObject.headers,\n };\n }\n\n return await httpRequest(requestOpts);\n },\n\n // Request with authentication (legacy)\n requestWithAuthentication: async (\n credentialsType: string,\n requestOptions: any,\n additionalCredentialOptions?: any,\n itemIndex?: number\n ): Promise<any> => {\n const creds = credentials[credentialsType] || {};\n \n // Try to load credential type and apply authentication generically\n const credentialType = loadCredentialType(\n (params as any).__moduleDefinition,\n credentialsType\n );\n \n const httpOptions: IHttpRequestOptions = {\n url: requestOptions.uri || requestOptions.url,\n method: requestOptions.method || 'GET',\n body: requestOptions.body,\n qs: requestOptions.qs,\n headers: requestOptions.headers || {},\n };\n \n if (credentialType) {\n applyCredentialAuthentication(httpOptions, credentialType, creds);\n } else {\n applyFallbackAuthentication(\n httpOptions.headers as Record<string, string>,\n creds\n );\n }\n\n return await httpRequest(httpOptions);\n },\n\n // Binary data helpers (stub implementations)\n prepareBinaryData: async (binaryData: Buffer, filePath?: string, mimeType?: string) => {\n return {\n data: binaryData.toString('base64'),\n mimeType: mimeType || 'application/octet-stream',\n fileName: filePath ? path.basename(filePath) : 'file',\n };\n },\n\n assertBinaryData: (itemIndex: number, propertyName: string) => {\n const item = inputData[itemIndex];\n if (!item?.binary?.[propertyName]) {\n throw new Error(`No binary data found for property: ${propertyName}`);\n }\n return item.binary[propertyName];\n },\n\n getBinaryDataBuffer: async (itemIndex: number, propertyName: string): Promise<Buffer> => {\n const item = inputData[itemIndex];\n if (!item?.binary?.[propertyName]) {\n throw new Error(`No binary data found for property: ${propertyName}`);\n }\n return Buffer.from(item.binary[propertyName].data, 'base64');\n },\n\n // Convert binary data to string\n binaryToString: async (binaryData: Buffer, encoding: BufferEncoding = 'utf-8'): Promise<string> => {\n return binaryData.toString(encoding);\n },\n\n // Create deferred promise\n createDeferredPromise: <T>(): { promise: Promise<T>; resolve: (value: T) => void; reject: (error: Error) => void } => {\n let resolve!: (value: T) => void;\n let reject!: (error: Error) => void;\n const promise = new Promise<T>((res, rej) => {\n resolve = res;\n reject = rej;\n });\n return { promise, resolve, reject };\n },\n } as any,\n\n // Node helpers\n nodeHelpers: {\n copyBinaryFile: async (filePath: string, fileName: string, mimeType?: string) => {\n return {\n data: '',\n mimeType: mimeType || 'application/octet-stream',\n fileName,\n };\n },\n } as any,\n\n // Additional methods that nodes might use\n getWorkflowStaticData: (type: string) => ({}),\n getTimezone: () => 'UTC',\n getRestApiUrl: () => 'http://localhost:5678/api/v1',\n getInstanceBaseUrl: () => 'http://localhost:5678',\n getInstanceId: () => 'instance-1',\n\n // Logging\n logger: {\n info: (...args: any[]) => logger.log('[n8n]', ...args),\n warn: (...args: any[]) => logger.warn('[n8n]', ...args),\n error: (...args: any[]) => logger.error('[n8n]', ...args),\n debug: (...args: any[]) => logger.log('[n8n:debug]', ...args),\n } as any,\n\n // Send message to UI (no-op in headless execution)\n sendMessageToUI: (message: any) => {\n logger.log('[n8n:ui]', message);\n },\n\n // Put execution to wait (for wait nodes)\n putExecutionToWait: async (waitTill: Date) => {\n logger.log(`[n8n] Waiting until: ${waitTill.toISOString()}`);\n },\n\n // Send response (for webhook response nodes)\n sendResponse: (response: any) => {\n logger.log('[n8n] Sending response:', response);\n },\n\n // Prepare output data - transforms INodeExecutionData[] to INodeExecutionData[][]\n prepareOutputData: async (outputData: any[], outputIndex: number = 0): Promise<any[][]> => {\n // n8n expects output as array of arrays (one array per output)\n const returnData: any[][] = [];\n \n // Initialize arrays for all outputs up to outputIndex\n for (let i = 0; i <= outputIndex; i++) {\n returnData.push(i === outputIndex ? outputData : []);\n }\n \n return returnData;\n },\n } as IExecuteFunctions;\n\n return context;\n}\n", "/**\n * HTTP Request utilities for n8n node execution\n */\n\nimport axios, { AxiosRequestConfig, AxiosResponse } from 'axios';\nimport FormData from 'form-data';\nimport {\n IHttpRequestOptions,\n IN8nHttpFullResponse,\n IN8nHttpResponse,\n} from './types';\nimport { LoggerFactory } from '@ha-bits/core';\n\nconst logger = LoggerFactory.getRoot();\n\n/**\n * Convert n8n request options to axios config\n */\nexport function convertN8nRequestToAxios(requestOptions: IHttpRequestOptions): AxiosRequestConfig {\n const { headers, method, timeout, auth, url, body, qs } = requestOptions;\n\n const axiosConfig: AxiosRequestConfig = {\n headers: (headers as Record<string, string>) ?? {},\n method: method || 'GET',\n timeout: timeout || 300000,\n url,\n maxBodyLength: Infinity,\n maxContentLength: Infinity,\n };\n\n // Add query parameters\n if (qs) {\n axiosConfig.params = qs;\n }\n\n // Add authentication\n if (auth) {\n axiosConfig.auth = {\n username: auth.username || '',\n password: auth.password || '',\n };\n }\n\n // Add base URL\n if (requestOptions.baseURL) {\n axiosConfig.baseURL = requestOptions.baseURL;\n }\n\n // Handle redirect options\n if (requestOptions.disableFollowRedirect) {\n axiosConfig.maxRedirects = 0;\n }\n\n // Handle response encoding\n if (requestOptions.encoding) {\n axiosConfig.responseType = requestOptions.encoding as any;\n }\n\n // Handle SSL certificate validation\n if (requestOptions.skipSslCertificateValidation) {\n // Note: In a real implementation, we'd configure the https agent\n // For simplicity, we'll just note this option\n }\n\n // Handle body\n if (body) {\n if (body instanceof FormData) {\n axiosConfig.data = body;\n axiosConfig.headers = {\n ...axiosConfig.headers,\n ...body.getHeaders(),\n };\n } else if (body instanceof URLSearchParams) {\n axiosConfig.headers = {\n ...axiosConfig.headers,\n 'Content-Type': 'application/x-www-form-urlencoded',\n };\n axiosConfig.data = body;\n } else if (typeof body === 'object' && Object.keys(body).length > 0) {\n axiosConfig.data = body;\n } else if (typeof body === 'string') {\n axiosConfig.data = body;\n }\n }\n\n // Add JSON accept header if requested\n if (requestOptions.json) {\n axiosConfig.headers = {\n ...axiosConfig.headers,\n Accept: 'application/json',\n };\n }\n\n // Add User-Agent header\n if (!axiosConfig.headers?.['User-Agent']) {\n axiosConfig.headers = {\n ...axiosConfig.headers,\n 'User-Agent': 'n8n-habits-executor',\n };\n }\n\n // Handle ignoreHttpStatusErrors\n if (requestOptions.ignoreHttpStatusErrors) {\n axiosConfig.validateStatus = () => true;\n }\n\n return axiosConfig;\n}\n\n/**\n * Execute HTTP request (real implementation)\n */\nexport async function httpRequest(\n requestOptions: IHttpRequestOptions\n): Promise<IN8nHttpFullResponse | IN8nHttpResponse> {\n // Remove empty body for GET/HEAD/OPTIONS\n const noBodyMethods = ['GET', 'HEAD', 'OPTIONS'];\n const method = (requestOptions.method || 'GET').toUpperCase();\n if (noBodyMethods.includes(method) && requestOptions.body && Object.keys(requestOptions.body).length === 0) {\n delete requestOptions.body;\n }\n\n const axiosConfig = convertN8nRequestToAxios(requestOptions);\n \n // Remove body for GET requests\n if (axiosConfig.data === undefined || (axiosConfig.method?.toUpperCase() === 'GET')) {\n delete axiosConfig.data;\n }\n\n logger.log(`\uD83C\uDF10 Making HTTP request: ${axiosConfig.method} ${axiosConfig.url}`);\n \n try {\n const response: AxiosResponse = await axios(axiosConfig);\n\n if (requestOptions.returnFullResponse) {\n return {\n body: response.data,\n headers: response.headers as Record<string, string>,\n statusCode: response.status,\n statusMessage: response.statusText,\n };\n }\n\n return response.data;\n } catch (error: any) {\n if (error.response) {\n logger.error(`HTTP Error (${error.response.status}): ${JSON.stringify(error.response.data)}`);\n throw new Error(`HTTP Error (${error.response.status}): ${JSON.stringify(error.response.data)}`);\n }\n throw error;\n }\n}\n", "/**\n * Credential Type Loading and Authentication\n * Handles loading credential type definitions and applying authentication\n */\n\nimport * as path from '@ha-bits/bindings/path';\nimport * as fs from '@ha-bits/bindings/fs';\nimport { customRequire } from '../utils/customRequire';\nimport { getModulePath, ModuleDefinition } from '../utils/moduleCloner';\nimport {\n IHttpRequestOptions,\n ICredentialType,\n IAuthenticateGeneric,\n ICredentialDataDecryptedObject,\n} from './types';\nimport { LoggerFactory } from '@ha-bits/core';\n\nconst logger = LoggerFactory.getRoot();\n\n// Cache for loaded credential types\nconst credentialTypeCache: Map<string, ICredentialType> = new Map();\n\n/**\n * Load credential type definition from a module\n * This looks for .credentials.ts files and loads the credential class\n */\nexport function loadCredentialType(\n moduleDefinition: ModuleDefinition,\n credentialTypeName: string\n): ICredentialType | null {\n // Check cache first\n if (credentialTypeCache.has(credentialTypeName)) {\n return credentialTypeCache.get(credentialTypeName)!;\n }\n\n if (!moduleDefinition) return null;\n\n try {\n const modulePath = getModulePath(moduleDefinition);\n if (!modulePath) return null;\n\n // Look for credentials directory\n const credentialsDir = path.join(modulePath, 'credentials');\n const distCredentialsDir = path.join(modulePath, 'dist', 'credentials');\n \n const dirsToCheck = [credentialsDir, distCredentialsDir];\n \n for (const dir of dirsToCheck) {\n if (!fs.existsSync(dir)) continue;\n \n const files = fs.readdirSync(dir);\n for (const file of files) {\n if (!file.endsWith('.js') && !file.endsWith('.ts')) continue;\n \n const filePath = path.join(dir, file);\n try {\n const module = customRequire(filePath, dir);\n \n for (const key of Object.keys(module)) {\n const exported = module[key];\n if (exported && typeof exported === 'function') {\n try {\n const instance = new exported();\n if (instance && instance.name === credentialTypeName) {\n credentialTypeCache.set(credentialTypeName, instance);\n logger.log(`\uD83D\uDCCB Loaded credential type: ${credentialTypeName}`);\n return instance;\n }\n } catch (e) {\n // Not a valid credential class, continue\n }\n }\n }\n } catch (e) {\n // Failed to load file, continue\n }\n }\n }\n } catch (error) {\n logger.warn(`Failed to load credential type ${credentialTypeName}: ${error}`);\n }\n \n return null;\n}\n\n/**\n * Resolve credential expression like ={{$credentials.xiApiKey}}\n */\nexport function resolveCredentialExpression(\n expression: string,\n credentials: ICredentialDataDecryptedObject\n): string {\n // Match patterns like ={{$credentials.propertyName}}\n const match = expression.match(/^=\\{\\{\\$credentials\\.([^}]+)\\}\\}$/);\n if (match) {\n const propName = match[1];\n const value = credentials[propName];\n return value !== undefined ? String(value) : '';\n }\n return expression;\n}\n\n/**\n * Apply authentication from credential type definition to request options\n * This reads the `authenticate` property from the credential type and applies it generically\n */\nexport function applyCredentialAuthentication(\n requestOptions: IHttpRequestOptions,\n credentialType: ICredentialType,\n credentials: ICredentialDataDecryptedObject\n): void {\n const auth = credentialType.authenticate;\n \n if (!auth) {\n logger.warn(`Credential type ${credentialType.name} has no authenticate property`);\n return;\n }\n\n // Handle IAuthenticateGeneric type\n if (typeof auth === 'object' && auth.type === 'generic') {\n const genericAuth = auth as IAuthenticateGeneric;\n const props = genericAuth.properties;\n \n // Apply headers\n if (props.headers) {\n const headers = requestOptions.headers as Record<string, string> || {};\n for (const [headerName, expression] of Object.entries(props.headers)) {\n const value = resolveCredentialExpression(String(expression), credentials);\n if (value) {\n headers[headerName] = value;\n }\n }\n requestOptions.headers = headers;\n }\n \n // Apply query parameters\n if (props.qs) {\n const qs = requestOptions.qs as Record<string, any> || {};\n for (const [paramName, expression] of Object.entries(props.qs)) {\n const value = resolveCredentialExpression(String(expression), credentials);\n if (value) {\n qs[paramName] = value;\n }\n }\n requestOptions.qs = qs;\n }\n \n // Apply body parameters\n if (props.body) {\n const body = requestOptions.body as Record<string, any> || {};\n for (const [bodyParam, expression] of Object.entries(props.body)) {\n const value = resolveCredentialExpression(String(expression), credentials);\n if (value) {\n body[bodyParam] = value;\n }\n }\n requestOptions.body = body;\n }\n \n // Apply basic auth\n if (props.auth) {\n const username = resolveCredentialExpression(\n String(props.auth.username || ''),\n credentials\n );\n const password = resolveCredentialExpression(\n String(props.auth.password || ''),\n credentials\n );\n requestOptions.auth = { username, password };\n }\n \n logger.log(`\u2705 Applied generic authentication from credential type: ${credentialType.name}`);\n } else if (typeof auth === 'function') {\n // Handle function-based authentication (advanced case)\n logger.warn(`Function-based authentication not yet supported for ${credentialType.name}`);\n }\n}\n\n/**\n * Apply credentials to request headers using credential type definitions\n * Falls back to common patterns if credential type is not found\n */\nexport function applyCredentialsToHeaders(\n headers: Record<string, string>,\n credentialTypeName: string,\n credentials: ICredentialDataDecryptedObject,\n moduleDefinition?: ModuleDefinition\n): void {\n // Try to load credential type definition\n let credentialType: ICredentialType | null = null;\n if (moduleDefinition) {\n credentialType = loadCredentialType(moduleDefinition, credentialTypeName);\n }\n \n if (credentialType) {\n // Use the authenticate property from the credential type\n const tempOptions: IHttpRequestOptions = { url: '', headers };\n applyCredentialAuthentication(tempOptions, credentialType, credentials);\n Object.assign(headers, tempOptions.headers);\n } else {\n // Fallback: Apply common authentication patterns\n logger.warn(`Credential type ${credentialTypeName} not found, using fallback patterns`);\n applyFallbackAuthentication(headers, credentials);\n }\n}\n\n/**\n * Fallback authentication for when credential type definition is not available\n * Supports common patterns like apiKey, Authorization, etc.\n */\nexport function applyFallbackAuthentication(\n headers: Record<string, string>,\n credentials: ICredentialDataDecryptedObject\n): void {\n // Check for common API key patterns\n if (credentials.apiKey) {\n headers['Authorization'] = `Bearer ${credentials.apiKey}`;\n }\n \n // Check for all credential properties that look like headers\n for (const [key, value] of Object.entries(credentials)) {\n if (typeof value !== 'string') continue;\n \n // Common header-like credential properties\n const headerMappings: Record<string, string> = {\n 'xiApiKey': 'xi-api-key',\n 'xApiKey': 'x-api-key',\n 'authToken': 'Authorization',\n 'bearerToken': 'Authorization',\n 'accessToken': 'Authorization',\n };\n \n if (headerMappings[key]) {\n const headerName = headerMappings[key];\n if (headerName === 'Authorization' && !value.startsWith('Bearer ')) {\n headers[headerName] = `Bearer ${value}`;\n } else {\n headers[headerName] = value;\n }\n }\n }\n}\n", "/**\n * Node Execution Functions\n * Contains executeGenericN8nNode and executeRoutingBasedNode\n */\n\nimport * as path from 'path';\nimport axios, { AxiosRequestConfig, AxiosResponse } from 'axios';\nimport { customRequire } from '../utils/customRequire';\nimport { getModuleName } from '../utils/moduleLoader';\nimport { ModuleDefinition } from '../utils/moduleCloner';\nimport {\n INodeType,\n INodeExecutionData,\n IExecuteFunctions,\n IHttpRequestOptions,\n INodeTypeDescription,\n} from './types';\nimport { createExecutionContext, N8nNodeExecutionOptions } from './executionContext';\nimport { loadCredentialType, applyCredentialAuthentication, applyFallbackAuthentication } from './credentialLoader';\nimport { LoggerFactory } from '@ha-bits/core';\n\nconst logger = LoggerFactory.getRoot();\n\n/**\n * Load a node from a module file\n */\nexport async function loadNodeFromModule(\n moduleDefinition: ModuleDefinition,\n mainFilePath: string\n): Promise<INodeType> {\n const moduleName = getModuleName(moduleDefinition);\n const originalCwd = process.cwd();\n const moduleDir = path.dirname(mainFilePath);\n\n try {\n process.chdir(moduleDir);\n // Use customRequire to bypass bundler's require and enable dynamic loading\n // n8n-workflow and n8n-core are resolved from the module's node_modules\n \n const module = customRequire(mainFilePath, moduleDir);\n\n // Find the node export - look for class that when instantiated has a description property\n let nodeInstance: INodeType | null = null;\n \n for (const key of Object.keys(module)) {\n const exported = module[key];\n if (exported && typeof exported === 'function') {\n try {\n // Try to instantiate and check for description property\n const instance = new exported();\n if (instance && typeof instance === 'object' && 'description' in instance) {\n nodeInstance = instance as INodeType;\n logger.debug(`Found n8n node class: ${key}`);\n break;\n }\n } catch (e) {\n // Not a valid node class, continue\n }\n }\n }\n\n if (!nodeInstance) {\n throw new Error(`No n8n node class found in module: ${moduleName}`);\n }\n \n process.chdir(originalCwd);\n return nodeInstance;\n } catch (error: any) {\n process.chdir(originalCwd);\n logger.error(error.stack);\n throw error;\n }\n}\n\n/**\n * Check if a node description has routing definitions\n */\nexport function hasRoutingInDescription(description: INodeTypeDescription): boolean {\n if (!description.properties) return false;\n \n for (const prop of description.properties) {\n if (prop.options) {\n for (const option of prop.options as any[]) {\n if (option.routing) {\n return true;\n }\n }\n }\n }\n return false;\n}\n\n/**\n * Execute a generic n8n node\n */\nexport async function executeGenericN8nNode(\n params: Record<string, any>,\n moduleDefinition: ModuleDefinition,\n mainFilePath: string\n): Promise<any> {\n try {\n const node = await loadNodeFromModule(moduleDefinition, mainFilePath);\n \n logger.log(`\uD83D\uDE80 Executing n8n node: ${node.description.displayName}`);\n \n const operation = params.operation;\n const resource = params.resource;\n \n logger.log(`Resource: ${resource || 'default'}, Operation: ${operation || 'default'}`);\n\n // Add moduleDefinition to params so it can be accessed in credential authentication\n const paramsWithModule = {\n ...params,\n __moduleDefinition: moduleDefinition,\n };\n\n // Create a real execution context for the node\n const context = createExecutionContext(node, paramsWithModule);\n\n // Execute the node\n let result: any = null;\n \n if (node.execute) {\n result = await node.execute.call(context);\n } else if (node.description.requestDefaults || hasRoutingInDescription(node.description)) {\n // Handle routing-based declarative nodes (like ElevenLabs)\n logger.log(`\uD83D\uDCE1 Using routing-based execution for declarative node`);\n result = await executeRoutingBasedNode(node, paramsWithModule, context);\n } else {\n throw new Error(`Node does not have an execute method and is not a routing-based node`);\n }\n\n logger.log(`\u2705 Successfully executed n8n node: ${node.description.displayName}`);\n\n // Extract the output from the result\n const output = result?.[0]?.map((item: any) => item.json) || result;\n\n return {\n success: true,\n module: moduleDefinition.repository,\n nodeLoaded: true,\n result: output,\n executedAt: new Date().toISOString(),\n data: {\n message: `Successfully executed n8n node: ${node.description.displayName}`,\n status: 'completed',\n output: result,\n rawOutput: output,\n },\n };\n } catch (error: any) {\n logger.error(`Failed to execute n8n node: ${error.message}`);\n logger.error(error.stack);\n throw error;\n }\n}\n\n/**\n * Execute a routing-based declarative n8n node\n * These nodes define HTTP routing in their operation descriptions instead of using execute()\n */\nexport async function executeRoutingBasedNode(\n node: INodeType,\n params: Record<string, any>,\n context: IExecuteFunctions\n): Promise<INodeExecutionData[][]> {\n const description = node.description;\n const resource = params.resource;\n const operation = params.operation;\n const credentials = params.credentials || {};\n \n // Find the operation definition with routing\n // n8n nodes can have routing at two levels:\n // 1. Property-level routing (on the 'operation' property itself) - contains request config\n // 2. Option-level routing (on individual operation options) - contains preSend/postReceive hooks\n let propertyRoutingConfig: any = null;\n let optionRoutingConfig: any = null;\n let operationDef: any = null;\n let operationProperty: any = null;\n \n for (const prop of description.properties || []) {\n if (prop.name === 'operation' && prop.options) {\n operationProperty = prop;\n // Check for property-level routing (has request.url template)\n if (prop.routing) {\n propertyRoutingConfig = prop.routing;\n }\n // Also check for option-level routing (has preSend hooks)\n for (const option of prop.options as any[]) {\n if (option.value === operation) {\n operationDef = option;\n if (option.routing) {\n optionRoutingConfig = option.routing;\n }\n break;\n }\n }\n }\n }\n \n // Merge routing configs: property-level provides request config, option-level provides hooks\n const routingConfig = {\n ...(propertyRoutingConfig || {}),\n ...(optionRoutingConfig || {}),\n request: {\n ...(propertyRoutingConfig?.request || {}),\n ...(optionRoutingConfig?.request || {}),\n },\n output: {\n ...(propertyRoutingConfig?.output || {}),\n ...(optionRoutingConfig?.output || {}),\n },\n send: {\n ...(propertyRoutingConfig?.send || {}),\n ...(optionRoutingConfig?.send || {}),\n },\n };\n \n if (!propertyRoutingConfig && !optionRoutingConfig) {\n throw new Error(`No routing configuration found for operation: ${operation}`);\n }\n \n logger.log(`\uD83D\uDCE1 Found routing config for operation: ${operation}`);\n \n // Build the request from routing config and requestDefaults\n const requestDefaults = description.requestDefaults || {};\n const requestConfig = routingConfig.request || {};\n \n // Resolve URL with parameter substitution\n let url = requestConfig.url || '';\n if (url.startsWith('=')) {\n // n8n expression format: ={{\"/text-to-speech/\"+$parameter[\"voice\"]}}\n url = resolveN8nExpression(url, params);\n }\n \n // Prepend baseURL if URL is relative\n const baseURL = requestDefaults.baseURL || '';\n if (url && !url.startsWith('http')) {\n url = baseURL + url;\n }\n \n // Build request body from field routing\n const body: Record<string, any> = {};\n const queryParams: Record<string, any> = {};\n \n for (const prop of description.properties || []) {\n // Skip meta fields\n if (['resource', 'operation', 'notice'].includes(prop.name)) {\n continue;\n }\n \n const paramValue = params[prop.name];\n \n // If property has explicit routing.send, use that\n if (prop.routing?.send) {\n const sendConfig = prop.routing.send;\n \n if (paramValue !== undefined && paramValue !== null && paramValue !== '') {\n if (sendConfig.type === 'body') {\n const propName = sendConfig.property || prop.name;\n body[propName] = resolveParamValue(paramValue);\n } else if (sendConfig.type === 'query') {\n const propName = sendConfig.property || prop.name;\n queryParams[propName] = resolveParamValue(paramValue);\n }\n }\n } else if ((prop as any).required && paramValue !== undefined && paramValue !== null && paramValue !== '') {\n // For required fields without explicit routing, add them to body by default\n // This handles cases where preSend hooks normally handle the parameter\n body[prop.name] = resolveParamValue(paramValue);\n } else if (paramValue !== undefined && paramValue !== null && paramValue !== '' && \n !prop.name.includes('_id') && prop.type === 'string') {\n // Also add string parameters that might be body content\n body[prop.name] = resolveParamValue(paramValue);\n }\n \n // Handle nested options (like additionalOptions)\n if (prop.type === 'collection' && prop.options && params[prop.name]) {\n const collectionValue = params[prop.name];\n for (const subProp of prop.options as any[]) {\n if (subProp.routing?.send && collectionValue[subProp.name] !== undefined) {\n const sendConfig = subProp.routing.send;\n const paramValue = collectionValue[subProp.name];\n \n if (paramValue !== undefined && paramValue !== null) {\n if (sendConfig.type === 'body') {\n const propName = sendConfig.property || subProp.name;\n body[propName] = resolveParamValue(paramValue);\n } else if (sendConfig.type === 'query') {\n const propName = sendConfig.property || subProp.name;\n queryParams[propName] = resolveParamValue(paramValue);\n }\n }\n }\n }\n }\n }\n \n // Determine HTTP method\n const method = (requestConfig.method || requestDefaults.method || 'POST').toUpperCase();\n \n // Build headers\n const headers: Record<string, string> = {\n ...(requestDefaults.headers || {}),\n ...(requestConfig.headers || {}),\n };\n \n // Apply credentials authentication using credential type definitions\n const credentialTypeName = description.credentials?.[0]?.name;\n if (credentialTypeName && credentials[credentialTypeName]) {\n const creds = credentials[credentialTypeName];\n const moduleDefinition = (params as any).__moduleDefinition;\n \n // Try to load credential type definition and apply authentication generically\n const credentialType = moduleDefinition \n ? loadCredentialType(moduleDefinition, credentialTypeName)\n : null;\n \n if (credentialType) {\n // Use the authenticate property from the credential type\n const tempOptions: IHttpRequestOptions = { url: '', headers };\n applyCredentialAuthentication(tempOptions, credentialType, creds);\n Object.assign(headers, tempOptions.headers);\n } else {\n // Fallback to common patterns\n applyFallbackAuthentication(headers, creds);\n }\n }\n \n logger.log(`\uD83C\uDF10 Making routing-based request: ${method} ${url}`);\n logger.log(`\uD83D\uDCE4 Request body:`, { body: body });\n \n // Make the HTTP request\n const axiosConfig: AxiosRequestConfig = {\n method: method as any,\n url,\n headers,\n params: Object.keys(queryParams).length > 0 ? queryParams : undefined,\n data: Object.keys(body).length > 0 ? body : undefined,\n };\n \n // Handle arraybuffer encoding for binary responses\n if (requestConfig.encoding === 'arraybuffer') {\n axiosConfig.responseType = 'arraybuffer';\n }\n \n try {\n const response: AxiosResponse = await axios(axiosConfig);\n \n logger.log(`\u2705 Routing-based request successful: ${response.status}`);\n \n // Handle binary response (audio data)\n if (requestConfig.encoding === 'arraybuffer' || response.headers['content-type']?.includes('audio')) {\n const binaryData = Buffer.from(response.data);\n const base64Data = binaryData.toString('base64');\n const mimeType = response.headers['content-type'] || 'audio/mpeg';\n \n return [[{\n json: {\n success: true,\n mimeType,\n dataSize: binaryData.length,\n base64: base64Data,\n },\n binary: {\n data: {\n data: base64Data,\n mimeType,\n fileName: `audio.${mimeType.split('/')[1] || 'mp3'}`,\n }\n }\n }]];\n }\n \n // Handle JSON response\n return [[{ json: response.data }]];\n \n } catch (error: any) {\n if (error.response) {\n const errorData = error.response.data;\n // If it's a buffer, try to convert to string\n const errorMessage = Buffer.isBuffer(errorData) \n ? errorData.toString('utf-8') \n : JSON.stringify(errorData);\n logger.error(`HTTP Error (${error.response.status}): ${errorMessage}`);\n throw new Error(`HTTP Error (${error.response.status}): ${errorMessage}`);\n }\n throw error;\n }\n}\n\n/**\n * Resolve n8n expression like ={{\"/text-to-speech/\"+$parameter[\"voice\"]}}\n */\nfunction resolveN8nExpression(expression: string, params: Record<string, any>): string {\n // Remove the leading = and {{ }} wrapper\n let expr = expression;\n if (expr.startsWith('=')) {\n expr = expr.substring(1);\n }\n if (expr.startsWith('{{') && expr.endsWith('}}')) {\n expr = expr.substring(2, expr.length - 2);\n }\n \n // Replace $parameter[\"paramName\"] with quoted placeholder values\n const paramValues: Record<string, string> = {};\n expr = expr.replace(/\\$parameter\\[\"([^\"]+)\"\\]/g, (match, paramName) => {\n const value = params[paramName];\n let resolved: string;\n if (typeof value === 'object' && value !== null) {\n // Handle resourceLocator type values\n resolved = value.value || value.id || JSON.stringify(value);\n } else {\n resolved = value !== undefined ? String(value) : '';\n }\n paramValues[paramName] = resolved;\n return `\"${resolved}\"`;\n });\n \n // Now evaluate the string concatenation expression\n // expr is now like: \"/text-to-speech/\"+\"21m00Tcm4TlvDq8ikWAM\"\n try {\n // Remove all quotes and plus signs to concatenate the parts\n // Match pattern: \"string1\"+\"string2\"+\"string3\" etc.\n const parts: string[] = [];\n const regex = /\"([^\"]*)\"/g;\n let match;\n while ((match = regex.exec(expr)) !== null) {\n parts.push(match[1]);\n }\n if (parts.length > 0) {\n return parts.join('');\n }\n // Fallback: just return the expression without quotes\n return expr.replace(/\"/g, '').replace(/\\+/g, '');\n } catch {\n return expr;\n }\n}\n\n/**\n * Resolve parameter value (handle resourceLocator and other complex types)\n */\nfunction resolveParamValue(value: any): any {\n if (typeof value === 'object' && value !== null) {\n // Handle resourceLocator type: { mode: 'list', value: 'actual_value' }\n if ('value' in value) {\n return value.value;\n }\n if ('id' in value) {\n return value.id;\n }\n }\n return value;\n}\n", "/**\n * n8n Module Executor\n * Main entry point for executing n8n nodes\n */\n\nimport { ensureModuleInstalled, getModuleName } from '../utils/moduleLoader';\nimport { getModuleMainFile, getModulePath, ModuleDefinition } from '../utils/moduleCloner';\nimport * as path from '@ha-bits/bindings/path';\nimport * as fs from '@ha-bits/bindings/fs';\n\n// Re-export types and functions from sub-modules\nexport { createExecutionContext, N8nNodeExecutionOptions } from './executionContext';\nexport { executeGenericN8nNode, executeRoutingBasedNode, loadNodeFromModule, hasRoutingInDescription } from './nodeExecution';\nexport { httpRequest, convertN8nRequestToAxios } from './httpRequest';\nexport { loadCredentialType, applyCredentialAuthentication, applyFallbackAuthentication, applyCredentialsToHeaders, resolveCredentialExpression } from './credentialLoader';\nimport { LoggerFactory } from '@ha-bits/core';\n\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport interface N8nExecutionParams {\n source: string;\n framework: string;\n moduleName: string;\n params: Record<string, any>;\n}\n\n// ============================================================================\n// N8n Module Path Resolution\n// ============================================================================\n\n/**\n * Find the main node file for an n8n module\n * N8n modules specify their nodes in package.json under \"n8n.nodes\"\n */\nfunction getN8nNodeFile(moduleDefinition: ModuleDefinition): string | null {\n const modulePath = getModulePath(moduleDefinition);\n logger.log(`\\n\uD83D\uDD0D getN8nNodeFile looking for module at: ${modulePath}`);\n logger.log(` Source: ${moduleDefinition.source}`);\n \n const packageJsonPath = path.join(modulePath, 'package.json');\n\n if (!fs.existsSync(packageJsonPath)) {\n logger.error(`package.json not found at: ${packageJsonPath}`);\n return null;\n }\n \n logger.log(` Found package.json at: ${packageJsonPath}`);\n\n try {\n const packageJson = JSON.parse(fs.readFileSync(packageJsonPath, 'utf-8'));\n \n // N8n modules specify nodes in the \"n8n\" section\n if (packageJson.n8n?.nodes && packageJson.n8n.nodes.length > 0) {\n // Get the first node file\n const nodeFile = packageJson.n8n.nodes[0];\n const fullPath = path.join(modulePath, nodeFile);\n \n if (fs.existsSync(fullPath)) {\n logger.log(`\uD83D\uDD0D Found n8n node at: ${fullPath}`);\n return fullPath;\n }\n }\n\n // Fallback: Try to find .node.js files in common locations\n const fallbackPaths = [\n 'dist/nodes',\n 'nodes',\n 'dist',\n ];\n\n for (const fallbackPath of fallbackPaths) {\n const dir = path.join(modulePath, fallbackPath);\n if (fs.existsSync(dir) && fs.statSync(dir).isDirectory()) {\n const nodeFile = findNodeFileInDirectory(dir);\n if (nodeFile) {\n logger.log(`\uD83D\uDD0D Found n8n node via search at: ${nodeFile}`);\n return nodeFile;\n }\n }\n }\n\n return null;\n } catch (error: any) {\n logger.error(`Error reading package.json: ${error.message}`);\n return null;\n }\n}\n\n/**\n * Recursively search for .node.js files in a directory\n */\nfunction findNodeFileInDirectory(dir: string): string | null {\n const entries = fs.readdirSync(dir, { withFileTypes: true });\n \n for (const entry of entries) {\n const fullPath = path.join(dir, entry.name);\n \n if (entry.isFile() && entry.name.endsWith('.node.js')) {\n return fullPath;\n }\n \n if (entry.isDirectory()) {\n const found = findNodeFileInDirectory(fullPath);\n if (found) {\n return found;\n }\n }\n }\n \n return null;\n}\n\n// ============================================================================\n// Main Execution Function\n// ============================================================================\n\n// Import executeGenericN8nNode here to avoid circular dependency\nimport { executeGenericN8nNode } from './nodeExecution';\n\n/**\n * Execute an n8n module with real HTTP calls and proper execution context\n */\nexport async function executeN8nModule(\n params: N8nExecutionParams\n): Promise<any>;\nexport async function executeN8nModule(\n moduleName: string,\n params: Record<string, any>\n): Promise<any>;\nexport async function executeN8nModule(\n paramsOrModuleName: N8nExecutionParams | string,\n maybeParams?: Record<string, any>\n): Promise<any> {\n // Handle both function signatures\n let moduleDefinition: ModuleDefinition;\n let executionParams: Record<string, any>;\n\n if (typeof paramsOrModuleName === 'string') {\n // Called as executeN8nModule(moduleName, params)\n logger.log(`\\n\uD83D\uDCCB executeN8nModule called with string: ${paramsOrModuleName}`);\n moduleDefinition = {\n framework: 'n8n',\n source: 'npm',\n repository: paramsOrModuleName,\n };\n executionParams = maybeParams || {};\n } else {\n // Called as executeN8nModule(params: N8nExecutionParams)\n logger.log(`\\n\uD83D\uDCCB executeN8nModule called with params object:`);\n logger.log(` Framework: ${paramsOrModuleName.framework}`);\n logger.log(` Source: ${paramsOrModuleName.source}`);\n logger.log(` ModuleName: ${paramsOrModuleName.moduleName}`);\n moduleDefinition = {\n framework: paramsOrModuleName.framework,\n source: paramsOrModuleName.source as 'github' | 'npm' | 'local',\n repository: paramsOrModuleName.moduleName,\n };\n executionParams = paramsOrModuleName.params;\n }\n\n // Ensure module is installed\n const inferredModuleName = getModuleName(moduleDefinition);\n logger.log(`\\n\uD83D\uDD0D Ensuring n8n module is ready: ${inferredModuleName}`);\n await ensureModuleInstalled(moduleDefinition);\n\n // Get the n8n node file path using n8n-specific resolution\n let mainFilePath = getN8nNodeFile(moduleDefinition);\n \n // Fallback to generic resolution if n8n-specific fails\n if (!mainFilePath) {\n mainFilePath = getModuleMainFile(moduleDefinition);\n }\n \n if (!mainFilePath) {\n throw new Error(`Could not locate node file for n8n module: ${inferredModuleName}`);\n }\n\n logger.log(`\uD83D\uDCE6 n8n node file at: ${mainFilePath}`);\n\n try {\n return await executeGenericN8nNode(executionParams, moduleDefinition, mainFilePath);\n } catch (error: any) {\n throw new Error(`Failed to execute n8n module '${moduleDefinition.repository}': ${error.message}`);\n }\n}\n", "import { ensureModuleInstalled, getModuleName } from '../utils/moduleLoader';\nimport { getModuleMainFile, ModuleDefinition, ensureActivepiecesReady } from '../utils/moduleCloner';\nimport * as path from '@ha-bits/bindings/path';\nimport { simpleRequire } from '../utils/customRequire';\n\n// Lazy-loaded activepieces modules - will be loaded after ensureActivepiecesReady() is called\nlet extractPieceFromModule: any;\nlet TriggerStrategy: any;\nlet trimVersionFromAlias: any;\n\n/**\n * Ensures activepieces dependencies are installed and loads the required modules.\n * Must be called before using any activepieces functionality.\n */\nasync function ensureActivepiecesModulesLoaded(): Promise<void> {\n if (extractPieceFromModule) return; // Already loaded\n \n // Ensure deps are installed first\n await ensureActivepiecesReady();\n \n // Now dynamically import the modules\n const shared = await import('@activepieces/shared');\n \n extractPieceFromModule = shared.extractPieceFromModule;\n TriggerStrategy = shared.TriggerStrategy;\n trimVersionFromAlias = shared.trimVersionFromAlias;\n}\n\nimport { LoggerFactory } from '@ha-bits/core';\nconst logger = LoggerFactory.getRoot();\n\n\n\nexport async function executeActivepiecesModule(\nparams: { source: string,\n framework: string,\n moduleName: string,\n params: Record<string, any>}\n): Promise<any> {\n // Ensure activepieces dependencies are installed and loaded\n await ensureActivepiecesModulesLoaded();\n\n // Get module definition from config\n const moduleDefinition: ModuleDefinition = {\n framework: params.framework,\n source: params.source as 'github' | 'npm',\n repository: params.moduleName,\n };\n \n\n\n\n \n if (!moduleDefinition) {\n throw new Error(`Activepieces module '${params.moduleName}' not found in modules.json`);\n }\n\n // Ensure module is cloned and built\n const inferredModuleName = getModuleName(moduleDefinition);\n console.log(`\\n\uD83D\uDD0D Ensuring module is ready: ${inferredModuleName}`);\n await ensureModuleInstalled(moduleDefinition);\n\n\n\n \n\n try {\n return await executeGenericActivepiecesPiece(params, moduleDefinition);\n\n } catch (error: any) {\n throw new Error(`Failed to load Activepieces module from '${moduleDefinition.repository}': ${error.message}`);\n }\n\n // Generic execution fallback\n}\nasync function pieceFromModule(\n moduleDefinition: ModuleDefinition\n): Promise<any> {\n const moduleName = getModuleName(moduleDefinition);\n\n\n // Get the main file path\n const mainFilePath = getModuleMainFile(moduleDefinition);\n if (!mainFilePath) {\n throw new Error(`Could not locate main file for module: ${moduleName}`);\n }\n\n console.log(`\uD83D\uDCE6 Module ready at: ${mainFilePath}`);\n\n // Import module using require for CommonJS compatibility \n // Save current working directory and change to module directory for proper resolution\n const originalCwd = process.cwd();\n const moduleDir = path.dirname(mainFilePath);\n \n // Find the node_modules directory containing the module\n // For /tmp/habits-nodes/node_modules/@activepieces/piece-openai/src/index.js\n // we want /tmp/habits-nodes/node_modules\n let nodeModulesDir = moduleDir;\n while (nodeModulesDir && !nodeModulesDir.endsWith('/node_modules') && nodeModulesDir !== path.dirname(nodeModulesDir)) {\n nodeModulesDir = path.dirname(nodeModulesDir);\n }\n \n try {\n process.chdir(moduleDir);\n // Use simpleRequire which creates require from the node_modules context\n // This avoids module resolution path manipulation that can cause circular dependency issues\n const loadedModule = simpleRequire(mainFilePath, nodeModulesDir);\n \n // Find the piece export in the module\n const pieceName = Object.keys(loadedModule).find(key => {\n const exported = loadedModule[key];\n return exported && typeof exported === 'object' && 'actions' in exported && 'triggers' in exported;\n });\n \n const piece = (extractPieceFromModule as any)({module: loadedModule, pieceName: pieceName!, pieceVersion: trimVersionFromAlias('2.0' )});\n process.chdir(originalCwd);\n return piece;\n } catch (error: any) {\n process.chdir(originalCwd);\n logger.error(error.stack);\n throw error;\n }\n\n\n}\nasync function hookTriggers(\n moduleDefinition: ModuleDefinition\n){\n // Ensure activepieces modules are loaded before using TriggerStrategy\n await ensureActivepiecesModulesLoaded();\n \n const piece = await pieceFromModule(moduleDefinition);\n\n const triggers = piece.triggers();\n for (const [triggerKey, trigger] of Object.entries(triggers)) {\n console.log(`\uD83D\uDD14 Hooking trigger: ${triggerKey}`);\n const triggerObj = trigger as any;\n\n // Check trigger type: polling, webhook, app-webhook\n if(triggerObj.type == TriggerStrategy.POLLING){\n // If Polling trigger, Check strategy either timebased or \n\n\n }\n\n if(triggerObj.type == TriggerStrategy.WEBHOOK){\n // If Webhook trigger\n // Here you would add logic to actually hook the trigger into your system\n // For example, setting up webhooks, polling mechanisms, etc.\n }\n if(triggerObj.type == TriggerStrategy.APP_WEBHOOK){\n // If App Webhook trigger\n // Here you would add logic to actually hook the trigger into your system\n // For example, setting up webhooks, polling mechanisms, etc.\n }\n}\n}\nasync function executeGenericActivepiecesPiece(\n params: Record<string, any>,\n moduleDefinition: ModuleDefinition\n): Promise<any> {\n\n try {\n\n \n const piece = await pieceFromModule(moduleDefinition);\n\n \n logger.log(`\uD83D\uDE80 Executing Activepieces piece: ${piece.displayName}`);\n const actionName = params.params.operation;\n const pieceActions = piece.actions();\n logger.log(`Available actions: ${Object.keys(pieceActions).join(', ')}`);\n logger.log(`Requested action: ${actionName}`);\n const action = piece.actions()[actionName] as any;\n \n // if action is not found, throw error with available actions\n if (!action) {\n throw new Error(`Action '${actionName}' not found in piece '${piece.displayName}'. Available actions: ${Object.keys(pieceActions).join(', ')}`);\n }\n // Extract auth from credentials if present\n // The piece expects auth to be passed separately from propsValue\n // Credentials are typically in params.params.credentials.<pieceName>\n let auth: any = undefined;\n const { credentials, ...actionProps } = params.params;\n if (credentials) {\n // Find the first credential object (e.g., credentials.intersect, credentials.openai, etc.)\n const credentialKeys = Object.keys(credentials);\n if (credentialKeys.length > 0) {\n // Pass auth data directly - pieces access auth properties directly (e.g., auth.host, auth.apiKey)\n // Some pieces may wrap in auth.props but most modern pieces access directly\n auth = credentials[credentialKeys[0]];\n logger.log(`\uD83D\uDD10 Using credentials for: ${credentialKeys[0]}`);\n }\n }\n \n const result = await action.run({\n auth,\n propsValue: {\n ...actionProps\n } as any\n } as any);\n logger.log(`\u2705 Successfully executed Activepieces piece action: ${actionName}`, result);\n \n \n return {\n success: true,\n module: moduleDefinition.repository,\n pieceLoaded: true,\n params,\n result,\n executedAt: new Date().toISOString(),\n data: {\n message: `Successfully executed Activepieces piece: ${piece.displayName}`,\n status: 'completed',\n pieceExports: Object.keys(module),\n },\n };\n \n } catch (error: any) {\n // Print stack\n logger.error(error.stack);\n throw error;\n }\n\n\n\n}\n", "import { inspect } from 'node:util';\nimport { getModuleName } from '../utils/moduleLoader';\nimport { getModuleMainFile, ModuleDefinition, ensureActivepiecesReady } from '../utils/moduleCloner';\nimport * as path from '@ha-bits/bindings/path';\n\n// Lazy-loaded activepieces modules - will be loaded after ensureActivepiecesReady() is called\nlet isNil: any;\nlet TriggerStrategy: any;\nlet extractPieceFromModule: any;\nlet trimVersionFromAlias: any;\n\n/**\n * Ensures activepieces dependencies are installed and loads the required modules.\n * Must be called before using any activepieces functionality.\n */\nasync function ensureActivepiecesModulesLoaded(): Promise<void> {\n if (extractPieceFromModule) return; // Already loaded\n \n // Ensure deps are installed first\n await ensureActivepiecesReady();\n \n // Now dynamically import the modules\n const shared = await import('@activepieces/shared');\n \n isNil = shared.isNil;\n TriggerStrategy = shared.TriggerStrategy;\n extractPieceFromModule = shared.extractPieceFromModule;\n trimVersionFromAlias = shared.trimVersionFromAlias;\n}\n\nimport { LoggerFactory } from '@ha-bits/core';\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport enum TriggerHookType {\n ON_ENABLE = 'ON_ENABLE',\n ON_DISABLE = 'ON_DISABLE',\n RUN = 'RUN',\n TEST = 'TEST',\n HANDSHAKE = 'HANDSHAKE',\n}\n\nexport interface Listener {\n events: string[];\n identifierValue: string;\n identifierKey: string;\n}\n\nexport interface ScheduleOptions {\n cronExpression: string;\n timezone?: string;\n}\n\nexport interface TriggerExecutionParams {\n moduleDefinition: ModuleDefinition;\n triggerName: string;\n input: Record<string, any>;\n hookType: TriggerHookType;\n trigger?: any; // Lazy-loaded Trigger type from @activepieces/pieces-framework\n payload?: unknown;\n webhookUrl?: string;\n isTest?: boolean;\n store?: SimpleStore;\n}\n\nexport interface TriggerExecutionResult {\n success: boolean;\n output?: unknown[];\n message?: string;\n listeners?: Listener[];\n scheduleOptions?: ScheduleOptions;\n response?: unknown;\n}\n\nexport interface SimpleTriggerContext {\n auth?: any;\n propsValue: Record<string, any>;\n payload: unknown;\n webhookUrl?: string;\n store: SimpleStore;\n app: {\n createListeners: (listener: Listener) => void;\n };\n setSchedule: (options: ScheduleOptions) => void;\n}\n\nexport interface SimpleStore {\n get: <T>(key: string) => Promise<T | null>;\n put: <T>(key: string, value: T) => Promise<void>;\n delete: (key: string) => Promise<void>;\n}\n\n// ============================================================================\n// Simple In-Memory Store (can be replaced with persistent storage)\n// ============================================================================\n\nfunction createSimpleStore(prefix: string = ''): SimpleStore {\n const storage = new Map<string, unknown>();\n \n return {\n async get<T>(key: string): Promise<T | null> {\n const fullKey = `${prefix}:${key}`;\n return (storage.get(fullKey) as T) ?? null;\n },\n async put<T>(key: string, value: T): Promise<void> {\n const fullKey = `${prefix}:${key}`;\n storage.set(fullKey, value);\n },\n async delete(key: string): Promise<void> {\n const fullKey = `${prefix}:${key}`;\n storage.delete(fullKey);\n },\n };\n}\n\n// ============================================================================\n// Trigger Helper\n// ============================================================================\n\nexport const triggerHelper = {\n /**\n * Load a piece from module definition\n */\n async loadPieceFromModule(moduleDefinition: ModuleDefinition): Promise<any> {\n // Ensure activepieces dependencies are installed and loaded\n await ensureActivepiecesModulesLoaded();\n \n const moduleName = getModuleName(moduleDefinition);\n const mainFilePath = getModuleMainFile(moduleDefinition);\n \n if (!mainFilePath) {\n throw new Error(`Could not locate main file for module: ${moduleName}`);\n }\n\n logger.log(`\uD83D\uDCE6 Loading piece from: ${mainFilePath}`);\n\n const originalCwd = process.cwd();\n const moduleDir = path.dirname(mainFilePath);\n\n try {\n process.chdir(moduleDir);\n // Use customRequire to bypass bundler's require and enable dynamic loading\n const module = require(mainFilePath);\n\n // Find the piece export\n const pieceName = Object.keys(module).find(key => {\n const exported = module[key];\n return exported && typeof exported === 'object' && 'actions' in exported && 'triggers' in exported;\n });\n\n if (!pieceName) {\n throw new Error(`No piece found in module: ${moduleName}`);\n }\n\n const piece = (extractPieceFromModule as any)({\n module,\n pieceName,\n pieceVersion: trimVersionFromAlias('2.0'),\n });\n\n process.chdir(originalCwd);\n return piece;\n } catch (error: any) {\n process.chdir(originalCwd);\n logger.error(error.stack);\n throw error;\n }\n },\n\n /**\n * Get a specific trigger from a piece\n */\n async getTrigger(\n moduleDefinition: ModuleDefinition,\n triggerName: string\n ): Promise<{ piece: any; trigger: any }> {\n const piece = await this.loadPieceFromModule(moduleDefinition);\n const triggers = piece.triggers();\n const trigger = triggers[triggerName];\n\n if (!trigger) {\n const availableTriggers = Object.keys(triggers).join(', ');\n throw new Error(\n `Trigger '${triggerName}' not found. Available triggers: ${availableTriggers}`\n );\n }\n\n return { piece, trigger };\n },\n\n /**\n * Execute a trigger based on hook type\n */\n async executeTrigger(params: TriggerExecutionParams): Promise<TriggerExecutionResult> {\n const { moduleDefinition, triggerName, input, hookType,trigger, payload, webhookUrl, isTest, store } = params;\n\n if (isNil(triggerName)) {\n throw new Error('Trigger name is not set');\n }\n let pieceTrigger: any;\n if(trigger){\n pieceTrigger=trigger;\n }else{\n const { piece,trigger } = await this.getTrigger(moduleDefinition, triggerName);\n pieceTrigger=trigger;\n }\n logger.log(`\uD83D\uDD14 Executing trigger: ${triggerName} (${hookType})`);\n\n const appListeners: Listener[] = [];\n let scheduleOptions: ScheduleOptions | undefined;\n const storePrefix = isTest ? 'test' : triggerName;\n\n // Use provided store or create a new one\n // This ensures state persists between onEnable and run calls\n const triggerStore = store || createSimpleStore(storePrefix);\n\n // Extract auth from credentials if present (similar to actions)\n // The auth object needs to have a `props` property for pieces that use CustomAuth\n let auth: any = undefined;\n const { credentials, ...triggerProps } = input;\n if (credentials) {\n // Find the first credential object (e.g., credentials.imapAuth, credentials.gmail, etc.)\n const credentialKeys = Object.keys(credentials);\n if (credentialKeys.length > 0) {\n const credentialData = credentials[credentialKeys[0]];\n // Wrap in props structure as expected by CustomAuth pieces\n auth = {\n props: credentialData,\n ...credentialData, // Also spread at top level for pieces that access directly\n };\n logger.log(`\uD83D\uDD10 Using credentials for trigger: ${credentialKeys[0]}`);\n logger.log(` Auth props: ${JSON.stringify(Object.keys(credentialData))}`);\n }\n }\n\n // Build context for trigger execution\n const context: SimpleTriggerContext = {\n auth,\n propsValue: triggerProps,\n payload: payload ?? {},\n webhookUrl,\n store: triggerStore,\n app: {\n createListeners(listener: Listener): void {\n appListeners.push(listener);\n },\n },\n setSchedule(options: ScheduleOptions): void {\n scheduleOptions = {\n cronExpression: options.cronExpression,\n timezone: options.timezone ?? 'UTC',\n };\n },\n };\n\n try {\n switch (hookType) {\n case TriggerHookType.ON_ENABLE: {\n if (pieceTrigger.onEnable) {\n await pieceTrigger.onEnable(context as any);\n }\n return {\n success: true,\n listeners: appListeners,\n scheduleOptions: pieceTrigger.type === TriggerStrategy.POLLING ? scheduleOptions : undefined,\n };\n }\n\n case TriggerHookType.ON_DISABLE: {\n if (pieceTrigger.onDisable) {\n await pieceTrigger.onDisable(context as any);\n }\n return { success: true };\n }\n\n case TriggerHookType.HANDSHAKE: {\n if (pieceTrigger.onHandshake) {\n const response = await pieceTrigger.onHandshake(context as any);\n return {\n success: true,\n response,\n };\n }\n return {\n success: false,\n message: 'Trigger does not support handshake',\n };\n }\n\n case TriggerHookType.TEST: {\n if (pieceTrigger.test) {\n const testResult = await pieceTrigger.test(context as any);\n return {\n success: true,\n output: Array.isArray(testResult) ? testResult : [testResult],\n };\n }\n return {\n success: false,\n message: 'Trigger does not support test mode',\n output: [],\n };\n }\n\n case TriggerHookType.RUN: {\n if (pieceTrigger.run) {\n const runResult = await pieceTrigger.run(context as any);\n return {\n success: true,\n output: Array.isArray(runResult) ? runResult : [runResult],\n };\n }\n return {\n success: false,\n message: 'Trigger does not have a run method',\n output: [],\n };\n }\n\n default:\n return {\n success: false,\n message: `Unknown hook type: ${hookType}`,\n };\n }\n } catch (error: any) {\n logger.error(`Error executing trigger ${triggerName}:`, error);\n return {\n success: false,\n message: `Error executing trigger: ${inspect(error)}`,\n output: [],\n };\n }\n },\n\n /**\n * List all triggers from a piece\n */\n async listTriggers(moduleDefinition: ModuleDefinition): Promise<{\n triggers: Array<{\n name: string;\n displayName: string;\n description: string;\n type: any; // TriggerStrategy - lazy-loaded from @activepieces/shared\n }>;\n }> {\n const piece = await this.loadPieceFromModule(moduleDefinition);\n const triggers = piece.triggers();\n\n return {\n triggers: Object.entries(triggers).map(([name, trigger]) => {\n const t = trigger as any;\n return {\n name,\n displayName: t.displayName,\n description: t.description,\n type: t.type,\n };\n }),\n };\n },\n\n /**\n * Execute trigger with proper flow based on trigger type\n * For polling: calls onEnable first, then run\n * For webhooks: calls run directly\n */\n async executeActivepiecesTrigger(params: {\n moduleDefinition: ModuleDefinition;\n triggerName: string;\n input: Record<string, any>;\n payload?: unknown;\n webhookUrl?: string;\n store?: SimpleStore;\n }): Promise<TriggerExecutionResult> {\n const { moduleDefinition, triggerName, input, payload, webhookUrl, store } = params;\n\n // Get the trigger to determine its type\n const { piece, trigger } = await this.getTrigger(moduleDefinition, triggerName);\n \n\n const triggerStore = store || createSimpleStore(`trigger:${triggerName}`);\n\n switch (trigger.type) {\n case TriggerStrategy.POLLING: {\n logger.log(`Polling trigger flow: onEnable \u2192 run`);\n \n const onEnableResult = await this.executeTrigger({\n moduleDefinition,\n triggerName,\n input,\n hookType: TriggerHookType.ON_ENABLE,\n trigger,\n payload,\n webhookUrl,\n isTest: false,\n store: triggerStore,\n });\n\n if (!onEnableResult.success) {\n return onEnableResult;\n }\n\n logger.log(` \u2705 onEnable completed`);\n if (onEnableResult.scheduleOptions) {\n logger.log(` \uD83D\uDCC5 Schedule: ${onEnableResult.scheduleOptions.cronExpression} (${onEnableResult.scheduleOptions.timezone})`);\n }\n if (onEnableResult.listeners && onEnableResult.listeners.length > 0) {\n logger.log(` \uD83D\uDC42 Listeners: ${onEnableResult.listeners.length}`);\n }\n\n logger.log(` \u2192 Calling run to fetch items...`);\n const runResult = await this.executeTrigger({\n moduleDefinition,\n triggerName,\n input,\n hookType: TriggerHookType.RUN,\n trigger,\n payload,\n webhookUrl,\n isTest: false,\n store: triggerStore, \n });\n\n if (!runResult.success) {\n logger.warn(` \u26A0\uFE0F Run failed: ${runResult.message}`);\n } else {\n logger.log(` \u2705 Run completed, items found: ${runResult.output?.length || 0}`);\n }\n\n return runResult;\n }\n\n case TriggerStrategy.WEBHOOK: {\n logger.log(`webhook trigger`);\n \n return await this.executeTrigger({\n moduleDefinition,\n triggerName,\n input,\n hookType: TriggerHookType.RUN,\n payload,\n webhookUrl,\n isTest: false,\n });\n }\n\n default: {\n return {\n success: false,\n message: `Unsupported trigger type: ${trigger.type}`,\n output: [],\n };\n }\n }\n },\n\n /**\n * Hook triggers for a piece - sets up polling/webhooks based on trigger type\n * For polling triggers, automatically runs after a delay (default 3 seconds)\n */\n async hookTriggers(\n moduleDefinition: ModuleDefinition,\n options?: {\n webhookBaseUrl?: string;\n onPollingTrigger?: (triggerName: string, trigger: any) => void;\n onWebhookTrigger?: (triggerName: string, trigger: any) => void;\n onAppWebhookTrigger?: (triggerName: string, trigger: any) => void;\n onTriggerResult?: (triggerName: string, result: TriggerExecutionResult) => void;\n input?: Record<string, any>; // Input params for the trigger\n }\n ): Promise<void> {\n const piece = await this.loadPieceFromModule(moduleDefinition);\n const triggers = piece.triggers();\n\n for (const [triggerName, trigger] of Object.entries(triggers)) {\n const t = trigger as any;\n logger.log(`\uD83D\uDD14 Hooking trigger: ${triggerName} (type: ${t.type})`);\n\n switch (t.type) {\n case TriggerStrategy.POLLING:\n logger.log(` \u2192 Setting up polling trigger`);\n if (options?.onPollingTrigger) {\n options.onPollingTrigger(triggerName, t);\n }\n \n // Auto-run polling trigger immediately\n logger.log(` \uD83D\uDE80 Running polling trigger immediately...`);\n try {\n const result = await this.executeActivepiecesTrigger({\n moduleDefinition,\n triggerName,\n input: options?.input || {},\n });\n \n if (result.success) {\n logger.log(` \u2705 Trigger ${triggerName} executed successfully`);\n logger.log(` \uD83D\uDCE6 Output items: ${result.output?.length || 0}`);\n } else {\n logger.warn(` \u26A0\uFE0F Trigger ${triggerName} failed: ${result.message}`);\n }\n \n // Notify callback if provided\n if (options?.onTriggerResult) {\n options.onTriggerResult(triggerName, result);\n }\n } catch (error: any) {\n logger.error(` \u274C Error running trigger ${triggerName}:`, error.message);\n }\n break;\n\n case TriggerStrategy.WEBHOOK:\n logger.log(` \u2192 Setting up webhook trigger`);\n if (options?.onWebhookTrigger) {\n options.onWebhookTrigger(triggerName, t);\n }\n break;\n\n case TriggerStrategy.APP_WEBHOOK:\n logger.log(` \u2192 Setting up app webhook trigger`);\n if (options?.onAppWebhookTrigger) {\n options.onAppWebhookTrigger(triggerName, t);\n }\n break;\n\n default:\n logger.warn(` \u26A0\uFE0F Unknown trigger type: ${t.type}`);\n }\n }\n },\n\n /**\n * Validate cron expression (simple validation)\n */\n isValidCron(expression: string): boolean {\n // Simple validation - checks for 5 or 6 space-separated parts\n const parts = expression.trim().split(/\\s+/);\n return parts.length >= 5 && parts.length <= 6;\n },\n\n /**\n * Check if a node is an Activepieces trigger (polling or webhook)\n */\n isActivepiecesTrigger(node: any): boolean {\n return (\n node.data?.framework === 'activepieces' &&\n (node.data?.triggerType === 'polling' || node.data?.triggerType === 'webhook')\n );\n },\n\n /**\n * Check if a node is a webhook trigger\n */\n isWebhookTrigger(node: any): boolean {\n return (\n node.type === 'trigger' &&\n node.data?.framework === 'activepieces' &&\n (node.data?.triggerType === 'webhook' || \n node.data?.module === '@activepieces/piece-webhook' ||\n node.data?.operation === 'catch_webhook')\n );\n },\n\n /**\n * Extract webhook trigger configuration from a node\n */\n getWebhookConfig(node: any): {\n nodeId: string;\n path: string;\n authType: 'none' | 'header' | 'query_param';\n authFields: Record<string, any>;\n } {\n return {\n nodeId: node.id,\n path: `/webhook/${node.id}`,\n authType: node.data?.triggerSettings?.authType || 'none',\n authFields: node.data?.triggerSettings?.authFields || {},\n };\n },\n\n /**\n * Execute a webhook trigger with received payload\n */\n async executeWebhookTrigger(\n nodeId: string,\n payload: any,\n headers?: Record<string, string>,\n query?: Record<string, string>\n ): Promise<TriggerExecutionResult> {\n logger.log(`\uD83D\uDD14 Executing webhook trigger for node: ${nodeId}`);\n \n // For webhook triggers, we just pass through the payload\n // The actual processing is done by the downstream nodes\n return {\n success: true,\n output: [{\n body: payload,\n headers: headers || {},\n query: query || {},\n method: 'POST',\n timestamp: new Date().toISOString(),\n }],\n message: 'Webhook received successfully',\n };\n },\n};\n\n// ============================================================================\n// Utility Functions\n// ============================================================================\n\n/**\n * Try-catch wrapper that returns a result object\n */\nexport async function tryCatch<T>(\n fn: () => Promise<T>\n): Promise<{ data: T | null; error: Error | null }> {\n try {\n const data = await fn();\n return { data, error: null };\n } catch (error: any) {\n return { data: null, error };\n }\n}\n\nexport default triggerHelper;\n", "/**\n * Declarative API Executor\n * \n * This module handles the execution of declarative bits that define API\n * integrations through a description object with routing configuration,\n * similar to n8n's declarative node pattern - but without any n8n dependencies.\n * \n * Example declarative bit:\n * ```typescript\n * export class FriendGrid implements INodeType {\n * description: INodeTypeDescription = {\n * displayName: 'FriendGrid',\n * name: 'friendGrid',\n * requestDefaults: {\n * baseURL: 'https://api.sendgrid.com/v3/marketing'\n * },\n * properties: [\n * {\n * displayName: 'Operation',\n * name: 'operation',\n * type: 'options',\n * options: [\n * {\n * name: 'Create',\n * value: 'create',\n * routing: {\n * request: {\n * method: 'POST',\n * url: '/contacts'\n * }\n * }\n * }\n * ]\n * }\n * ]\n * }\n * }\n * ```\n */\n\nimport axios, { AxiosRequestConfig, Method } from 'axios';\n\n// ============================================================================\n// Types for Declarative Node Definition\n// ============================================================================\n\n/**\n * HTTP methods supported in routing\n */\nexport type DeclarativeHttpMethod = 'GET' | 'POST' | 'PUT' | 'PATCH' | 'DELETE' | 'HEAD' | 'OPTIONS';\n\n/**\n * Expression resolver context - available variables in expressions\n */\nexport interface ExpressionContext {\n $parameter: Record<string, any>;\n $credentials: Record<string, any>;\n $response?: any;\n $input?: any;\n $json?: any;\n}\n\n/**\n * Send configuration for request body/query\n */\nexport interface RoutingSend {\n type: 'body' | 'query';\n property?: string;\n properties?: Record<string, any>;\n value?: any;\n preSend?: PreSendAction[];\n}\n\n/**\n * Pre-send action types\n */\nexport interface PreSendAction {\n type: 'setKeyValue' | 'json';\n properties?: Record<string, any>;\n}\n\n/**\n * Post-receive action types\n */\nexport interface PostReceiveAction {\n type: 'set' | 'setKeyValue' | 'filter' | 'rootProperty' | 'limit' | 'sort' | 'binaryData';\n properties?: {\n value?: string;\n key?: string;\n property?: string;\n enabled?: string | boolean;\n maxResults?: number;\n };\n}\n\n/**\n * Routing output configuration\n */\nexport interface RoutingOutput {\n postReceive?: PostReceiveAction[];\n}\n\n/**\n * Request routing configuration\n */\nexport interface RoutingRequest {\n method?: DeclarativeHttpMethod;\n url?: string;\n baseURL?: string;\n headers?: Record<string, string>;\n qs?: Record<string, any>;\n body?: Record<string, any> | any;\n send?: RoutingSend;\n ignoreHttpStatusErrors?: boolean;\n returnFullResponse?: boolean;\n skipOnEmpty?: string;\n}\n\n/**\n * Complete routing configuration for an operation\n */\nexport interface RoutingConfig {\n request?: RoutingRequest;\n send?: RoutingSend;\n output?: RoutingOutput;\n}\n\n/**\n * Option definition for dropdown/options type properties\n */\nexport interface PropertyOption {\n name: string;\n value: string | number | boolean;\n description?: string;\n action?: string;\n routing?: RoutingConfig;\n}\n\n/**\n * Display options for conditional visibility\n */\nexport interface DisplayOptions {\n show?: Record<string, any[]>;\n hide?: Record<string, any[]>;\n}\n\n/**\n * Property definition in declarative node\n */\nexport interface DeclarativeProperty {\n displayName: string;\n name: string;\n type: 'string' | 'number' | 'boolean' | 'options' | 'multiOptions' | 'collection' | 'fixedCollection' | 'json' | 'notice' | 'hidden';\n default?: any;\n required?: boolean;\n description?: string;\n placeholder?: string;\n noDataExpression?: boolean;\n displayOptions?: DisplayOptions;\n options?: PropertyOption[] | DeclarativeProperty[];\n typeOptions?: {\n multipleValues?: boolean;\n multipleValueButtonText?: string;\n minValue?: number;\n maxValue?: number;\n numberStepSize?: number;\n rows?: number;\n alwaysOpenEditWindow?: boolean;\n password?: boolean;\n loadOptionsMethod?: string;\n };\n routing?: RoutingConfig;\n}\n\n/**\n * Request defaults configuration\n */\nexport interface RequestDefaults {\n baseURL?: string;\n url?: string;\n headers?: Record<string, string>;\n method?: DeclarativeHttpMethod;\n qs?: Record<string, any>;\n body?: Record<string, any>;\n}\n\n/**\n * Credential definition for declarative nodes\n */\nexport interface CredentialDefinition {\n name: string;\n required?: boolean;\n displayOptions?: DisplayOptions;\n}\n\n/**\n * Complete declarative node type description\n */\nexport interface DeclarativeNodeDescription {\n displayName: string;\n name: string;\n icon?: string;\n group?: string[];\n version?: number | number[];\n subtitle?: string;\n description?: string;\n defaults?: {\n name?: string;\n color?: string;\n };\n inputs?: string[];\n outputs?: string[];\n credentials?: CredentialDefinition[];\n requestDefaults?: RequestDefaults;\n requestOperations?: {\n pagination?: any;\n };\n properties: DeclarativeProperty[];\n}\n\n/**\n * Declarative node type interface (the class structure)\n */\nexport interface IDeclarativeNodeType {\n description: DeclarativeNodeDescription;\n // Optional methods for advanced use cases\n methods?: {\n loadOptions?: Record<string, (this: any) => Promise<PropertyOption[]>>;\n credentialTest?: Record<string, (this: any, credentials: any) => Promise<{ status: string; message: string }>>;\n };\n}\n\n/**\n * Execution context for declarative nodes\n */\nexport interface DeclarativeExecutionContext {\n parameters: Record<string, any>;\n credentials?: Record<string, any>;\n input?: any;\n}\n\n/**\n * Execution result\n */\nexport interface DeclarativeExecutionResult {\n success: boolean;\n data: any;\n status?: number;\n headers?: Record<string, string>;\n}\n\n// ============================================================================\n// Expression Resolver\n// ============================================================================\n\n/**\n * Resolve expressions in strings like:\n * - \"={{$parameter['email']}}\"\n * - \"={{$parameter.email}}\" \n * - \"=/contacts/{{$parameter['id']}}\"\n * - Simple property reference without braces\n */\nexport function resolveExpression(expression: any, context: ExpressionContext): any {\n if (expression === null || expression === undefined) {\n return expression;\n }\n\n if (typeof expression !== 'string') {\n // If it's an object, recursively resolve\n if (typeof expression === 'object' && !Array.isArray(expression)) {\n const resolved: Record<string, any> = {};\n for (const [key, value] of Object.entries(expression)) {\n resolved[key] = resolveExpression(value, context);\n }\n return resolved;\n }\n if (Array.isArray(expression)) {\n return expression.map(item => resolveExpression(item, context));\n }\n return expression;\n }\n\n // Check if it's an expression (starts with = or contains {{ }})\n const trimmed = expression.trim();\n \n // Full expression: ={{...}}\n if (trimmed.startsWith('={{') && trimmed.endsWith('}}')) {\n const expr = trimmed.slice(3, -2);\n return evaluateExpression(expr, context);\n }\n\n // Path expression: =/path/{{...}}\n if (trimmed.startsWith('=') && trimmed.includes('{{')) {\n let result = trimmed.slice(1); // Remove leading =\n // Replace all {{...}} occurrences\n result = result.replace(/\\{\\{([^}]+)\\}\\}/g, (_, expr) => {\n const value = evaluateExpression(expr.trim(), context);\n return value !== undefined && value !== null ? String(value) : '';\n });\n return result;\n }\n\n // Simple expression: =$parameter.email\n if (trimmed.startsWith('=')) {\n const expr = trimmed.slice(1);\n return evaluateExpression(expr, context);\n }\n\n // Template literal style: ${...}\n if (trimmed.includes('${')) {\n let result = trimmed;\n result = result.replace(/\\$\\{([^}]+)\\}/g, (_, expr) => {\n const value = evaluateExpression(expr.trim(), context);\n return value !== undefined && value !== null ? String(value) : '';\n });\n return result;\n }\n\n // No expression, return as-is\n return expression;\n}\n\n/**\n * Evaluate an expression string against the context\n */\nfunction evaluateExpression(expr: string, context: ExpressionContext): any {\n try {\n // Handle $parameter['key'] or $parameter.key syntax\n if (expr.startsWith('$parameter')) {\n return resolvePropertyAccess(expr.slice(1), { parameter: context.$parameter });\n }\n \n // Handle $credentials['key'] or $credentials.key syntax\n if (expr.startsWith('$credentials')) {\n return resolvePropertyAccess(expr.slice(1), { credentials: context.$credentials });\n }\n \n // Handle $response\n if (expr.startsWith('$response')) {\n return resolvePropertyAccess(expr.slice(1), { response: context.$response });\n }\n\n // Handle $input or $json\n if (expr.startsWith('$input') || expr.startsWith('$json')) {\n const key = expr.startsWith('$input') ? 'input' : 'json';\n return resolvePropertyAccess(expr.slice(expr.indexOf('$') + key.length + 1), { [key]: context.$input || context.$json });\n }\n\n // Try to evaluate as a simple JS expression (for things like ternary, etc.)\n // Create a safe evaluation context\n const safeContext = {\n $parameter: context.$parameter || {},\n $credentials: context.$credentials || {},\n $response: context.$response,\n $input: context.$input,\n $json: context.$json,\n };\n\n // Use Function constructor for safe evaluation\n const fn = new Function(...Object.keys(safeContext), `return ${expr}`);\n return fn(...Object.values(safeContext));\n } catch (error) {\n console.warn(`Failed to evaluate expression: ${expr}`, error);\n return undefined;\n }\n}\n\n/**\n * Resolve property access like \"parameter['email']\" or \"parameter.email\"\n */\nfunction resolvePropertyAccess(path: string, obj: Record<string, any>): any {\n // Normalize different access patterns\n // parameter['key'] -> parameter.key\n // parameter[\"key\"] -> parameter.key\n const normalizedPath = path\n .replace(/\\[['\"]([^'\"]+)['\"]\\]/g, '.$1')\n .replace(/\\[(\\d+)\\]/g, '.$1')\n .replace(/^\\./, '');\n\n const parts = normalizedPath.split('.');\n let current: any = obj;\n\n for (const part of parts) {\n if (current === null || current === undefined) {\n return undefined;\n }\n current = current[part];\n }\n\n return current;\n}\n\n// ============================================================================\n// Request Builder\n// ============================================================================\n\n/**\n * Build the final request configuration by merging defaults, operation routing, and property routing\n */\nexport function buildRequest(\n description: DeclarativeNodeDescription,\n context: DeclarativeExecutionContext\n): AxiosRequestConfig {\n const expressionContext: ExpressionContext = {\n $parameter: context.parameters,\n $credentials: context.credentials || {},\n $input: context.input,\n };\n\n // Start with request defaults\n const defaults = description.requestDefaults || {};\n \n let config: AxiosRequestConfig = {\n baseURL: resolveExpression(defaults.baseURL, expressionContext),\n url: resolveExpression(defaults.url, expressionContext) || '',\n method: (defaults.method || 'GET') as Method,\n headers: { ...resolveExpression(defaults.headers, expressionContext) },\n params: { ...resolveExpression(defaults.qs, expressionContext) },\n data: defaults.body ? { ...resolveExpression(defaults.body, expressionContext) } : undefined,\n };\n\n // Find and apply routing from selected options\n const routingConfigs = collectRoutingConfigs(description.properties, context.parameters, expressionContext);\n\n // Merge all routing configs\n for (const routing of routingConfigs) {\n config = mergeRoutingIntoConfig(config, routing, expressionContext);\n }\n\n // Process all properties for their routing configurations\n for (const prop of description.properties) {\n if (shouldShowProperty(prop, context.parameters)) {\n const propRouting = getPropertyRouting(prop, context.parameters, expressionContext);\n if (propRouting) {\n config = mergeRoutingIntoConfig(config, propRouting, expressionContext);\n }\n }\n }\n\n // Clean up undefined values\n if (config.data && typeof config.data === 'object') {\n config.data = removeUndefinedValues(config.data);\n if (Object.keys(config.data).length === 0) {\n config.data = undefined;\n }\n }\n\n if (config.params && typeof config.params === 'object') {\n config.params = removeUndefinedValues(config.params);\n if (Object.keys(config.params).length === 0) {\n config.params = undefined;\n }\n }\n\n return config;\n}\n\n/**\n * Remove undefined values from an object\n */\nfunction removeUndefinedValues(obj: Record<string, any>): Record<string, any> {\n const result: Record<string, any> = {};\n for (const [key, value] of Object.entries(obj)) {\n if (value !== undefined) {\n result[key] = value;\n }\n }\n return result;\n}\n\n/**\n * Check if a property should be shown based on displayOptions\n */\nfunction shouldShowProperty(prop: DeclarativeProperty, parameters: Record<string, any>): boolean {\n if (!prop.displayOptions) {\n return true;\n }\n\n // Check show conditions\n if (prop.displayOptions.show) {\n for (const [key, values] of Object.entries(prop.displayOptions.show)) {\n const paramValue = parameters[key];\n if (!values.includes(paramValue)) {\n return false;\n }\n }\n }\n\n // Check hide conditions\n if (prop.displayOptions.hide) {\n for (const [key, values] of Object.entries(prop.displayOptions.hide)) {\n const paramValue = parameters[key];\n if (values.includes(paramValue)) {\n return false;\n }\n }\n }\n\n return true;\n}\n\n/**\n * Collect routing configurations from selected options in properties\n */\nfunction collectRoutingConfigs(\n properties: DeclarativeProperty[],\n parameters: Record<string, any>,\n expressionContext: ExpressionContext\n): RoutingConfig[] {\n const configs: RoutingConfig[] = [];\n\n for (const prop of properties) {\n if (!shouldShowProperty(prop, parameters)) {\n continue;\n }\n\n const paramValue = parameters[prop.name];\n\n // Handle options type - find selected option's routing\n if (prop.type === 'options' && prop.options && paramValue !== undefined) {\n const selectedOption = (prop.options as PropertyOption[]).find(\n opt => opt.value === paramValue\n );\n if (selectedOption?.routing) {\n configs.push(selectedOption.routing);\n }\n }\n\n // Handle multiOptions type\n if (prop.type === 'multiOptions' && prop.options && Array.isArray(paramValue)) {\n for (const val of paramValue) {\n const selectedOption = (prop.options as PropertyOption[]).find(\n opt => opt.value === val\n );\n if (selectedOption?.routing) {\n configs.push(selectedOption.routing);\n }\n }\n }\n\n // Handle collection/fixedCollection - recurse into sub-properties\n if ((prop.type === 'collection' || prop.type === 'fixedCollection') && prop.options) {\n const subProperties = prop.options as DeclarativeProperty[];\n const subParams = paramValue || {};\n \n // For fixedCollection, the value is nested under property names\n if (typeof subParams === 'object') {\n for (const subProp of subProperties) {\n const subValue = subParams[subProp.name];\n if (subValue !== undefined && subProp.routing) {\n configs.push(subProp.routing);\n }\n }\n }\n }\n }\n\n return configs;\n}\n\n/**\n * Get routing configuration from a property based on its value\n */\nfunction getPropertyRouting(\n prop: DeclarativeProperty,\n parameters: Record<string, any>,\n expressionContext: ExpressionContext\n): RoutingConfig | null {\n const value = parameters[prop.name];\n \n // If property has direct routing\n if (prop.routing && value !== undefined) {\n return prop.routing;\n }\n\n return null;\n}\n\n/**\n * Merge a routing config into the axios config\n */\nfunction mergeRoutingIntoConfig(\n config: AxiosRequestConfig,\n routing: RoutingConfig,\n expressionContext: ExpressionContext\n): AxiosRequestConfig {\n const request = routing.request;\n \n if (!request) {\n return config;\n }\n\n // Update method if specified\n if (request.method) {\n config.method = request.method as Method;\n }\n\n // Update URL if specified\n if (request.url) {\n const resolvedUrl = resolveExpression(request.url, expressionContext);\n config.url = resolvedUrl;\n }\n\n // Update base URL if specified\n if (request.baseURL) {\n config.baseURL = resolveExpression(request.baseURL, expressionContext);\n }\n\n // Merge headers\n if (request.headers) {\n config.headers = {\n ...config.headers,\n ...resolveExpression(request.headers, expressionContext),\n };\n }\n\n // Merge query parameters\n if (request.qs) {\n config.params = {\n ...config.params,\n ...resolveExpression(request.qs, expressionContext),\n };\n }\n\n // Handle body\n if (request.body) {\n const resolvedBody = resolveExpression(request.body, expressionContext);\n if (typeof config.data === 'object' && typeof resolvedBody === 'object') {\n config.data = { ...config.data, ...resolvedBody };\n } else {\n config.data = resolvedBody;\n }\n }\n\n // Handle send configuration\n if (request.send || routing.send) {\n const send = request.send || routing.send!;\n const sendData = processSend(send, expressionContext);\n \n if (send.type === 'body') {\n if (send.property) {\n // Nest under a property\n config.data = {\n ...config.data,\n [send.property]: sendData,\n };\n } else {\n config.data = {\n ...config.data,\n ...sendData,\n };\n }\n } else if (send.type === 'query') {\n config.params = {\n ...config.params,\n ...sendData,\n };\n }\n }\n\n return config;\n}\n\n/**\n * Process send configuration to build data\n */\nfunction processSend(send: RoutingSend, expressionContext: ExpressionContext): Record<string, any> {\n const data: Record<string, any> = {};\n\n if (send.properties) {\n for (const [key, value] of Object.entries(send.properties)) {\n data[key] = resolveExpression(value, expressionContext);\n }\n }\n\n if (send.value !== undefined) {\n return resolveExpression(send.value, expressionContext);\n }\n\n return data;\n}\n\n// ============================================================================\n// Response Processor\n// ============================================================================\n\n/**\n * Process the response according to output configuration\n */\nexport function processResponse(\n response: any,\n routing: RoutingConfig | undefined,\n expressionContext: ExpressionContext\n): any {\n if (!routing?.output?.postReceive) {\n return response;\n }\n\n let result = response;\n const ctx = { ...expressionContext, $response: response };\n\n for (const action of routing.output.postReceive) {\n result = applyPostReceiveAction(result, action, ctx);\n }\n\n return result;\n}\n\n/**\n * Apply a single post-receive action\n */\nfunction applyPostReceiveAction(\n data: any,\n action: PostReceiveAction,\n context: ExpressionContext\n): any {\n switch (action.type) {\n case 'set':\n if (action.properties?.value) {\n return resolveExpression(action.properties.value, context);\n }\n return data;\n\n case 'setKeyValue':\n if (action.properties?.key) {\n const key = resolveExpression(action.properties.key, context);\n return { [key]: data };\n }\n return data;\n\n case 'rootProperty':\n if (action.properties?.property) {\n const prop = action.properties.property;\n return data?.[prop];\n }\n return data;\n\n case 'filter':\n if (action.properties?.enabled !== undefined) {\n const enabled = resolveExpression(action.properties.enabled, context);\n if (!enabled) {\n return [];\n }\n }\n return data;\n\n case 'limit':\n if (Array.isArray(data) && action.properties?.maxResults) {\n return data.slice(0, action.properties.maxResults);\n }\n return data;\n\n case 'sort':\n // Basic sort implementation\n if (Array.isArray(data)) {\n return [...data].sort();\n }\n return data;\n\n default:\n return data;\n }\n}\n\n// ============================================================================\n// Declarative Executor\n// ============================================================================\n\n/**\n * Execute a declarative node\n */\nexport async function executeDeclarativeNode(\n node: IDeclarativeNodeType,\n context: DeclarativeExecutionContext\n): Promise<DeclarativeExecutionResult> {\n const description = node.description;\n \n // Build the request configuration\n const requestConfig = buildRequest(description, context);\n \n // Add credentials to headers if needed\n if (context.credentials) {\n applyCredentials(requestConfig, context.credentials, description);\n }\n\n // Ensure we have a URL\n if (!requestConfig.url && !requestConfig.baseURL) {\n throw new Error('No URL specified in request configuration or defaults');\n }\n\n try {\n // Make the request\n const response = await axios(requestConfig);\n\n // Find the operation routing for response processing\n const operationRouting = findOperationRouting(description.properties, context.parameters);\n \n // Process the response\n const expressionContext: ExpressionContext = {\n $parameter: context.parameters,\n $credentials: context.credentials || {},\n $response: response.data,\n };\n \n const processedData = processResponse(response.data, operationRouting, expressionContext);\n\n return {\n success: true,\n data: processedData,\n status: response.status,\n headers: response.headers as Record<string, string>,\n };\n } catch (error: any) {\n // Check if we should ignore HTTP errors\n const operationRouting = findOperationRouting(description.properties, context.parameters);\n if (operationRouting?.request?.ignoreHttpStatusErrors && error.response) {\n return {\n success: true,\n data: error.response.data,\n status: error.response.status,\n headers: error.response.headers,\n };\n }\n\n throw new Error(`Request failed: ${error.message}`);\n }\n}\n\n/**\n * Find the routing configuration for the current operation\n */\nfunction findOperationRouting(\n properties: DeclarativeProperty[],\n parameters: Record<string, any>\n): RoutingConfig | undefined {\n for (const prop of properties) {\n if (prop.type === 'options' && prop.options) {\n const value = parameters[prop.name];\n const selectedOption = (prop.options as PropertyOption[]).find(\n opt => opt.value === value\n );\n if (selectedOption?.routing) {\n return selectedOption.routing;\n }\n }\n }\n return undefined;\n}\n\n/**\n * Apply credentials to the request configuration\n */\nfunction applyCredentials(\n config: AxiosRequestConfig,\n credentials: Record<string, any>,\n description: DeclarativeNodeDescription\n): void {\n // Common patterns for credential application\n \n // API Key in header\n if (credentials.apiKey) {\n const headerName = credentials.headerName || credentials.apiKeyHeader || 'Authorization';\n const headerPrefix = credentials.headerPrefix || credentials.apiKeyPrefix || '';\n \n config.headers = {\n ...config.headers,\n [headerName]: headerPrefix ? `${headerPrefix} ${credentials.apiKey}` : credentials.apiKey,\n };\n }\n\n // Bearer token\n if (credentials.accessToken || credentials.token || credentials.bearerToken) {\n const token = credentials.accessToken || credentials.token || credentials.bearerToken;\n config.headers = {\n ...config.headers,\n Authorization: `Bearer ${token}`,\n };\n }\n\n // Basic auth\n if (credentials.username && credentials.password) {\n const auth = Buffer.from(`${credentials.username}:${credentials.password}`).toString('base64');\n config.headers = {\n ...config.headers,\n Authorization: `Basic ${auth}`,\n };\n }\n\n // OAuth2 token\n if (credentials.oauthTokenData?.access_token) {\n config.headers = {\n ...config.headers,\n Authorization: `Bearer ${credentials.oauthTokenData.access_token}`,\n };\n }\n}\n\n// ============================================================================\n// Detection and Integration\n// ============================================================================\n\n/**\n * Check if a loaded module is a declarative node type\n */\nexport function isDeclarativeNode(module: any): boolean {\n // Check if it has the description property with the required fields\n if (!module) return false;\n \n // Could be a class instance or the class itself\n const target = module.description ? module : (module.prototype?.description ? new module() : null);\n \n if (!target?.description) return false;\n \n const desc = target.description;\n \n // Must have properties with routing or requestDefaults\n const hasRoutingProperties = desc.properties?.some((prop: DeclarativeProperty) => {\n if (prop.routing) return true;\n if (prop.type === 'options' && prop.options) {\n return (prop.options as PropertyOption[]).some(opt => opt.routing);\n }\n return false;\n });\n\n const hasRequestDefaults = !!desc.requestDefaults;\n \n return hasRoutingProperties || hasRequestDefaults;\n}\n\n/**\n * Extract declarative node from a loaded module\n */\nexport function extractDeclarativeNode(loadedModule: any): IDeclarativeNodeType | null {\n // Check direct export\n if (isDeclarativeNode(loadedModule)) {\n return loadedModule.description ? loadedModule : new loadedModule();\n }\n\n // Check named exports\n for (const key of Object.keys(loadedModule)) {\n const exported = loadedModule[key];\n if (isDeclarativeNode(exported)) {\n return exported.description ? exported : new exported();\n }\n }\n\n // Check default export\n if (loadedModule.default && isDeclarativeNode(loadedModule.default)) {\n return loadedModule.default.description \n ? loadedModule.default \n : new loadedModule.default();\n }\n\n return null;\n}\n\n/**\n * Convert declarative node to Bits action format for compatibility\n */\nexport function declarativeNodeToBitsAction(node: IDeclarativeNodeType): {\n name: string;\n displayName: string;\n description: string;\n props: Record<string, any>;\n run: (context: { auth?: any; propsValue: Record<string, any> }) => Promise<any>;\n} {\n const desc = node.description;\n\n // Convert declarative properties to bits properties\n const props: Record<string, any> = {};\n for (const prop of desc.properties) {\n props[prop.name] = convertDeclarativePropertyToBitsProp(prop);\n }\n\n return {\n name: desc.name,\n displayName: desc.displayName,\n description: desc.description || '',\n props,\n run: async (context) => {\n const result = await executeDeclarativeNode(node, {\n parameters: context.propsValue,\n credentials: context.auth,\n });\n return result.data;\n },\n };\n}\n\n/**\n * Convert a declarative property to bits property format\n */\nfunction convertDeclarativePropertyToBitsProp(prop: DeclarativeProperty): any {\n const base = {\n displayName: prop.displayName,\n description: prop.description,\n required: prop.required || false,\n defaultValue: prop.default,\n };\n\n switch (prop.type) {\n case 'string':\n return { ...base, type: 'SHORT_TEXT' };\n case 'number':\n return { ...base, type: 'NUMBER' };\n case 'boolean':\n return { ...base, type: 'CHECKBOX' };\n case 'options':\n return {\n ...base,\n type: 'STATIC_DROPDOWN',\n options: {\n options: (prop.options as PropertyOption[]).map(opt => ({\n label: opt.name,\n value: opt.value,\n })),\n },\n };\n case 'json':\n return { ...base, type: 'JSON' };\n case 'collection':\n case 'fixedCollection':\n return { ...base, type: 'OBJECT' };\n default:\n return { ...base, type: 'SHORT_TEXT' };\n }\n}\n\n// Alias for execute\nexport const execute = executeDeclarativeNode;\n", "/**\n * Bits Module Executor\n * \n * Executes bits modules.\n */\n\nimport { ensureModuleInstalled, getModuleName } from '../utils/moduleLoader';\nimport { getModuleMainFile, ModuleDefinition } from '../utils/moduleCloner';\nimport * as path from '@ha-bits/bindings/path';\nimport { simpleRequire } from '../utils/customRequire';\nimport { \n isDeclarativeNode, \n extractDeclarativeNode, \n executeDeclarativeNode,\n declarativeNodeToBitsAction,\n type IDeclarativeNodeType \n} from './declarativeExecutor';\nimport { ILogger, LoggerFactory } from '@ha-bits/core';\n\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// Types \n// ============================================================================\n\n/**\n * Represents a Bits action that can be executed\n */\nexport interface BitsAction {\n name: string;\n displayName: string;\n description: string;\n props: Record<string, any>;\n run: (context: BitsActionContext) => Promise<any>;\n}\n\n/**\n * Context passed to action.run()\n */\nexport interface BitsActionContext {\n auth?: any;\n propsValue: Record<string, any>;\n store?: BitsStore;\n files?: any;\n /** Logger instance for structured logging */\n logger?: ILogger;\n}\n\n/**\n * Represents a Bits trigger\n */\nexport interface BitsTrigger {\n name: string;\n displayName: string;\n description: string;\n type: BitsTriggerType;\n props: Record<string, any>;\n onEnable?: (context: BitsTriggerContext) => Promise<void>;\n onDisable?: (context: BitsTriggerContext) => Promise<void>;\n run?: (context: BitsTriggerContext) => Promise<any[]>;\n test?: (context: BitsTriggerContext) => Promise<any[]>;\n onHandshake?: (context: BitsTriggerContext) => Promise<any>;\n}\n\n/**\n * Trigger types\n */\nexport enum BitsTriggerType {\n POLLING = 'POLLING',\n WEBHOOK = 'WEBHOOK',\n APP_WEBHOOK = 'APP_WEBHOOK',\n}\n\n/**\n * Context passed to trigger methods\n */\nexport interface BitsTriggerContext {\n auth?: any;\n propsValue: Record<string, any>;\n payload: unknown;\n webhookUrl?: string;\n store: BitsStore;\n app: {\n createListeners: (listener: BitsListener) => void;\n };\n setSchedule: (options: BitsScheduleOptions) => void;\n}\n\n/**\n * Listener configuration for app webhooks\n */\nexport interface BitsListener {\n events: string[];\n identifierValue: string;\n identifierKey: string;\n}\n\n/**\n * Schedule options for polling triggers\n */\nexport interface BitsScheduleOptions {\n cronExpression: string;\n timezone?: string;\n}\n\n/**\n * Simple key-value store interface\n */\nexport interface BitsStore {\n get: <T>(key: string) => Promise<T | null>;\n put: <T>(key: string, value: T) => Promise<void>;\n delete: (key: string) => Promise<void>;\n}\n\n/**\n * Represents a loaded Bits piece/module\n */\nexport interface BitsPiece {\n displayName: string;\n description?: string;\n logoUrl?: string;\n auth?: any;\n actions: () => Record<string, BitsAction>;\n triggers: () => Record<string, BitsTrigger>;\n}\n\n/**\n * Execution parameters for bits module\n */\nexport interface BitsExecutionParams {\n source: string;\n framework: string;\n moduleName: string;\n params: Record<string, any>;\n /** Logger instance to pass to bit context */\n logger?: ILogger;\n /** Workflow ID for context */\n workflowId?: string;\n /** Node ID for context */\n nodeId?: string;\n /** Execution ID for tracing */\n executionId?: string;\n}\n\n/**\n * Result of bits module execution\n */\nexport interface BitsExecutionResult {\n success: boolean;\n module: string;\n pieceLoaded: boolean;\n params: Record<string, any>;\n result: any;\n executedAt: string;\n data: {\n message: string;\n status: string;\n pieceExports: string[];\n };\n}\n\n// ============================================================================\n// Module Loading\n// ============================================================================\n\n/**\n * Extract piece from a loaded module.\n * Bits modules export a piece object with 'actions' and 'triggers' properties.\n * Also supports declarative nodes (n8n-style) that have a description with routing.\n */\nfunction extractBitsPieceFromModule(loadedModule: any): BitsPiece {\n // First, check if this is a declarative node (n8n-style with routing)\n const declarativeNode = extractDeclarativeNode(loadedModule);\n if (declarativeNode) {\n logger.log(`\uD83D\uDCCB Detected declarative node: ${declarativeNode.description.displayName}`);\n return convertDeclarativeNodeToBitsPiece(declarativeNode);\n }\n\n // Find the piece export in the module\n // It's the object that has both 'actions' and 'triggers' methods/properties\n let piece: any = null;\n\n // Check if it's a direct export\n if (loadedModule && typeof loadedModule === 'object') {\n // Check direct properties\n for (const key of Object.keys(loadedModule)) {\n const exported = loadedModule[key];\n if (exported && typeof exported === 'object') {\n // Check if it has actions and triggers (either as functions or objects)\n const hasActions = 'actions' in exported;\n const hasTriggers = 'triggers' in exported;\n if (hasActions && hasTriggers) {\n piece = exported;\n break;\n }\n }\n }\n }\n\n if (!piece) {\n throw new Error('No valid bits piece found in module. Expected export with actions and triggers.');\n }\n\n // Normalize the piece to our interface\n return {\n displayName: piece.displayName || 'Unknown Piece',\n description: piece.description,\n logoUrl: piece.logoUrl,\n auth: piece.auth,\n actions: typeof piece.actions === 'function' \n ? piece.actions.bind(piece)\n : () => piece.actions || {},\n triggers: typeof piece.triggers === 'function'\n ? piece.triggers.bind(piece)\n : () => piece.triggers || {},\n };\n}\n\n/**\n * Convert a declarative node to BitsPiece format\n */\nfunction convertDeclarativeNodeToBitsPiece(node: IDeclarativeNodeType): BitsPiece {\n const desc = node.description;\n \n // Extract operations from properties to create actions\n const actions: Record<string, BitsAction> = {};\n \n // Find operation/resource properties to determine available actions\n const operationProp = desc.properties.find(p => p.name === 'operation');\n const resourceProp = desc.properties.find(p => p.name === 'resource');\n \n if (operationProp?.options) {\n // Create an action for each operation\n for (const opt of operationProp.options as any[]) {\n if (opt.value && opt.routing) {\n const actionName = String(opt.value);\n actions[actionName] = {\n name: actionName,\n displayName: opt.name || actionName,\n description: opt.description || '',\n props: buildPropsForOperation(desc.properties, actionName, resourceProp?.default),\n run: createDeclarativeActionRunner(node, actionName),\n };\n }\n }\n }\n \n // If no operation-based actions found, create a single \"execute\" action\n if (Object.keys(actions).length === 0) {\n actions['execute'] = {\n name: 'execute',\n displayName: desc.displayName,\n description: desc.description || '',\n props: buildPropsFromDeclarative(desc.properties),\n run: createDeclarativeActionRunner(node),\n };\n }\n\n return {\n displayName: desc.displayName,\n description: desc.description,\n logoUrl: desc.icon,\n auth: undefined, // Declarative nodes handle auth differently\n actions: () => actions,\n triggers: () => ({}), // Declarative nodes typically don't have triggers\n };\n}\n\n/**\n * Build props for a specific operation\n */\nfunction buildPropsForOperation(\n properties: any[],\n operation: string,\n resource?: string\n): Record<string, any> {\n const props: Record<string, any> = {};\n \n for (const prop of properties) {\n // Skip operation and resource props - they're handled differently\n if (prop.name === 'operation' || prop.name === 'resource') continue;\n \n // Check if prop should be shown for this operation\n if (prop.displayOptions?.show) {\n const showOp = prop.displayOptions.show.operation;\n const showRes = prop.displayOptions.show.resource;\n \n if (showOp && !showOp.includes(operation)) continue;\n if (showRes && resource && !showRes.includes(resource)) continue;\n }\n \n props[prop.name] = convertDeclarativePropertyToProp(prop);\n }\n \n return props;\n}\n\n/**\n * Build props from declarative properties\n */\nfunction buildPropsFromDeclarative(properties: any[]): Record<string, any> {\n const props: Record<string, any> = {};\n \n for (const prop of properties) {\n props[prop.name] = convertDeclarativePropertyToProp(prop);\n }\n \n return props;\n}\n\n/**\n * Convert declarative property to bits prop format\n */\nfunction convertDeclarativePropertyToProp(prop: any): any {\n const base = {\n displayName: prop.displayName,\n description: prop.description,\n required: prop.required || false,\n defaultValue: prop.default,\n };\n\n switch (prop.type) {\n case 'string':\n return { ...base, type: 'SHORT_TEXT' };\n case 'number':\n return { ...base, type: 'NUMBER' };\n case 'boolean':\n return { ...base, type: 'CHECKBOX' };\n case 'options':\n return {\n ...base,\n type: 'STATIC_DROPDOWN',\n options: {\n options: (prop.options || []).map((opt: any) => ({\n label: opt.name,\n value: opt.value,\n })),\n },\n };\n case 'json':\n return { ...base, type: 'JSON' };\n case 'collection':\n case 'fixedCollection':\n return { ...base, type: 'OBJECT' };\n default:\n return { ...base, type: 'SHORT_TEXT' };\n }\n}\n\n/**\n * Create a runner function for declarative actions\n */\nfunction createDeclarativeActionRunner(\n node: IDeclarativeNodeType,\n operation?: string\n): (context: BitsActionContext) => Promise<any> {\n return async (context: BitsActionContext) => {\n const parameters = { ...context.propsValue };\n \n // Add operation to parameters if specified\n if (operation) {\n parameters.operation = operation;\n }\n \n const result = await executeDeclarativeNode(node, {\n parameters,\n credentials: context.auth,\n });\n \n return result.data;\n };\n}\n\n/**\n * Load a bits piece from module definition\n */\nasync function pieceFromModule(moduleDefinition: ModuleDefinition): Promise<BitsPiece> {\n const moduleName = getModuleName(moduleDefinition);\n\n // Get the main file path\n const mainFilePath = getModuleMainFile(moduleDefinition);\n if (!mainFilePath) {\n throw new Error(`Could not locate main file for module: ${moduleName}`);\n }\n\n logger.log(`\uD83D\uDCE6 Bits module ready at: ${mainFilePath}`);\n\n // Save current working directory and change to module directory for proper resolution\n const originalCwd = process.cwd();\n const moduleDir = path.dirname(mainFilePath);\n\n // Find the node_modules directory containing the module\n let nodeModulesDir = moduleDir;\n while (nodeModulesDir && !nodeModulesDir.endsWith('/node_modules') && nodeModulesDir !== path.dirname(nodeModulesDir)) {\n nodeModulesDir = path.dirname(nodeModulesDir);\n }\n\n try {\n process.chdir(moduleDir);\n // Use simpleRequire which creates require from the node_modules context\n const loadedModule = simpleRequire(mainFilePath, nodeModulesDir);\n\n // Extract piece\n const piece = extractBitsPieceFromModule(loadedModule);\n \n process.chdir(originalCwd);\n return piece;\n } catch (error: any) {\n process.chdir(originalCwd);\n logger.error(error.stack);\n throw error;\n }\n}\n\n// ============================================================================\n// Action Execution\n// ============================================================================\n\n/**\n * Execute a bits module action\n */\nasync function executeGenericBitsPiece(\n params: BitsExecutionParams,\n moduleDefinition: ModuleDefinition\n): Promise<BitsExecutionResult> {\n try {\n const piece = await pieceFromModule(moduleDefinition);\n\n logger.log(`\uD83D\uDE80 Executing Bits piece: ${piece.displayName}`);\n const actionName = params.params.operation;\n const pieceActions = piece.actions();\n logger.log(`Available actions: ${Object.keys(pieceActions).join(', ')}`);\n logger.log(`Requested action: ${actionName}`);\n \n const action = pieceActions[actionName];\n\n // If action is not found, throw error with available actions\n if (!action) {\n throw new Error(\n `Action '${actionName}' not found in piece '${piece.displayName}'. Available actions: ${Object.keys(pieceActions).join(', ')}`\n );\n }\n\n // Extract auth from credentials if present\n let auth: any = undefined;\n const { credentials, ...actionProps } = params.params;\n if (credentials) {\n const credentialKeys = Object.keys(credentials);\n if (credentialKeys.length > 0) {\n // Pass auth data directly - pieces access auth properties directly (e.g., auth.host, auth.apiKey)\n auth = credentials[credentialKeys[0]];\n logger.log(`\uD83D\uDD10 Using credentials for: ${credentialKeys[0]}`);\n }\n }\n\n // Create bit-scoped logger if a parent logger was provided\n let bitLogger: ILogger | undefined = undefined;\n if (params.logger) {\n bitLogger = params.logger.child({\n bitName: moduleDefinition.repository,\n actionName: actionName,\n workflowId: params.workflowId,\n nodeId: params.nodeId,\n executionId: params.executionId,\n });\n }\n\n // Execute the action\n const result = await action.run({\n auth,\n propsValue: {\n ...actionProps,\n },\n logger: bitLogger,\n } as BitsActionContext);\n\n logger.log(`\u2705 Successfully executed Bits piece action: ${actionName}`, result);\n\n return {\n success: true,\n module: moduleDefinition.repository,\n pieceLoaded: true,\n params,\n result,\n executedAt: new Date().toISOString(),\n data: {\n message: `Successfully executed Bits piece: ${piece.displayName}`,\n status: 'completed',\n pieceExports: Object.keys(pieceActions),\n },\n };\n } catch (error: any) {\n logger.error(error.stack);\n throw error;\n }\n}\n\n// ============================================================================\n// Main Export\n// ============================================================================\n\n/**\n * Execute a bits module.\n * This is the main entry point for running bits modules.\n */\nexport async function executeBitsModule(params: BitsExecutionParams): Promise<BitsExecutionResult> {\n // Get module definition from config\n const moduleDefinition: ModuleDefinition = {\n framework: params.framework,\n source: params.source as 'github' | 'npm',\n repository: params.moduleName,\n };\n\n if (!moduleDefinition) {\n throw new Error(`Bits module '${params.moduleName}' not found in modules.json`);\n }\n\n // Ensure module is installed\n const inferredModuleName = getModuleName(moduleDefinition);\n logger.log(`\\n\uD83D\uDD0D Ensuring bits module is ready: ${inferredModuleName}`);\n await ensureModuleInstalled(moduleDefinition);\n\n try {\n return await executeGenericBitsPiece(params, moduleDefinition);\n } catch (error: any) {\n throw new Error(`Failed to load Bits module from '${moduleDefinition.repository}': ${error.message}`);\n }\n}\n\n/**\n * Get available actions from a bits module\n */\nexport async function getBitsModuleActions(params: {\n source: string;\n framework: string;\n moduleName: string;\n}): Promise<string[]> {\n const moduleDefinition: ModuleDefinition = {\n framework: params.framework,\n source: params.source as 'github' | 'npm',\n repository: params.moduleName,\n };\n\n await ensureModuleInstalled(moduleDefinition);\n const piece = await pieceFromModule(moduleDefinition);\n return Object.keys(piece.actions());\n}\n\n/**\n * Get available triggers from a bits module\n */\nexport async function getBitsModuleTriggers(params: {\n source: string;\n framework: string;\n moduleName: string;\n}): Promise<string[]> {\n const moduleDefinition: ModuleDefinition = {\n framework: params.framework,\n source: params.source as 'github' | 'npm',\n repository: params.moduleName,\n };\n\n await ensureModuleInstalled(moduleDefinition);\n const piece = await pieceFromModule(moduleDefinition);\n return Object.keys(piece.triggers());\n}\n\n// Export the piece loader for use in bitsWatcher\nexport { pieceFromModule, extractBitsPieceFromModule };\n", "/**\n * Bits Trigger Watcher\n * \n * Handles bits module triggers (polling, webhook, app webhook).\n */\n\nimport { ensureModuleInstalled } from '../utils/moduleLoader';\nimport { ModuleDefinition } from '../utils/moduleCloner';\nimport { \n pieceFromModule, \n BitsPiece, \n BitsTrigger, \n BitsTriggerType, \n BitsStore, \n BitsTriggerContext,\n BitsListener,\n BitsScheduleOptions,\n} from './bitsDoer';\nimport { LoggerFactory } from '@ha-bits/core';\n\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// Types\n// ============================================================================\n\nexport enum TriggerHookType {\n ON_ENABLE = 'ON_ENABLE',\n ON_DISABLE = 'ON_DISABLE',\n RUN = 'RUN',\n TEST = 'TEST',\n HANDSHAKE = 'HANDSHAKE',\n}\n\nexport interface TriggerExecutionParams {\n moduleDefinition: ModuleDefinition;\n triggerName: string;\n input: Record<string, any>;\n hookType: TriggerHookType;\n trigger?: BitsTrigger;\n payload?: unknown;\n webhookUrl?: string;\n isTest?: boolean;\n store?: BitsStore;\n}\n\nexport interface TriggerExecutionResult {\n success: boolean;\n output?: unknown[];\n message?: string;\n listeners?: BitsListener[];\n scheduleOptions?: BitsScheduleOptions;\n response?: unknown;\n}\n\n// ============================================================================\n// Simple In-Memory Store\n// ============================================================================\n\nfunction createSimpleStore(prefix: string = ''): BitsStore {\n const storage = new Map<string, unknown>();\n\n return {\n async get<T>(key: string): Promise<T | null> {\n const fullKey = `${prefix}:${key}`;\n return (storage.get(fullKey) as T) ?? null;\n },\n async put<T>(key: string, value: T): Promise<void> {\n const fullKey = `${prefix}:${key}`;\n storage.set(fullKey, value);\n },\n async delete(key: string): Promise<void> {\n const fullKey = `${prefix}:${key}`;\n storage.delete(fullKey);\n },\n };\n}\n\n// ============================================================================\n// Helper to check if value is nil (null or undefined)\n// ============================================================================\n\nfunction isNil(value: any): value is null | undefined {\n return value === null || value === undefined;\n}\n\n// ============================================================================\n// Map trigger type from loaded module to our enum\n// ============================================================================\n\nfunction mapTriggerType(type: string | undefined): BitsTriggerType {\n if (!type) return BitsTriggerType.POLLING;\n \n const typeUpper = type.toUpperCase();\n switch (typeUpper) {\n case 'POLLING':\n return BitsTriggerType.POLLING;\n case 'WEBHOOK':\n return BitsTriggerType.WEBHOOK;\n case 'APP_WEBHOOK':\n return BitsTriggerType.APP_WEBHOOK;\n default:\n return BitsTriggerType.POLLING;\n }\n}\n\n// ============================================================================\n// Bits Trigger Helper\n// ============================================================================\n\nexport const bitsTriggerHelper = {\n /**\n * Load a piece from module definition\n */\n async loadPieceFromModule(moduleDefinition: ModuleDefinition): Promise<BitsPiece> {\n await ensureModuleInstalled(moduleDefinition);\n return pieceFromModule(moduleDefinition);\n },\n\n /**\n * Get a specific trigger from a piece\n */\n async getTrigger(\n moduleDefinition: ModuleDefinition,\n triggerName: string\n ): Promise<{ piece: BitsPiece; trigger: BitsTrigger }> {\n const piece = await this.loadPieceFromModule(moduleDefinition);\n const triggers = piece.triggers();\n const trigger = triggers[triggerName];\n\n if (!trigger) {\n const availableTriggers = Object.keys(triggers).join(', ');\n throw new Error(\n `Trigger '${triggerName}' not found. Available triggers: ${availableTriggers || 'none'}`\n );\n }\n\n return { piece, trigger };\n },\n\n /**\n * Execute a trigger based on hook type\n */\n async executeTrigger(params: TriggerExecutionParams): Promise<TriggerExecutionResult> {\n const { moduleDefinition, triggerName, input, hookType, trigger, payload, webhookUrl, isTest, store } = params;\n\n if (isNil(triggerName)) {\n throw new Error('Trigger name is not set');\n }\n\n let bitsTrigger: BitsTrigger;\n if (trigger) {\n bitsTrigger = trigger;\n } else {\n const { trigger: loadedTrigger } = await this.getTrigger(moduleDefinition, triggerName);\n bitsTrigger = loadedTrigger;\n }\n\n logger.log(`\uD83D\uDD14 Executing bits trigger: ${triggerName} (${hookType})`);\n\n const appListeners: BitsListener[] = [];\n let scheduleOptions: BitsScheduleOptions | undefined;\n const storePrefix = isTest ? 'test' : triggerName;\n\n // Use provided store or create a new one\n const triggerStore = store || createSimpleStore(storePrefix);\n\n // Extract auth from credentials if present\n let auth: any = undefined;\n const { credentials, ...triggerProps } = input;\n if (credentials) {\n const credentialKeys = Object.keys(credentials);\n if (credentialKeys.length > 0) {\n const credentialData = credentials[credentialKeys[0]];\n // Wrap in props structure and also spread at top level\n auth = {\n props: credentialData,\n ...credentialData,\n };\n logger.log(`\uD83D\uDD10 Using credentials for trigger: ${credentialKeys[0]}`);\n }\n }\n\n // Build context for trigger execution\n const context: BitsTriggerContext = {\n auth,\n propsValue: triggerProps,\n payload: payload ?? {},\n webhookUrl,\n store: triggerStore,\n app: {\n createListeners(listener: BitsListener): void {\n appListeners.push(listener);\n },\n },\n setSchedule(options: BitsScheduleOptions): void {\n scheduleOptions = {\n cronExpression: options.cronExpression,\n timezone: options.timezone ?? 'UTC',\n };\n },\n };\n\n try {\n switch (hookType) {\n case TriggerHookType.ON_ENABLE: {\n if (bitsTrigger.onEnable) {\n await bitsTrigger.onEnable(context);\n }\n const triggerType = mapTriggerType((bitsTrigger as any).type);\n return {\n success: true,\n listeners: appListeners,\n scheduleOptions: triggerType === BitsTriggerType.POLLING ? scheduleOptions : undefined,\n };\n }\n\n case TriggerHookType.ON_DISABLE: {\n if (bitsTrigger.onDisable) {\n await bitsTrigger.onDisable(context);\n }\n return { success: true };\n }\n\n case TriggerHookType.HANDSHAKE: {\n if (bitsTrigger.onHandshake) {\n const response = await bitsTrigger.onHandshake(context);\n return {\n success: true,\n response,\n };\n }\n return {\n success: false,\n message: 'Trigger does not support handshake',\n };\n }\n\n case TriggerHookType.TEST: {\n if (bitsTrigger.test) {\n const testResult = await bitsTrigger.test(context);\n return {\n success: true,\n output: Array.isArray(testResult) ? testResult : [testResult],\n };\n }\n return {\n success: false,\n message: 'Trigger does not support test mode',\n output: [],\n };\n }\n\n case TriggerHookType.RUN: {\n if (bitsTrigger.run) {\n const runResult = await bitsTrigger.run(context);\n return {\n success: true,\n output: Array.isArray(runResult) ? runResult : [runResult],\n };\n }\n return {\n success: false,\n message: 'Trigger does not have a run method',\n output: [],\n };\n }\n\n default:\n return {\n success: false,\n message: `Unknown hook type: ${hookType}`,\n };\n }\n } catch (error: any) {\n logger.error(`Error executing trigger ${triggerName}:`, error);\n return {\n success: false,\n message: `Error executing trigger: ${(error)}`,\n output: [],\n };\n }\n },\n\n /**\n * List all triggers from a piece\n */\n async listTriggers(moduleDefinition: ModuleDefinition): Promise<{\n triggers: Array<{\n name: string;\n displayName: string;\n description: string;\n type: BitsTriggerType;\n }>;\n }> {\n const piece = await this.loadPieceFromModule(moduleDefinition);\n const triggers = piece.triggers();\n\n return {\n triggers: Object.entries(triggers).map(([name, trigger]) => ({\n name,\n displayName: trigger.displayName,\n description: trigger.description,\n type: mapTriggerType((trigger as any).type),\n })),\n };\n },\n\n /**\n * Execute trigger with proper flow based on trigger type\n * For polling: calls onEnable first, then run\n * For webhooks: calls run directly\n */\n async executeBitsTrigger(params: {\n moduleDefinition: ModuleDefinition;\n triggerName: string;\n input: Record<string, any>;\n payload?: unknown;\n webhookUrl?: string;\n store?: BitsStore;\n }): Promise<TriggerExecutionResult> {\n const { moduleDefinition, triggerName, input, payload, webhookUrl, store } = params;\n\n // Get the trigger to determine its type\n const { piece, trigger } = await this.getTrigger(moduleDefinition, triggerName);\n const triggerType = mapTriggerType((trigger as any).type);\n\n const triggerStore = store || createSimpleStore(`trigger:${triggerName}`);\n\n switch (triggerType) {\n case BitsTriggerType.POLLING: {\n logger.log(`Polling trigger flow: onEnable \u2192 run`);\n\n const onEnableResult = await this.executeTrigger({\n moduleDefinition,\n triggerName,\n input,\n hookType: TriggerHookType.ON_ENABLE,\n trigger,\n payload,\n webhookUrl,\n isTest: false,\n store: triggerStore,\n });\n\n if (!onEnableResult.success) {\n return onEnableResult;\n }\n\n logger.log(` \u2705 onEnable completed`);\n if (onEnableResult.scheduleOptions) {\n logger.log(` \uD83D\uDCC5 Schedule: ${onEnableResult.scheduleOptions.cronExpression} (${onEnableResult.scheduleOptions.timezone})`);\n }\n if (onEnableResult.listeners && onEnableResult.listeners.length > 0) {\n logger.log(` \uD83D\uDC42 Listeners: ${onEnableResult.listeners.length}`);\n }\n\n logger.log(` \u2192 Calling run to fetch items...`);\n const runResult = await this.executeTrigger({\n moduleDefinition,\n triggerName,\n input,\n hookType: TriggerHookType.RUN,\n trigger,\n payload,\n webhookUrl,\n isTest: false,\n store: triggerStore,\n });\n\n if (!runResult.success) {\n logger.warn(` \u26A0\uFE0F Run failed: ${runResult.message}`);\n } else {\n logger.log(` \u2705 Run completed, items found: ${runResult.output?.length || 0}`);\n }\n\n return runResult;\n }\n\n case BitsTriggerType.WEBHOOK: {\n logger.log(`Webhook trigger`);\n\n return await this.executeTrigger({\n moduleDefinition,\n triggerName,\n input,\n hookType: TriggerHookType.RUN,\n payload,\n webhookUrl,\n isTest: false,\n });\n }\n\n default: {\n return {\n success: false,\n message: `Unsupported trigger type: ${triggerType}`,\n output: [],\n };\n }\n }\n },\n\n /**\n * Hook triggers for a piece - sets up polling/webhooks based on trigger type\n */\n async hookTriggers(\n moduleDefinition: ModuleDefinition,\n options?: {\n webhookBaseUrl?: string;\n onPollingTrigger?: (triggerName: string, trigger: BitsTrigger) => void;\n onWebhookTrigger?: (triggerName: string, trigger: BitsTrigger) => void;\n onAppWebhookTrigger?: (triggerName: string, trigger: BitsTrigger) => void;\n onTriggerResult?: (triggerName: string, result: TriggerExecutionResult) => void;\n input?: Record<string, any>;\n }\n ): Promise<void> {\n const piece = await this.loadPieceFromModule(moduleDefinition);\n const triggers = piece.triggers();\n\n for (const [triggerName, trigger] of Object.entries(triggers)) {\n const triggerType = mapTriggerType((trigger as any).type);\n logger.log(`\uD83D\uDD14 Hooking trigger: ${triggerName} (type: ${triggerType})`);\n\n switch (triggerType) {\n case BitsTriggerType.POLLING:\n logger.log(` \u2192 Setting up polling trigger`);\n if (options?.onPollingTrigger) {\n options.onPollingTrigger(triggerName, trigger);\n }\n\n // Auto-run polling trigger immediately\n logger.log(` \uD83D\uDE80 Running polling trigger immediately...`);\n try {\n const result = await this.executeBitsTrigger({\n moduleDefinition,\n triggerName,\n input: options?.input || {},\n });\n\n if (result.success) {\n logger.log(` \u2705 Trigger ${triggerName} executed successfully`);\n logger.log(` \uD83D\uDCE6 Output items: ${result.output?.length || 0}`);\n } else {\n logger.warn(` \u26A0\uFE0F Trigger ${triggerName} failed: ${result.message}`);\n }\n\n if (options?.onTriggerResult) {\n options.onTriggerResult(triggerName, result);\n }\n } catch (error: any) {\n logger.error(` \u274C Error running trigger ${triggerName}:`, error.message);\n }\n break;\n\n case BitsTriggerType.WEBHOOK:\n logger.log(` \u2192 Setting up webhook trigger`);\n if (options?.onWebhookTrigger) {\n options.onWebhookTrigger(triggerName, trigger);\n }\n break;\n\n case BitsTriggerType.APP_WEBHOOK:\n logger.log(` \u2192 Setting up app webhook trigger`);\n if (options?.onAppWebhookTrigger) {\n options.onAppWebhookTrigger(triggerName, trigger);\n }\n break;\n\n default:\n logger.warn(` \u26A0\uFE0F Unknown trigger type: ${triggerType}`);\n }\n }\n },\n\n /**\n * Validate cron expression (simple validation)\n */\n isValidCron(expression: string): boolean {\n const parts = expression.trim().split(/\\s+/);\n return parts.length >= 5 && parts.length <= 6;\n },\n\n /**\n * Check if a node is a Bits trigger (polling or webhook)\n */\n isBitsTrigger(node: any): boolean {\n return (\n node.data?.framework === 'bits' &&\n (node.data?.triggerType === 'polling' || node.data?.triggerType === 'webhook')\n );\n },\n\n /**\n * Check if a node is a webhook trigger\n */\n isWebhookTrigger(node: any): boolean {\n return (\n node.type === 'trigger' &&\n node.data?.framework === 'bits' &&\n (node.data?.triggerType === 'webhook' || node.data?.operation === 'catch_webhook')\n );\n },\n\n /**\n * Extract webhook trigger configuration from a node\n */\n getWebhookConfig(node: any): {\n nodeId: string;\n path: string;\n authType: 'none' | 'header' | 'query_param';\n authFields: Record<string, any>;\n } {\n return {\n nodeId: node.id,\n path: `/webhook/${node.id}`,\n authType: node.data?.triggerSettings?.authType || 'none',\n authFields: node.data?.triggerSettings?.authFields || {},\n };\n },\n\n /**\n * Execute a webhook trigger with received payload\n */\n async executeWebhookTrigger(\n nodeId: string,\n payload: any,\n headers?: Record<string, string>,\n query?: Record<string, string>\n ): Promise<TriggerExecutionResult> {\n logger.log(`\uD83D\uDD14 Executing webhook trigger for node: ${nodeId}`);\n\n return {\n success: true,\n output: [\n {\n body: payload,\n headers: headers || {},\n query: query || {},\n method: 'POST',\n timestamp: new Date().toISOString(),\n },\n ],\n message: 'Webhook received successfully',\n };\n },\n};\n\n// ============================================================================\n// Utility Functions\n// ============================================================================\n\n/**\n * Try-catch wrapper that returns a result object\n */\nexport async function tryCatch<T>(\n fn: () => Promise<T>\n): Promise<{ data: T | null; error: Error | null }> {\n try {\n const data = await fn();\n return { data, error: null };\n } catch (error: any) {\n return { data: null, error };\n }\n}\n\n// Re-export types for convenience\nexport { \n BitsTrigger, \n BitsTriggerType, \n BitsStore, \n BitsTriggerContext,\n BitsListener,\n BitsScheduleOptions,\n} from './bitsDoer';\n\nexport default bitsTriggerHelper;\n", "/**\n * Script Executor\n * \n * Executes scripts in a Node.js environment.\n * Supports TypeScript/JavaScript (converted from Deno), Python, Go, and Bash scripts.\n */\n\nimport * as fs from 'fs';\nimport * as path from 'path';\nimport * as vm from 'vm';\nimport { spawn, execSync } from 'child_process';\nimport * as os from 'os';\nimport * as ts from 'typescript';\nimport {\n ScriptDefinition,\n ScriptExecutionParams,\n ScriptExecutionResult,\n ScriptContext,\n ScriptState,\n DenoToNodeConversionResult,\n} from './types';\nimport { LoggerFactory } from '@ha-bits/core';\n\nconst logger = LoggerFactory.getRoot();\n\n// ============================================================================\n// Internal State Management\n// ============================================================================\n\nconst internalStates: Map<string, ScriptState> = new Map();\n\nfunction getInternalStatePath(scriptPath: string): string {\n return `state:${scriptPath}`;\n}\n\nasync function getInternalState(scriptPath: string): Promise<any> {\n return internalStates.get(getInternalStatePath(scriptPath)) || null;\n}\n\nasync function setInternalState(scriptPath: string, state: any): Promise<void> {\n internalStates.set(getInternalStatePath(scriptPath), state);\n}\n\n// ============================================================================\n// Deno to Node.js Conversion\n// ============================================================================\n\n/**\n * Convert Deno imports to Node.js compatible imports\n */\nfunction convertDenoImports(code: string): DenoToNodeConversionResult {\n const npmPackages: string[] = [];\n const imports: string[] = [];\n let convertedCode = code;\n\n // Replace Deno.land imports with npm equivalents\n const denoImportPatterns: Array<{\n pattern: RegExp;\n replacement: string | ((match: string, ...args: string[]) => string);\n npmPackage?: string;\n }> = [\n {\n pattern: /import\\s+\\*\\s+as\\s+wmill\\s+from\\s+[\"']https:\\/\\/deno\\.land\\/x\\/[@\\w.]*\\/mod\\.ts[\"'];?/g,\n replacement: `// Script SDK (mocked for Node.js)\nconst wmill = {\n getInternalStatePath: () => '__internal_state__',\n getInternalState: async () => globalThis.__script_state || null,\n setInternalState: async (state) => { globalThis.__script_state = state; },\n getVariable: async (path) => process.env[path] || null,\n setVariable: async (path, value) => { process.env[path] = value; },\n getResource: async (path) => globalThis.__script_resources?.[path] || null,\n};`,\n },\n // Standard library fetch (use native)\n {\n pattern: /import\\s*{\\s*([^}]+)\\s*}\\s*from\\s+[\"']https:\\/\\/deno\\.land\\/std[@\\w.]*\\/http\\/mod\\.ts[\"'];?/g,\n replacement: '', // fetch is native in Node 18+\n },\n // Crypto\n {\n pattern: /import\\s*{\\s*([^}]+)\\s*}\\s*from\\s+[\"']https:\\/\\/deno\\.land\\/std[@\\w.]*\\/crypto\\/mod\\.ts[\"'];?/g,\n replacement: `const crypto = require('crypto');`,\n },\n // Path\n {\n pattern: /import\\s*{\\s*([^}]+)\\s*}\\s*from\\s+[\"']https:\\/\\/deno\\.land\\/std[@\\w.]*\\/path\\/mod\\.ts[\"'];?/g,\n replacement: `const path = require('path');`,\n },\n // fs\n {\n pattern: /import\\s*{\\s*([^}]+)\\s*}\\s*from\\s+[\"']https:\\/\\/deno\\.land\\/std[@\\w.]*\\/fs\\/mod\\.ts[\"'];?/g,\n replacement: `const fs = require('fs').promises;`,\n },\n // npm: imports\n {\n pattern: /import\\s+(?:(\\*\\s+as\\s+\\w+)|{([^}]+)}|(\\w+))\\s+from\\s+[\"']npm:([^@\"']+)(?:@[^\"']*)?[\"'];?/g,\n replacement: (match: string, star: string, named: string, defaultImport: string, pkg: string) => {\n npmPackages.push(pkg);\n if (star) {\n return `const ${star.replace('* as ', '')} = require('${pkg}');`;\n } else if (named) {\n return `const { ${named} } = require('${pkg}');`;\n } else {\n return `const ${defaultImport} = require('${pkg}');`;\n }\n },\n },\n ];\n\n for (const { pattern, replacement, npmPackage } of denoImportPatterns) {\n if (typeof replacement === 'function') {\n convertedCode = convertedCode.replace(pattern, replacement as any);\n } else {\n convertedCode = convertedCode.replace(pattern, replacement);\n }\n if (npmPackage) {\n npmPackages.push(npmPackage);\n }\n }\n\n // Replace Deno.* APIs with Node.js equivalents\n const denoApiReplacements: Array<[RegExp, string]> = [\n [/Deno\\.env\\.get\\(([^)]+)\\)/g, 'process.env[$1]'],\n [/Deno\\.env\\.set\\(([^,]+),\\s*([^)]+)\\)/g, 'process.env[$1] = $2'],\n [/Deno\\.args/g, 'process.argv.slice(2)'],\n [/Deno\\.exit\\(([^)]*)\\)/g, 'process.exit($1)'],\n [/Deno\\.cwd\\(\\)/g, 'process.cwd()'],\n [/Deno\\.readTextFile\\(([^)]+)\\)/g, 'fs.readFileSync($1, \"utf-8\")'],\n [/Deno\\.writeTextFile\\(([^,]+),\\s*([^)]+)\\)/g, 'fs.writeFileSync($1, $2)'],\n [/Deno\\.readFile\\(([^)]+)\\)/g, 'fs.readFileSync($1)'],\n [/Deno\\.writeFile\\(([^,]+),\\s*([^)]+)\\)/g, 'fs.writeFileSync($1, $2)'],\n [/Deno\\.remove\\(([^)]+)\\)/g, 'fs.unlinkSync($1)'],\n [/Deno\\.mkdir\\(([^)]+)\\)/g, 'fs.mkdirSync($1, { recursive: true })'],\n [/Deno\\.stat\\(([^)]+)\\)/g, 'fs.statSync($1)'],\n ];\n\n for (const [pattern, replacement] of denoApiReplacements) {\n convertedCode = convertedCode.replace(pattern, replacement);\n }\n\n // Extract import statements for reference\n const importRegex = /^(import\\s+.+from\\s+['\"].+['\"];?)$/gm;\n let match;\n while ((match = importRegex.exec(code)) !== null) {\n imports.push(match[1]);\n }\n\n return {\n code: convertedCode,\n imports,\n npmPackages: [...new Set(npmPackages)],\n };\n}\n\n/**\n * Convert TypeScript to JavaScript using the TypeScript compiler\n */\nfunction transpileTypeScript(code: string): string {\n // Use TypeScript compiler to transpile\n const result = ts.transpileModule(code, {\n compilerOptions: {\n module: ts.ModuleKind.CommonJS,\n target: ts.ScriptTarget.ES2020,\n strict: false,\n esModuleInterop: true,\n skipLibCheck: true,\n removeComments: false,\n },\n });\n\n let jsCode = result.outputText;\n\n // Remove CommonJS exports wrapper if present\n jsCode = jsCode.replace(/^\"use strict\";\\s*/m, '');\n jsCode = jsCode.replace(/Object\\.defineProperty\\(exports,\\s*\"__esModule\",\\s*\\{\\s*value:\\s*true\\s*\\}\\);?\\s*/g, '');\n jsCode = jsCode.replace(/exports\\.\\w+\\s*=\\s*/g, '');\n\n return jsCode;\n}\n\n/**\n * Convert Deno script to Node.js compatible JavaScript\n */\nexport function convertDenoToNode(code: string): string {\n // First convert Deno-specific imports and APIs\n const { code: convertedCode } = convertDenoImports(code);\n \n // Then transpile TypeScript to JavaScript\n const jsCode = transpileTypeScript(convertedCode);\n \n return jsCode;\n}\n\n// ============================================================================\n// Script Execution\n// ============================================================================\n\n/**\n * Execute a JavaScript/TypeScript script in Node.js\n */\nasync function executeJavaScript(\n code: string,\n params: Record<string, any>,\n context: ScriptContext\n): Promise<any> {\n // Convert Deno code to Node.js\n const nodeCode = convertDenoToNode(code);\n \n // Create a wrapper that exports the main function result\n const wrappedCode = `\n ${nodeCode}\n \n // Execute main function\n (async () => {\n if (typeof main === 'function') {\n return await main(...Object.values(__params__));\n }\n throw new Error('No main function found in script');\n })();\n `;\n\n // Create a sandbox context\n const sandbox: Record<string, any> = {\n __params__: params,\n __context__: context,\n globalThis: {\n __script_state: null,\n __script_resources: {},\n },\n console,\n process,\n require,\n fetch,\n Buffer,\n setTimeout,\n setInterval,\n clearTimeout,\n clearInterval,\n Promise,\n JSON,\n Object,\n Array,\n String,\n Number,\n Boolean,\n Date,\n Math,\n RegExp,\n Error,\n URL,\n URLSearchParams,\n TextEncoder: globalThis.TextEncoder,\n TextDecoder: globalThis.TextDecoder,\n crypto: globalThis.crypto,\n fs: require('fs'),\n path: require('path'),\n };\n\n const vmContext = vm.createContext(sandbox);\n \n try {\n const script = new vm.Script(wrappedCode, {\n filename: 'script-executor.js',\n });\n \n const result = await script.runInContext(vmContext, {\n timeout: 300000, // 5 minute timeout\n });\n \n return result;\n } catch (error: any) {\n logger.error(`JavaScript execution error: ${error.message}`);\n throw error;\n }\n}\n\n/**\n * Execute a Python script\n */\nasync function executePython(\n code: string,\n params: Record<string, any>,\n context: ScriptContext\n): Promise<any> {\n const tmpDir = os.tmpdir();\n const scriptPath = path.join(tmpDir, `script_${Date.now()}.py`);\n \n // Create a wrapper that calls main with parameters\n const paramsList = Object.entries(params)\n .map(([key, value]) => `${key}=${JSON.stringify(value)}`)\n .join(', ');\n \n const wrappedCode = `\nimport json\nimport sys\n\n# Inject context\nflow_input = json.loads('''${JSON.stringify(context.flow_input)}''')\nprevious_result = json.loads('''${JSON.stringify(context.previous_result)}''')\n\n${code}\n\nif __name__ == \"__main__\":\n try:\n result = main(${paramsList})\n print(json.dumps({\"success\": True, \"result\": result}))\n except Exception as e:\n print(json.dumps({\"success\": False, \"error\": str(e)}))\n sys.exit(1)\n`;\n\n fs.writeFileSync(scriptPath, wrappedCode);\n\n return new Promise((resolve, reject) => {\n const pythonCmd = process.platform === 'win32' ? 'python' : 'python3';\n const proc = spawn(pythonCmd, [scriptPath], {\n env: { ...process.env },\n cwd: tmpDir,\n });\n\n let stdout = '';\n let stderr = '';\n\n proc.stdout.on('data', (data) => {\n stdout += data.toString();\n });\n\n proc.stderr.on('data', (data) => {\n stderr += data.toString();\n });\n\n proc.on('close', (exitCode) => {\n // Clean up temp file\n try {\n fs.unlinkSync(scriptPath);\n } catch {}\n\n if (exitCode !== 0) {\n reject(new Error(`Python script failed: ${stderr || stdout}`));\n return;\n }\n\n try {\n // Parse the last line as JSON result\n const lines = stdout.trim().split('\\n');\n const lastLine = lines[lines.length - 1];\n const result = JSON.parse(lastLine);\n \n if (result.success) {\n resolve(result.result);\n } else {\n reject(new Error(result.error));\n }\n } catch (parseError) {\n // Return raw output if not JSON\n resolve(stdout.trim());\n }\n });\n\n proc.on('error', (error) => {\n try {\n fs.unlinkSync(scriptPath);\n } catch {}\n reject(new Error(`Failed to spawn Python: ${error.message}`));\n });\n });\n}\n\n/**\n * Execute a Go script\n */\nasync function executeGo(\n code: string,\n params: Record<string, any>,\n context: ScriptContext\n): Promise<any> {\n const tmpDir = os.tmpdir();\n const scriptDir = path.join(tmpDir, `script_go_${Date.now()}`);\n const scriptPath = path.join(scriptDir, 'main.go');\n \n // Create directory\n fs.mkdirSync(scriptDir, { recursive: true });\n\n // Create a wrapper for the Go code\n const wrappedCode = `\npackage main\n\nimport (\n\t\"encoding/json\"\n\t\"fmt\"\n\t\"os\"\n)\n\nvar flowInput = \\`${JSON.stringify(context.flow_input)}\\`\nvar previousResult = \\`${JSON.stringify(context.previous_result)}\\`\nvar params = \\`${JSON.stringify(params)}\\`\n\n${code}\n\nfunc main() {\n\tvar p map[string]interface{}\n\tjson.Unmarshal([]byte(params), &p)\n\t\n\tresult := Main(p)\n\t\n\toutput, _ := json.Marshal(map[string]interface{}{\n\t\t\"success\": true,\n\t\t\"result\": result,\n\t})\n\tfmt.Println(string(output))\n}\n`;\n\n fs.writeFileSync(scriptPath, wrappedCode);\n\n return new Promise((resolve, reject) => {\n try {\n // Build the Go program\n execSync(`go build -o main`, { cwd: scriptDir, stdio: 'pipe' });\n \n // Run the compiled program\n const proc = spawn('./main', [], {\n cwd: scriptDir,\n env: { ...process.env },\n });\n\n let stdout = '';\n let stderr = '';\n\n proc.stdout.on('data', (data) => {\n stdout += data.toString();\n });\n\n proc.stderr.on('data', (data) => {\n stderr += data.toString();\n });\n\n proc.on('close', (exitCode) => {\n // Clean up\n try {\n fs.rmSync(scriptDir, { recursive: true, force: true });\n } catch {}\n\n if (exitCode !== 0) {\n reject(new Error(`Go script failed: ${stderr || stdout}`));\n return;\n }\n\n try {\n const lines = stdout.trim().split('\\n');\n const lastLine = lines[lines.length - 1];\n const result = JSON.parse(lastLine);\n \n if (result.success) {\n resolve(result.result);\n } else {\n reject(new Error(result.error));\n }\n } catch {\n resolve(stdout.trim());\n }\n });\n\n proc.on('error', (error) => {\n try {\n fs.rmSync(scriptDir, { recursive: true, force: true });\n } catch {}\n reject(new Error(`Failed to run Go: ${error.message}`));\n });\n } catch (error: any) {\n try {\n fs.rmSync(scriptDir, { recursive: true, force: true });\n } catch {}\n reject(new Error(`Failed to build Go: ${error.message}`));\n }\n });\n}\n\n/**\n * Execute a Bash script\n */\nasync function executeBash(\n code: string,\n params: Record<string, any>,\n context: ScriptContext\n): Promise<any> {\n const tmpDir = os.tmpdir();\n const scriptPath = path.join(tmpDir, `script_${Date.now()}.sh`);\n \n // Export parameters as environment variables\n const envExports = Object.entries(params)\n .map(([key, value]) => {\n const safeValue = typeof value === 'string' \n ? value.replace(/'/g, \"'\\\\''\") \n : JSON.stringify(value);\n return `export ${key}='${safeValue}'`;\n })\n .join('\\n');\n \n const wrappedCode = `#!/bin/bash\nset -e\n\n# Exported parameters\n${envExports}\n\n# Context\nexport FLOW_INPUT='${JSON.stringify(context.flow_input)}'\nexport PREVIOUS_RESULT='${JSON.stringify(context.previous_result)}'\n\n# User script\n${code}\n`;\n\n fs.writeFileSync(scriptPath, wrappedCode, { mode: 0o755 });\n\n return new Promise((resolve, reject) => {\n const proc = spawn('bash', [scriptPath], {\n env: { ...process.env },\n cwd: tmpDir,\n });\n\n let stdout = '';\n let stderr = '';\n\n proc.stdout.on('data', (data) => {\n stdout += data.toString();\n });\n\n proc.stderr.on('data', (data) => {\n stderr += data.toString();\n });\n\n proc.on('close', (exitCode) => {\n try {\n fs.unlinkSync(scriptPath);\n } catch {}\n\n if (exitCode !== 0) {\n reject(new Error(`Bash script failed: ${stderr || stdout}`));\n return;\n }\n\n // Try to parse as JSON, otherwise return raw output\n try {\n resolve(JSON.parse(stdout.trim()));\n } catch {\n resolve(stdout.trim());\n }\n });\n\n proc.on('error', (error) => {\n try {\n fs.unlinkSync(scriptPath);\n } catch {}\n reject(new Error(`Failed to spawn Bash: ${error.message}`));\n });\n });\n}\n\n// ============================================================================\n// Script Loading\n// ============================================================================\n\n/**\n * Load a script from the local filesystem\n */\nfunction loadLocalScript(moduleName: string): ScriptDefinition | null {\n const basePath = path.resolve(__dirname, '../../nodes/script', moduleName);\n \n // Try different file extensions\n const extensions = [\n { ext: 'script.ts', language: 'deno' as const },\n { ext: 'script.js', language: 'javascript' as const },\n { ext: 'script.py', language: 'python3' as const },\n { ext: 'script.go', language: 'go' as const },\n { ext: 'script.sh', language: 'bash' as const },\n ];\n\n for (const { ext, language } of extensions) {\n const scriptPath = path.join(basePath, ext);\n if (fs.existsSync(scriptPath)) {\n const content = fs.readFileSync(scriptPath, 'utf-8');\n return {\n type: 'script',\n language,\n content,\n path: scriptPath,\n };\n }\n }\n\n return null;\n}\n\n// ============================================================================\n// Main Execution Function\n// ============================================================================\n\n/**\n * Execute a Script module\n */\nexport async function executeScriptModule(\n params: ScriptExecutionParams\n): Promise<ScriptExecutionResult>;\nexport async function executeScriptModule(\n moduleName: string,\n params: Record<string, any>\n): Promise<ScriptExecutionResult>;\nexport async function executeScriptModule(\n paramsOrModuleName: ScriptExecutionParams | string,\n maybeParams?: Record<string, any>\n): Promise<ScriptExecutionResult> {\n let source: 'local' | 'hub' | 'inline';\n let moduleName: string;\n let executionParams: Record<string, any>;\n let inlineScript: ScriptDefinition | undefined;\n\n if (typeof paramsOrModuleName === 'string') {\n source = 'local';\n moduleName = paramsOrModuleName;\n executionParams = maybeParams || {};\n } else {\n source = paramsOrModuleName.source;\n moduleName = paramsOrModuleName.moduleName;\n executionParams = paramsOrModuleName.params;\n inlineScript = paramsOrModuleName.script;\n }\n\n logger.log(`\\n\uD83C\uDF00 Executing Script module: ${moduleName}`);\n logger.log(` Source: ${source}`);\n\n // Load the script\n let script: ScriptDefinition | null = null;\n\n if (source === 'inline' && inlineScript) {\n script = inlineScript;\n } else if (source === 'local') {\n script = loadLocalScript(moduleName);\n } else if (source === 'hub') {\n // TODO: Implement Script Hub integration\n throw new Error('Script Hub source not yet implemented');\n }\n\n if (!script || !script.content) {\n throw new Error(`Could not load script: ${moduleName}`);\n }\n\n logger.log(` Language: ${script.language}`);\n\n // Create execution context\n const context: ScriptContext = {\n flow_input: executionParams,\n previous_result: executionParams.previous_result || null,\n result: null,\n };\n\n // Execute based on language\n let result: any;\n\n try {\n switch (script.language) {\n case 'deno':\n case 'typescript':\n case 'javascript':\n result = await executeJavaScript(script.content, executionParams, context);\n break;\n\n case 'python3':\n result = await executePython(script.content, executionParams, context);\n break;\n\n case 'go':\n result = await executeGo(script.content, executionParams, context);\n break;\n\n case 'bash':\n result = await executeBash(script.content, executionParams, context);\n break;\n\n default:\n throw new Error(`Unsupported language: ${script.language}`);\n }\n\n logger.log(`\u2705 Script executed successfully`);\n\n return {\n success: true,\n module: moduleName,\n result,\n executedAt: new Date().toISOString(),\n language: script.language,\n data: {\n message: `Successfully executed script: ${moduleName}`,\n status: 'completed',\n output: result,\n },\n };\n } catch (error: any) {\n logger.error(`\u274C Script failed: ${error.message}`);\n\n return {\n success: false,\n module: moduleName,\n result: null,\n executedAt: new Date().toISOString(),\n language: script.language,\n data: {\n message: `Failed to execute script: ${moduleName}`,\n status: 'failed',\n output: null,\n error: error.message,\n },\n };\n }\n}\n\n/**\n * Execute a raw script (inline content)\n */\nexport async function executeScript(\n content: string,\n language: ScriptDefinition['language'],\n params: Record<string, any>,\n options?: { previous_result?: any }\n): Promise<any> {\n const result = await executeScriptModule({\n source: 'inline',\n framework: 'script',\n moduleName: 'inline-script',\n params: {\n ...params,\n previous_result: options?.previous_result,\n },\n script: {\n type: 'script',\n language,\n content,\n },\n });\n\n if (!result.success) {\n throw new Error(result.data.error || 'Script execution failed');\n }\n\n return result.result;\n}\n\n// ============================================================================\n// Exports\n// ============================================================================\n\nexport {\n loadLocalScript,\n getInternalState,\n setInternalState,\n};\n", "/**\n * Security Scanning Module (DLP, PII, Moderation)\n * \n * Provides input scanning capabilities for security concerns.\n * Uses @codenteam/intersect package from private registry.\n */\n\nimport type { ILogger } from '@ha-bits/core';\n\n// ============================================================================\n// Types\n// ============================================================================\n\n/**\n * Security scan configuration from environment variables\n */\nexport interface SecurityScanConfig {\n dlpEnabled: boolean;\n dlpIcapUrl: string | null;\n dlpIcapTimeout: number;\n piiMode: 'log' | 'eradicate' | 'replace' | null;\n moderationEnabled: boolean;\n}\n\n// ============================================================================\n// Configuration\n// ============================================================================\n\n/**\n * Get security configuration from environment variables\n * \n * Environment variables:\n * - HABITS_DLP_ENABLED: Set to 'true' to enable DLP scanning\n * - HABITS_DLP_ICAP_URL: ICAP server URL for enterprise DLP (e.g., icap://server:1344/scan)\n * - HABITS_DLP_ICAP_TIMEOUT: ICAP request timeout in ms (default: 5000)\n * - HABITS_PII_PROTECTION: Set to 'log', 'eradicate', or 'replace'\n * - HABITS_MODERATION_ENABLED: Set to 'true' to enable content moderation\n */\nexport function getSecurityConfig(): SecurityScanConfig {\n const dlpEnabled = process.env.HABITS_DLP_ENABLED === 'true';\n const dlpIcapUrl = process.env.HABITS_DLP_ICAP_URL || null;\n const dlpIcapTimeout = parseInt(process.env.HABITS_DLP_ICAP_TIMEOUT || '5000', 10);\n const piiValue = process.env.HABITS_PII_PROTECTION;\n const piiMode = (piiValue === 'log' || piiValue === 'eradicate' || piiValue === 'replace') ? piiValue : null;\n const moderationEnabled = process.env.HABITS_MODERATION_ENABLED === 'true';\n \n return { dlpEnabled, dlpIcapUrl, dlpIcapTimeout, piiMode, moderationEnabled };\n}\n\n// ============================================================================\n// Scanning Functions\n// ============================================================================\n\n/**\n * Scan input data for security concerns (DLP, PII, Moderation)\n * Called on habits.input.* data and trigger output data\n * \n * @param data - The input data to scan (string, object, or array)\n * @param config - Security configuration from getSecurityConfig()\n * @param logger - Logger instance for output\n * @returns Processed data (potentially redacted/modified based on config)\n */\nexport async function scanInputForSecurity(\n data: any,\n config: SecurityScanConfig,\n logger: ILogger\n): Promise<any> {\n let processedData = data;\n \n // Skip if no security features enabled\n if (!config.dlpEnabled && !config.piiMode && !config.moderationEnabled) {\n return processedData;\n }\n \n try {\n // Import @codenteam/intersect from private registry\n // This package is hosted on a private npm registry and provides DLP, PII, and moderation capabilities\n // @ts-ignore - Package is from private registry, not available at compile time\n const intersect = await import('@codenteam/intersect');\n \n // DLP Scanning\n if (config.dlpEnabled) {\n logger.log('\uD83D\uDD10 [Security] Running DLP scan on input data...');\n try {\n const dlpOptions: { icapUrl?: string; timeout?: number } = {};\n if (config.dlpIcapUrl) {\n dlpOptions.icapUrl = config.dlpIcapUrl;\n dlpOptions.timeout = config.dlpIcapTimeout;\n logger.log(`\uD83D\uDD10 [DLP] Using ICAP server: ${config.dlpIcapUrl}`);\n }\n const dlpResult = await intersect.dlp.consume(processedData, dlpOptions);\n processedData = dlpResult.data ?? processedData;\n if (dlpResult.findings && dlpResult.findings.length > 0) {\n logger.log(`\uD83D\uDD10 [DLP] Found ${dlpResult.findings.length} sensitive data instance(s)`);\n }\n } catch (dlpError: any) {\n logger.warn(`\u26A0\uFE0F [DLP] Scan failed: ${dlpError.message}`);\n }\n }\n \n // PII Protection\n if (config.piiMode) {\n logger.log(`\uD83D\uDD10 [Security] Running PII scan (mode: ${config.piiMode}) on input data...`);\n try {\n const piiResult = await intersect.pii.consume(processedData, { mode: config.piiMode });\n processedData = piiResult.data ?? processedData;\n if (piiResult.detections && piiResult.detections.length > 0) {\n logger.log(`\uD83D\uDD10 [PII] Found ${piiResult.detections.length} PII instance(s) - mode: ${config.piiMode}`);\n }\n } catch (piiError: any) {\n logger.warn(`\u26A0\uFE0F [PII] Scan failed: ${piiError.message}`);\n }\n }\n \n // Content Moderation\n if (config.moderationEnabled) {\n logger.log('\uD83D\uDD10 [Security] Running moderation scan on input data...');\n try {\n const modResult = await intersect.moderation.consume(processedData);\n if (modResult.flagged) {\n logger.warn(`\u26A0\uFE0F [Moderation] Content flagged: ${JSON.stringify(modResult.categories)}`);\n }\n processedData = modResult.data ?? processedData;\n } catch (modError: any) {\n logger.warn(`\u26A0\uFE0F [Moderation] Scan failed: ${modError.message}`);\n }\n }\n } catch (importError: any) {\n // Package not available - log and continue without security scanning\n logger.warn(`\u26A0\uFE0F [Security] @codenteam/intersect package not available: ${importError.message}`);\n logger.warn(' Security features (DLP, PII, Moderation) are disabled.');\n }\n \n return processedData;\n}\n", "/**\n * @ha-bits/cortex ESM Entry Point\n * \n * This module provides a framework-agnostic API for executing habits (workflows)\n * that works in both browser and Node.js environments.\n * \n * Usage:\n * ```typescript\n * import { HabitsExecutor } from '@ha-bits/cortex/esm';\n * \n * const executor = new HabitsExecutor(config, workflows, env);\n * const result = await executor.startWorkflow('my-workflow', { input: 'data' });\n * ```\n * \n * Note: Webhook triggers are NOT supported in this ESM module.\n * For webhook support, use the full server-based exports from '@ha-bits/cortex'.\n */\n\nimport {\n Workflow,\n WorkflowExecution,\n WorkflowConfig,\n LoadedWorkflow,\n StreamCallback,\n} from '@habits/shared/types';\nimport { WorkflowExecutor, InitFromDataOptions } from './WorkflowExecutor';\n\n/**\n * Options for starting a workflow execution.\n */\nexport interface StartWorkflowOptions {\n /** Initial context data (e.g., { habits: { input: {...} } }) */\n initialContext?: Record<string, any>;\n /** Callback for streaming execution events */\n onStream?: StreamCallback;\n /** Pre-populated trigger node outputs */\n triggerData?: Record<string, any>;\n /** Start execution from a specific node */\n startFromNode?: string;\n}\n\n/**\n * HabitsExecutor - Browser/ESM-compatible workflow executor.\n * \n * This class wraps the core WorkflowExecutor and provides a clean OOP API\n * for executing workflows without any Node.js or Express dependencies.\n * \n * Features:\n * - Works in browsers, Deno, Bun, and Node.js\n * - No file system access (all data passed in-memory)\n * - No webhook trigger support (throws error if webhook triggers detected)\n * - Streaming support via callbacks\n * \n * @example\n * ```typescript\n * // Initialize\n * const config: WorkflowConfig = { version: '1.0', workflows: [...] };\n * const workflows = new Map([['my-workflow', workflowDef]]);\n * const env = { OPENAI_API_KEY: 'sk-...' };\n * \n * const executor = new HabitsExecutor(config, workflows, env);\n * \n * // Execute a workflow\n * const result = await executor.startWorkflow('my-workflow', {\n * initialContext: {\n * habits: {\n * input: { prompt: 'Hello world' }\n * }\n * }\n * });\n * \n * console.log(result.output);\n * ```\n */\nexport class HabitsExecutor {\n private executor: WorkflowExecutor;\n private initialized: boolean = false;\n private initPromise: Promise<void> | null = null;\n\n /**\n * Create a new HabitsExecutor instance.\n * \n * @param config - The workflow configuration (describes which workflows are available)\n * @param workflows - Map or Record of workflow ID to workflow definition\n * @param env - Environment variables to pass to workflows (e.g., API keys)\n */\n constructor(\n private config: WorkflowConfig,\n private workflows: Map<string, Workflow> | Record<string, Workflow>,\n private env?: Record<string, string>\n ) {\n this.executor = new WorkflowExecutor();\n // Start initialization immediately\n this.initPromise = this.initialize();\n }\n\n /**\n * Initialize the executor. This is called automatically in the constructor,\n * but can be awaited explicitly if needed.\n */\n private async initialize(): Promise<void> {\n if (this.initialized) return;\n \n await this.executor.initFromData({\n config: this.config,\n workflows: this.workflows,\n env: this.env,\n });\n \n this.initialized = true;\n }\n\n /**\n * Ensure the executor is initialized before operations.\n */\n private async ensureInitialized(): Promise<void> {\n if (this.initPromise) {\n await this.initPromise;\n }\n }\n\n /**\n * Execute a workflow by ID.\n * \n * @param workflowId - The ID of the workflow to execute\n * @param options - Execution options\n * @returns The workflow execution result\n * \n * @throws If the workflow is not found\n * @throws If the workflow contains webhook triggers (not supported in ESM mode)\n * \n * @example\n * ```typescript\n * const result = await executor.startWorkflow('analyze-text', {\n * initialContext: {\n * habits: {\n * input: { text: 'Hello world' }\n * }\n * },\n * onStream: (event) => {\n * console.log('Event:', event.type, event.nodeId);\n * }\n * });\n * ```\n */\n async startWorkflow(\n workflowId: string,\n options?: StartWorkflowOptions\n ): Promise<WorkflowExecution> {\n await this.ensureInitialized();\n \n const loadedWorkflow = this.executor.getWorkflow(workflowId);\n if (!loadedWorkflow) {\n throw new Error(`Workflow not found: ${workflowId}`);\n }\n\n // Execute with no webhook handler - will throw if webhooks are needed\n return this.executor.executeWorkflow(loadedWorkflow.workflow, {\n // No webhookHandler - will throw a clear error if webhook triggers exist\n initialContext: options?.initialContext,\n onStream: options?.onStream,\n triggerData: options?.triggerData,\n startFromNode: options?.startFromNode,\n });\n }\n\n /**\n * Execute a workflow object directly (without loading from config).\n * \n * @param workflow - The workflow definition to execute\n * @param options - Execution options\n * @returns The workflow execution result\n * \n * @example\n * ```typescript\n * const workflow: Workflow = { id: 'inline', name: 'Inline', nodes: [...], edges: [...] };\n * const result = await executor.executeWorkflow(workflow, {\n * initialContext: { habits: { input: { data: 'test' } } }\n * });\n * ```\n */\n async executeWorkflow(\n workflow: Workflow,\n options?: StartWorkflowOptions\n ): Promise<WorkflowExecution> {\n await this.ensureInitialized();\n \n return this.executor.executeWorkflow(workflow, {\n initialContext: options?.initialContext,\n onStream: options?.onStream,\n triggerData: options?.triggerData,\n startFromNode: options?.startFromNode,\n });\n }\n\n /**\n * Get a workflow definition by ID.\n * \n * @param workflowId - The ID of the workflow\n * @returns The loaded workflow or undefined if not found\n */\n async getWorkflow(workflowId: string): Promise<LoadedWorkflow | undefined> {\n await this.ensureInitialized();\n return this.executor.getWorkflow(workflowId);\n }\n\n /**\n * Get all loaded workflows.\n * \n * @returns Array of all loaded workflows\n */\n async getAllWorkflows(): Promise<LoadedWorkflow[]> {\n await this.ensureInitialized();\n return this.executor.getAllWorkflows();\n }\n\n /**\n * Get an execution by ID.\n * \n * @param executionId - The execution ID\n * @returns The execution or undefined if not found\n */\n async getExecution(executionId: string): Promise<WorkflowExecution | undefined> {\n await this.ensureInitialized();\n return this.executor.getExecution(executionId);\n }\n\n /**\n * List all executions.\n * \n * @returns Array of all executions\n */\n async listExecutions(): Promise<WorkflowExecution[]> {\n await this.ensureInitialized();\n return this.executor.listExecutions();\n }\n\n /**\n * Cancel a running execution.\n * \n * @param executionId - The execution ID to cancel\n * @returns True if cancelled, false if not found or not running\n */\n async cancelExecution(executionId: string): Promise<boolean> {\n await this.ensureInitialized();\n return this.executor.cancelExecution(executionId);\n }\n\n /**\n * Get the current configuration.\n * \n * @returns The workflow configuration\n */\n async getConfig(): Promise<WorkflowConfig | null> {\n await this.ensureInitialized();\n return this.executor.getConfig();\n }\n}\n\n// Re-export types for convenience\nexport type {\n Workflow,\n WorkflowExecution,\n WorkflowConfig,\n LoadedWorkflow,\n StreamCallback,\n InitFromDataOptions,\n};\n", "export function assertNotNullOrUndefined<T>(\n value: T | null | undefined,\n fieldName: string,\n): asserts value is T {\n if (value === null || value === undefined) {\n throw new Error(`${fieldName} is null or undefined`)\n }\n}\n\nexport { getNodesBasePath, getNodesPath, getModuleFullPath, getLocalModulePath, clearNodesBasePathCache } from './utils';", "/**\n * Bits Framework\n * \n * This module provides framework utilities for creating bits modules,\n * \n * Modules can import from '@ha-bits/cortex' to access these utilities.\n */\n\nimport axios, { AxiosRequestConfig, AxiosResponse, Method } from 'axios';\nimport { ILogger } from '@ha-bits/core';\n// ============================================================================\n// HTTP Client Types and Implementation\n// ============================================================================\n\n/**\n * Authentication types for HTTP requests\n */\nexport enum AuthenticationType {\n BEARER_TOKEN = 'BEARER_TOKEN',\n BASIC = 'BASIC',\n API_KEY = 'API_KEY',\n CUSTOM = 'CUSTOM',\n NONE = 'NONE',\n}\n\n/**\n * HTTP Methods\n */\nexport enum HttpMethod {\n GET = 'GET',\n POST = 'POST',\n PUT = 'PUT',\n DELETE = 'DELETE',\n PATCH = 'PATCH',\n HEAD = 'HEAD',\n OPTIONS = 'OPTIONS',\n}\n\n/**\n * HTTP request configuration\n */\nexport interface HttpRequest {\n url: string;\n method: HttpMethod;\n headers?: Record<string, string>;\n body?: any;\n queryParams?: Record<string, string>;\n timeout?: number;\n authentication?: {\n type: AuthenticationType;\n token?: string;\n username?: string;\n password?: string;\n apiKey?: string;\n headerName?: string;\n };\n}\n\n/**\n * HTTP response\n */\nexport interface HttpResponse<T = any> {\n status: number;\n headers: Record<string, string>;\n body: T;\n}\n\n/**\n * HTTP client for making requests\n */\nexport const httpClient = {\n async sendRequest<T = any>(request: HttpRequest): Promise<HttpResponse<T>> {\n const config: AxiosRequestConfig = {\n url: request.url,\n method: request.method as Method,\n headers: { ...request.headers },\n data: request.body,\n params: request.queryParams,\n timeout: request.timeout || 30000,\n };\n\n // Handle authentication\n if (request.authentication) {\n switch (request.authentication.type) {\n case AuthenticationType.BEARER_TOKEN:\n config.headers = {\n ...config.headers,\n Authorization: `Bearer ${request.authentication.token}`,\n };\n break;\n case AuthenticationType.BASIC:\n config.auth = {\n username: request.authentication.username || '',\n password: request.authentication.password || '',\n };\n break;\n case AuthenticationType.API_KEY:\n const headerName = request.authentication.headerName || 'X-API-Key';\n config.headers = {\n ...config.headers,\n [headerName]: request.authentication.apiKey || '',\n };\n break;\n }\n }\n\n const response: AxiosResponse<T> = await axios(config);\n\n return {\n status: response.status,\n headers: response.headers as Record<string, string>,\n body: response.data,\n };\n },\n};\n\n// ============================================================================\n// Property Types and Builders\n// ============================================================================\n\n/**\n * Store scope for persistent storage\n */\nexport enum StoreScope {\n PROJECT = 'PROJECT',\n FLOW = 'FLOW',\n}\n\n/**\n * Property value types\n */\nexport type PropertyType = \n | 'SHORT_TEXT'\n | 'LONG_TEXT'\n | 'NUMBER'\n | 'CHECKBOX'\n | 'DROPDOWN'\n | 'STATIC_DROPDOWN'\n | 'MULTI_SELECT_DROPDOWN'\n | 'JSON'\n | 'OBJECT'\n | 'ARRAY'\n | 'FILE'\n | 'DATE_TIME'\n | 'MARKDOWN'\n | 'CUSTOM_AUTH'\n | 'SECRET_TEXT';\n\n/**\n * Base property definition\n */\nexport interface PropertyDefinition<T = any> {\n type: PropertyType;\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: T;\n}\n\n/**\n * Dropdown option\n */\nexport interface DropdownOption<T = any> {\n label: string;\n value: T;\n}\n\n/**\n * Dropdown state (for dynamic dropdowns)\n */\nexport interface DropdownState<T = any> {\n disabled: boolean;\n placeholder?: string;\n options: DropdownOption<T>[];\n}\n\n/**\n * Dynamic dropdown property\n */\nexport interface DynamicDropdownProperty<T = any> extends PropertyDefinition<T> {\n type: 'DROPDOWN';\n refreshers: string[];\n options: (context: { auth?: any; propsValue?: Record<string, any> }) => Promise<DropdownState<T>>;\n}\n\n/**\n * Static dropdown property\n */\nexport interface StaticDropdownProperty<T = any> extends PropertyDefinition<T> {\n type: 'STATIC_DROPDOWN';\n options: {\n disabled?: boolean;\n options: DropdownOption<T>[];\n };\n}\n\n/**\n * Array property for defining arrays with sub-properties\n */\nexport interface ArrayProperty<T = any> extends PropertyDefinition<T[]> {\n type: 'ARRAY';\n properties: Record<string, PropertyDefinition>;\n}\n\n/**\n * File property value\n */\nexport interface FilePropertyValue {\n filename: string;\n data: Buffer;\n extension?: string;\n}\n\n/**\n * Short text property config\n */\ninterface ShortTextConfig {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: string;\n}\n\n/**\n * Long text property config\n */\ninterface LongTextConfig {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: string;\n}\n\n/**\n * Number property config\n */\ninterface NumberConfig {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: number;\n}\n\n/**\n * Checkbox property config\n */\ninterface CheckboxConfig {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: boolean;\n}\n\n/**\n * Dropdown property config\n */\ninterface DropdownConfig<T = any> {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: T;\n refreshers: string[];\n auth?: any;\n options: (context: { auth?: any; propsValue?: Record<string, any> }) => Promise<DropdownState<T>>;\n}\n\n/**\n * Static dropdown property config\n */\ninterface StaticDropdownConfig<T = any> {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: T;\n options: {\n disabled?: boolean;\n options: DropdownOption<T>[];\n };\n}\n\n/**\n * JSON property config\n */\ninterface JsonConfig {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: any;\n}\n\n/**\n * Object property config\n */\ninterface ObjectConfig<T = any> {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: T;\n properties?: Record<string, PropertyDefinition>;\n}\n\n/**\n * Array property config\n */\ninterface ArrayConfig {\n displayName: string;\n description?: string;\n required: boolean;\n defaultValue?: any[];\n properties: Record<string, PropertyDefinition>;\n}\n\n/**\n * File property config\n */\ninterface FileConfig {\n displayName: string;\n description?: string;\n required: boolean;\n}\n\n/**\n * Property builder - creates property definitions\n */\nexport const Property = {\n ShortText(config: ShortTextConfig): PropertyDefinition<string> {\n return {\n type: 'SHORT_TEXT',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n LongText(config: LongTextConfig): PropertyDefinition<string> {\n return {\n type: 'LONG_TEXT',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n Number(config: NumberConfig): PropertyDefinition<number> {\n return {\n type: 'NUMBER',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n Checkbox(config: CheckboxConfig): PropertyDefinition<boolean> {\n return {\n type: 'CHECKBOX',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n Dropdown<T = any>(config: DropdownConfig<T>): DynamicDropdownProperty<T> {\n return {\n type: 'DROPDOWN',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n refreshers: config.refreshers,\n options: config.options,\n };\n },\n\n StaticDropdown<T = any>(config: StaticDropdownConfig<T>): StaticDropdownProperty<T> {\n return {\n type: 'STATIC_DROPDOWN',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n options: config.options,\n };\n },\n\n Json(config: JsonConfig): PropertyDefinition<any> {\n return {\n type: 'JSON',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n Object<T = any>(config: ObjectConfig<T>): PropertyDefinition<T> {\n return {\n type: 'OBJECT',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n Array(config: ArrayConfig): ArrayProperty {\n return {\n type: 'ARRAY',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n properties: config.properties,\n };\n },\n\n File(config: FileConfig): PropertyDefinition<FilePropertyValue> {\n return {\n type: 'FILE',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n };\n },\n\n DateTime(config: { displayName: string; description?: string; required: boolean; defaultValue?: string }): PropertyDefinition<string> {\n return {\n type: 'DATE_TIME',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n defaultValue: config.defaultValue,\n };\n },\n\n Markdown(config: { displayName: string; description?: string; value: string }): PropertyDefinition<string> {\n return {\n type: 'MARKDOWN',\n displayName: config.displayName,\n description: config.description,\n required: false,\n defaultValue: config.value,\n };\n },\n};\n\n// ============================================================================\n// Auth Definitions\n// ============================================================================\n\n/**\n * Custom auth validation result\n */\nexport interface AuthValidationResult {\n valid: boolean;\n error?: string;\n}\n\n/**\n * Custom auth configuration\n */\ninterface CustomAuthConfig<T = any> {\n description?: string;\n required: boolean;\n props: Record<string, PropertyDefinition>;\n validate?: (context: { auth: T }) => Promise<AuthValidationResult>;\n}\n\n/**\n * Secret text configuration\n */\ninterface SecretTextConfig {\n displayName: string;\n description?: string;\n required: boolean;\n}\n\n/**\n * Authentication property builders\n */\nexport const BitAuth = {\n CustomAuth<T = any>(config: CustomAuthConfig<T>): PropertyDefinition & { props: Record<string, PropertyDefinition>; validate?: (context: { auth: T }) => Promise<AuthValidationResult> } {\n return {\n type: 'CUSTOM_AUTH',\n displayName: 'Authentication',\n description: config.description,\n required: config.required,\n props: config.props,\n validate: config.validate,\n };\n },\n\n SecretText(config: SecretTextConfig): PropertyDefinition<string> {\n return {\n type: 'SECRET_TEXT',\n displayName: config.displayName,\n description: config.description,\n required: config.required,\n };\n },\n\n None(): PropertyDefinition<void> {\n return {\n type: 'CUSTOM_AUTH',\n displayName: 'None',\n required: false,\n };\n },\n\n OAuth2(config: any): PropertyDefinition<any> {\n return {\n type: 'CUSTOM_AUTH',\n displayName: 'OAuth2',\n description: config.description,\n required: config.required,\n ...config,\n };\n },\n\n BasicAuth(config: any): PropertyDefinition<{ username: string; password: string }> {\n return {\n type: 'CUSTOM_AUTH',\n displayName: 'Basic Authentication',\n description: config.description,\n required: config.required,\n ...config,\n };\n },\n};\n\nexport const PieceAuth = BitAuth; // Alias for compatibility with AP if needed\n\n// ============================================================================\n// Action Builder\n// ============================================================================\n\n/**\n * Action context passed to run function\n */\nexport interface BitActionContext<AuthType = any, PropsType = any> {\n auth: AuthType;\n propsValue: PropsType;\n store: {\n get: <T>(key: string, scope?: StoreScope) => Promise<T | null>;\n put: <T>(key: string, value: T, scope?: StoreScope) => Promise<void>;\n delete: (key: string, scope?: StoreScope) => Promise<void>;\n };\n files: {\n write: (params: { fileName: string; data: Buffer }) => Promise<string>;\n };\n server: {\n publicUrl: string;\n apiUrl: string;\n };\n /** Logger instance for structured logging within the bit */\n logger?: ILogger;\n}\n\n/**\n * Action definition\n */\nexport interface BitAction<AuthType = any, PropsType = Record<string, any>> {\n name: string;\n displayName: string;\n description: string;\n auth?: PropertyDefinition;\n props: Record<string, PropertyDefinition>;\n run: (context: BitActionContext<AuthType, PropsType>) => Promise<any>;\n}\n\n/**\n * Action configuration for createAction\n */\ninterface ActionConfig<AuthType = any, PropsType = Record<string, any>> {\n name: string;\n displayName: string;\n description: string;\n auth?: PropertyDefinition;\n props: Record<string, PropertyDefinition>;\n run: (context: BitActionContext<AuthType, PropsType>) => Promise<any>;\n}\n\n/**\n * Create a bit action\n */\nexport function createAction<AuthType = any, PropsType = Record<string, any>>(\n config: ActionConfig<AuthType, PropsType>\n): BitAction<AuthType, PropsType> {\n return {\n name: config.name,\n displayName: config.displayName,\n description: config.description,\n auth: config.auth,\n props: config.props,\n run: config.run,\n };\n}\n\n// Alias for compatibility\nexport const createBitAction = createAction;\n\n// ============================================================================\n// Trigger Builder\n// ============================================================================\n\n/**\n * Trigger types\n */\nexport enum TriggerStrategy {\n POLLING = 'POLLING',\n WEBHOOK = 'WEBHOOK',\n APP_WEBHOOK = 'APP_WEBHOOK',\n}\n\n/**\n * Trigger context\n */\nexport interface BitTriggerContext<AuthType = any, PropsType = any> {\n auth: AuthType;\n propsValue: PropsType;\n payload: unknown;\n webhookUrl?: string;\n store: {\n get: <T>(key: string, scope?: StoreScope) => Promise<T | null>;\n put: <T>(key: string, value: T, scope?: StoreScope) => Promise<void>;\n delete: (key: string, scope?: StoreScope) => Promise<void>;\n };\n app: {\n createListeners: (listener: { events: string[]; identifierValue: string; identifierKey: string }) => void;\n };\n setSchedule: (options: { cronExpression: string; timezone?: string }) => void;\n}\n\n/**\n * Trigger definition\n */\nexport interface BitTrigger<AuthType = any, PropsType = Record<string, any>> {\n name: string;\n displayName: string;\n description: string;\n type: TriggerStrategy;\n auth?: PropertyDefinition;\n props: Record<string, PropertyDefinition>;\n onEnable?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<void>;\n onDisable?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<void>;\n run?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<any[]>;\n test?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<any[]>;\n onHandshake?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<any>;\n sampleData?: any;\n}\n\n/**\n * Trigger configuration\n */\ninterface TriggerConfig<AuthType = any, PropsType = Record<string, any>> {\n name: string;\n displayName: string;\n description: string;\n type: TriggerStrategy;\n auth?: PropertyDefinition;\n props: Record<string, PropertyDefinition>;\n onEnable?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<void>;\n onDisable?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<void>;\n run?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<any[]>;\n test?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<any[]>;\n onHandshake?: (context: BitTriggerContext<AuthType, PropsType>) => Promise<any>;\n sampleData?: any;\n}\n\n/**\n * Create a bit trigger\n */\nexport function createTrigger<AuthType = any, PropsType = Record<string, any>>(\n config: TriggerConfig<AuthType, PropsType>\n): BitTrigger<AuthType, PropsType> {\n return {\n name: config.name,\n displayName: config.displayName,\n description: config.description,\n type: config.type,\n auth: config.auth,\n props: config.props,\n onEnable: config.onEnable,\n onDisable: config.onDisable,\n run: config.run,\n test: config.test,\n onHandshake: config.onHandshake,\n sampleData: config.sampleData,\n };\n}\n\n// Alias for compatibility\nexport const createBitTrigger = createTrigger;\n\n// ============================================================================\n// Piece/Bit Builder\n// ============================================================================\n\n/**\n * Piece/Bit categories\n */\nexport enum BitCategory {\n ARTIFICIAL_INTELLIGENCE = 'ARTIFICIAL_INTELLIGENCE',\n COMMUNICATION = 'COMMUNICATION',\n CORE = 'CORE',\n CONTENT_AND_FILES = 'CONTENT_AND_FILES',\n DEVELOPER_TOOLS = 'DEVELOPER_TOOLS',\n BUSINESS_INTELLIGENCE = 'BUSINESS_INTELLIGENCE',\n ACCOUNTING = 'ACCOUNTING',\n SALES_AND_CRM = 'SALES_AND_CRM',\n PRODUCTIVITY = 'PRODUCTIVITY',\n MARKETING = 'MARKETING',\n CUSTOMER_SUPPORT = 'CUSTOMER_SUPPORT',\n PREMIUM = 'PREMIUM',\n}\n\nexport enum PieceCategory {\n ARTIFICIAL_INTELLIGENCE = 'ARTIFICIAL_INTELLIGENCE',\n COMMUNICATION = 'COMMUNICATION',\n CORE = 'CORE',\n CONTENT_AND_FILES = 'CONTENT_AND_FILES',\n DEVELOPER_TOOLS = 'DEVELOPER_TOOLS',\n BUSINESS_INTELLIGENCE = 'BUSINESS_INTELLIGENCE',\n ACCOUNTING = 'ACCOUNTING',\n SALES_AND_CRM = 'SALES_AND_CRM',\n PRODUCTIVITY = 'PRODUCTIVITY',\n MARKETING = 'MARKETING',\n CUSTOMER_SUPPORT = 'CUSTOMER_SUPPORT',\n PREMIUM = 'PREMIUM',\n}\n\n/**\n * Bit/Piece definition\n */\nexport interface Bit<AuthType = any> {\n displayName: string;\n description?: string;\n logoUrl: string;\n minimumSupportedRelease?: string;\n maximumSupportedRelease?: string;\n categories?: BitCategory[];\n auth?: PropertyDefinition;\n actions: Record<string, BitAction<AuthType>>;\n triggers: Record<string, BitTrigger<AuthType>>;\n authors?: string[];\n}\n\n/**\n * Bit configuration for createBit/createPiece\n */\ninterface BitConfig<AuthType = any> {\n displayName: string;\n description?: string;\n logoUrl: string;\n minimumSupportedRelease?: string;\n maximumSupportedRelease?: string;\n categories?: BitCategory[];\n auth?: PropertyDefinition;\n actions: BitAction<AuthType>[];\n triggers?: BitTrigger<AuthType>[];\n authors?: string[];\n}\n\n/**\n * Create a bit/piece module\n */\nexport function createBit<AuthType = any>(config: BitConfig<AuthType>): Bit<AuthType> {\n // Convert arrays to records keyed by name\n const actionsRecord: Record<string, BitAction<AuthType>> = {};\n for (const action of config.actions) {\n actionsRecord[action.name] = action;\n }\n\n const triggersRecord: Record<string, BitTrigger<AuthType>> = {};\n if (config.triggers) {\n for (const trigger of config.triggers) {\n triggersRecord[trigger.name] = trigger;\n }\n }\n\n return {\n displayName: config.displayName,\n description: config.description,\n logoUrl: config.logoUrl,\n minimumSupportedRelease: config.minimumSupportedRelease,\n maximumSupportedRelease: config.maximumSupportedRelease,\n categories: config.categories,\n auth: config.auth,\n actions: actionsRecord,\n triggers: triggersRecord,\n authors: config.authors,\n };\n}\n\nexport const createPiece = createBit;\n\n// ============================================================================\n// Utility: Custom API Call Action\n// ============================================================================\n\n/**\n * Create a custom API call action \n */\nexport function createCustomApiCallAction(config: {\n baseUrl: (auth: any) => string;\n auth: PropertyDefinition;\n authMapping?: (auth: any) => Promise<{ headers: Record<string, string> }>;\n}): BitAction {\n return createAction({\n name: 'custom_api_call',\n displayName: 'Custom API Call',\n description: 'Make a custom API call to any endpoint',\n auth: config.auth,\n props: {\n method: Property.StaticDropdown({\n displayName: 'Method',\n required: true,\n defaultValue: 'GET',\n options: {\n options: [\n { label: 'GET', value: 'GET' },\n { label: 'POST', value: 'POST' },\n { label: 'PUT', value: 'PUT' },\n { label: 'PATCH', value: 'PATCH' },\n { label: 'DELETE', value: 'DELETE' },\n ],\n },\n }),\n path: Property.ShortText({\n displayName: 'Path',\n description: 'API path (e.g., /users)',\n required: true,\n }),\n headers: Property.Json({\n displayName: 'Headers',\n description: 'Request headers as JSON object',\n required: false,\n defaultValue: {},\n }),\n queryParams: Property.Json({\n displayName: 'Query Parameters',\n description: 'Query parameters as JSON object',\n required: false,\n defaultValue: {},\n }),\n body: Property.Json({\n displayName: 'Body',\n description: 'Request body as JSON (for POST, PUT, PATCH)',\n required: false,\n defaultValue: {},\n }),\n },\n async run({ auth, propsValue }) {\n const baseUrl = config.baseUrl(auth);\n const authHeaders = config.authMapping \n ? await config.authMapping(auth)\n : { headers: {} };\n\n const response = await httpClient.sendRequest({\n url: `${baseUrl}${propsValue.path}`,\n method: propsValue.method as HttpMethod,\n headers: {\n ...authHeaders.headers,\n ...(propsValue.headers || {}),\n },\n queryParams: propsValue.queryParams,\n body: propsValue.body,\n });\n\n return response.body;\n },\n });\n}\n\n// ============================================================================\n// Re-exports for convenience\n// ============================================================================\n\nexport {\n // BitsDoer types (for runtime)\n type BitsAction,\n type BitsActionContext,\n type BitsTrigger,\n type BitsTriggerType,\n type BitsTriggerContext,\n type BitsStore,\n type BitsPiece,\n} from './bitsDoer';\n\n// ============================================================================\n// Declarative Node Types (for creating n8n-style declarative bits)\n// ============================================================================\n\nexport {\n // Core types for declarative nodes\n type IDeclarativeNodeType,\n type DeclarativeNodeDescription,\n type DeclarativeProperty,\n type PropertyOption,\n type DisplayOptions,\n type CredentialDefinition,\n \n // Routing configuration\n type RoutingConfig,\n type RoutingRequest,\n type RoutingSend,\n type RoutingOutput,\n type PostReceiveAction,\n type PreSendAction,\n type RequestDefaults,\n type DeclarativeHttpMethod,\n \n // Execution\n type DeclarativeExecutionContext,\n type DeclarativeExecutionResult,\n type ExpressionContext,\n \n // Functions\n executeDeclarativeNode,\n buildRequest,\n resolveExpression,\n processResponse,\n isDeclarativeNode,\n extractDeclarativeNode,\n declarativeNodeToBitsAction,\n} from './declarativeExecutor';\n"],
|
|
5
|
+
"mappings": "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",
|
|
6
|
+
"names": ["path", "resolve", "resolve", "resolve", "ts", "currentDir", "path", "fs", "path", "logger", "path", "logger", "logger", "module", "logger", "options", "resolve", "path", "axios", "logger", "module", "paramValue", "axios", "logger", "logger", "logger", "TriggerStrategy", "extractPieceFromModule", "trimVersionFromAlias", "ensureActivepiecesModulesLoaded", "logger", "TriggerHookType", "module", "trigger", "axios", "path", "module", "logger", "logger", "pieceFromModule", "logger", "createSimpleStore", "isNil", "pieceFromModule", "logger", "fs", "path", "logger", "match", "logger", "resolve", "logger", "axios", "AuthenticationType", "HttpMethod", "StoreScope", "TriggerStrategy", "BitCategory", "PieceCategory"]
|
|
7
7
|
}
|