@path58/n8n-mcp 0.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (319) hide show
  1. package/AGENT_INSTALL.md +223 -0
  2. package/CHANGELOG.md +38 -0
  3. package/LICENSE +21 -0
  4. package/README.md +187 -0
  5. package/dist/autofix/suggestion-fixers/deprecated-node-fixer.js +465 -0
  6. package/dist/autofix/suggestion-fixers/deprecated-node-fixer.js.map +1 -0
  7. package/dist/autofix/suggestion-fixers/fixer-registry.js +495 -0
  8. package/dist/autofix/suggestion-fixers/fixer-registry.js.map +1 -0
  9. package/dist/autofix/suggestion-fixers/l1-structure-fixer.js +639 -0
  10. package/dist/autofix/suggestion-fixers/l1-structure-fixer.js.map +1 -0
  11. package/dist/autofix/suggestion-fixers/l4-connection-fixer.js +449 -0
  12. package/dist/autofix/suggestion-fixers/l4-connection-fixer.js.map +1 -0
  13. package/dist/autofix/suggestion-fixers/l5-parameter-fixer.js +575 -0
  14. package/dist/autofix/suggestion-fixers/l5-parameter-fixer.js.map +1 -0
  15. package/dist/autofix/suggestion-fixers/l5-typeversion-fixer.js +431 -0
  16. package/dist/autofix/suggestion-fixers/l5-typeversion-fixer.js.map +1 -0
  17. package/dist/autofix/suggestion-fixers/l5-webhook-path-fixer.js +356 -0
  18. package/dist/autofix/suggestion-fixers/l5-webhook-path-fixer.js.map +1 -0
  19. package/dist/autofix/suggestion-fixers/l6-ai-tool-variant-fixer.js +618 -0
  20. package/dist/autofix/suggestion-fixers/l6-ai-tool-variant-fixer.js.map +1 -0
  21. package/dist/autofix/suggestion-fixers/l6-pattern-fixer.js +1475 -0
  22. package/dist/autofix/suggestion-fixers/l6-pattern-fixer.js.map +1 -0
  23. package/dist/autofix/suggestion-fixers/llm-fixer.js +716 -0
  24. package/dist/autofix/suggestion-fixers/llm-fixer.js.map +1 -0
  25. package/dist/autofix/suggestion-fixers/missing-credential-fixer.js +336 -0
  26. package/dist/autofix/suggestion-fixers/missing-credential-fixer.js.map +1 -0
  27. package/dist/autofix/suggestion-fixers/types.js +29 -0
  28. package/dist/autofix/suggestion-fixers/types.js.map +1 -0
  29. package/dist/autofix/suggestion-fixers/typo-fixer.js +197 -0
  30. package/dist/autofix/suggestion-fixers/typo-fixer.js.map +1 -0
  31. package/dist/classification/certification-engine.js +208 -0
  32. package/dist/classification/certification-engine.js.map +1 -0
  33. package/dist/classification/feedback-collector.js +516 -0
  34. package/dist/classification/feedback-collector.js.map +1 -0
  35. package/dist/classification/l5-parameter-analyzer.js +670 -0
  36. package/dist/classification/l5-parameter-analyzer.js.map +1 -0
  37. package/dist/classification/l6-graph-analyzer.js +613 -0
  38. package/dist/classification/l6-graph-analyzer.js.map +1 -0
  39. package/dist/classification/severity-classifier.js +237 -0
  40. package/dist/classification/severity-classifier.js.map +1 -0
  41. package/dist/config/env.js +280 -0
  42. package/dist/config/env.js.map +1 -0
  43. package/dist/config/env.schema.js +234 -0
  44. package/dist/config/env.schema.js.map +1 -0
  45. package/dist/config/scraperEnv.js +55 -0
  46. package/dist/config/scraperEnv.js.map +1 -0
  47. package/dist/db/postgresClient.js +38 -0
  48. package/dist/db/postgresClient.js.map +1 -0
  49. package/dist/db/scraperDb.js +6 -0
  50. package/dist/db/scraperDb.js.map +1 -0
  51. package/dist/db/scraperPostgresClient.js +118 -0
  52. package/dist/db/scraperPostgresClient.js.map +1 -0
  53. package/dist/db/validationRepository.js +55 -0
  54. package/dist/db/validationRepository.js.map +1 -0
  55. package/dist/db/validatorPostgresClient.js +248 -0
  56. package/dist/db/validatorPostgresClient.js.map +1 -0
  57. package/dist/db/workflowInstanceMappingRepository.js +128 -0
  58. package/dist/db/workflowInstanceMappingRepository.js.map +1 -0
  59. package/dist/errors/AppError.js +156 -0
  60. package/dist/errors/AppError.js.map +1 -0
  61. package/dist/errors/index.js +7 -0
  62. package/dist/errors/index.js.map +1 -0
  63. package/dist/factory/error-to-problem-mappers.js +385 -0
  64. package/dist/factory/error-to-problem-mappers.js.map +1 -0
  65. package/dist/factory/gap-recorder.js +260 -0
  66. package/dist/factory/gap-recorder.js.map +1 -0
  67. package/dist/factory/problem-recorder.js +94 -0
  68. package/dist/factory/problem-recorder.js.map +1 -0
  69. package/dist/factory/warning-to-gap-mappers.js +493 -0
  70. package/dist/factory/warning-to-gap-mappers.js.map +1 -0
  71. package/dist/factory/workflow-normalizer.js +247 -0
  72. package/dist/factory/workflow-normalizer.js.map +1 -0
  73. package/dist/mcp/adapters/catalog.js +13 -0
  74. package/dist/mcp/adapters/catalog.js.map +1 -0
  75. package/dist/mcp/adapters/index.js +36 -0
  76. package/dist/mcp/adapters/index.js.map +1 -0
  77. package/dist/mcp/adapters/supabase-catalog.js +467 -0
  78. package/dist/mcp/adapters/supabase-catalog.js.map +1 -0
  79. package/dist/mcp/adapters/test-catalog-adapter.js +100 -0
  80. package/dist/mcp/adapters/test-catalog-adapter.js.map +1 -0
  81. package/dist/mcp/adapters/validation.js +258 -0
  82. package/dist/mcp/adapters/validation.js.map +1 -0
  83. package/dist/mcp/build-email-workflow.js +113 -0
  84. package/dist/mcp/build-email-workflow.js.map +1 -0
  85. package/dist/mcp/config.js +22 -0
  86. package/dist/mcp/config.js.map +1 -0
  87. package/dist/mcp/formatters/errors.js +217 -0
  88. package/dist/mcp/formatters/errors.js.map +1 -0
  89. package/dist/mcp/formatters/index.js +12 -0
  90. package/dist/mcp/formatters/index.js.map +1 -0
  91. package/dist/mcp/formatters/response.js +141 -0
  92. package/dist/mcp/formatters/response.js.map +1 -0
  93. package/dist/mcp/quick-test.js +33 -0
  94. package/dist/mcp/quick-test.js.map +1 -0
  95. package/dist/mcp/server.js +70 -0
  96. package/dist/mcp/server.js.map +1 -0
  97. package/dist/mcp/test-mcp-error.js +81 -0
  98. package/dist/mcp/test-mcp-error.js.map +1 -0
  99. package/dist/mcp/test-mcp.js +80 -0
  100. package/dist/mcp/test-mcp.js.map +1 -0
  101. package/dist/mcp/tools/fixes/expression-fixes.js +166 -0
  102. package/dist/mcp/tools/fixes/expression-fixes.js.map +1 -0
  103. package/dist/mcp/tools/fixes/flow-fixes.js +155 -0
  104. package/dist/mcp/tools/fixes/flow-fixes.js.map +1 -0
  105. package/dist/mcp/tools/fixes/index.js +91 -0
  106. package/dist/mcp/tools/fixes/index.js.map +1 -0
  107. package/dist/mcp/tools/fixes/node-fixes.js +233 -0
  108. package/dist/mcp/tools/fixes/node-fixes.js.map +1 -0
  109. package/dist/mcp/tools/fixes/parameter-fixes.js +277 -0
  110. package/dist/mcp/tools/fixes/parameter-fixes.js.map +1 -0
  111. package/dist/mcp/tools/fixes/types.js +10 -0
  112. package/dist/mcp/tools/fixes/types.js.map +1 -0
  113. package/dist/mcp/tools/handlers/check-parameter.js +300 -0
  114. package/dist/mcp/tools/handlers/check-parameter.js.map +1 -0
  115. package/dist/mcp/tools/handlers/find-similar-pattern.js +121 -0
  116. package/dist/mcp/tools/handlers/find-similar-pattern.js.map +1 -0
  117. package/dist/mcp/tools/handlers/get-node-info.js +131 -0
  118. package/dist/mcp/tools/handlers/get-node-info.js.map +1 -0
  119. package/dist/mcp/tools/handlers/get-operation-schema.js +141 -0
  120. package/dist/mcp/tools/handlers/get-operation-schema.js.map +1 -0
  121. package/dist/mcp/tools/handlers/list-nodes.js +126 -0
  122. package/dist/mcp/tools/handlers/list-nodes.js.map +1 -0
  123. package/dist/mcp/tools/handlers/list-operations.js +138 -0
  124. package/dist/mcp/tools/handlers/list-operations.js.map +1 -0
  125. package/dist/mcp/tools/handlers/suggest-fix.js +120 -0
  126. package/dist/mcp/tools/handlers/suggest-fix.js.map +1 -0
  127. package/dist/mcp/tools/handlers/validate-workflow.js +92 -0
  128. package/dist/mcp/tools/handlers/validate-workflow.js.map +1 -0
  129. package/dist/mcp/tools/index.js +190 -0
  130. package/dist/mcp/tools/index.js.map +1 -0
  131. package/dist/mcp/tools/schemas.js +195 -0
  132. package/dist/mcp/tools/schemas.js.map +1 -0
  133. package/dist/mcp/tools/validate.js +95 -0
  134. package/dist/mcp/tools/validate.js.map +1 -0
  135. package/dist/mcp/types/mcp.js +7 -0
  136. package/dist/mcp/types/mcp.js.map +1 -0
  137. package/dist/mcp/utils/timeout.js +78 -0
  138. package/dist/mcp/utils/timeout.js.map +1 -0
  139. package/dist/services/BatchProcessor.js +433 -0
  140. package/dist/services/BatchProcessor.js.map +1 -0
  141. package/dist/services/CheckpointManager.js +281 -0
  142. package/dist/services/CheckpointManager.js.map +1 -0
  143. package/dist/services/CostCalculator.js +211 -0
  144. package/dist/services/CostCalculator.js.map +1 -0
  145. package/dist/services/EmbeddingCache.js +68 -0
  146. package/dist/services/EmbeddingCache.js.map +1 -0
  147. package/dist/services/EmbeddingService.js +143 -0
  148. package/dist/services/EmbeddingService.js.map +1 -0
  149. package/dist/services/RankingService.js +81 -0
  150. package/dist/services/RankingService.js.map +1 -0
  151. package/dist/services/RedisCache.js +376 -0
  152. package/dist/services/RedisCache.js.map +1 -0
  153. package/dist/services/RedisCatalogCache.js +680 -0
  154. package/dist/services/RedisCatalogCache.js.map +1 -0
  155. package/dist/services/ResumeManager.js +252 -0
  156. package/dist/services/ResumeManager.js.map +1 -0
  157. package/dist/services/SearchService.js +282 -0
  158. package/dist/services/SearchService.js.map +1 -0
  159. package/dist/services/SemanticCatalogSearch.js +405 -0
  160. package/dist/services/SemanticCatalogSearch.js.map +1 -0
  161. package/dist/services/ValidationCache.js +157 -0
  162. package/dist/services/ValidationCache.js.map +1 -0
  163. package/dist/services/WorkflowPipelineService.js +1997 -0
  164. package/dist/services/WorkflowPipelineService.js.map +1 -0
  165. package/dist/services/catalog/index.js +34 -0
  166. package/dist/services/catalog/index.js.map +1 -0
  167. package/dist/services/catalog/interfaces.js +17 -0
  168. package/dist/services/catalog/interfaces.js.map +1 -0
  169. package/dist/services/catalog/loaders.js +169 -0
  170. package/dist/services/catalog/loaders.js.map +1 -0
  171. package/dist/services/catalog/types.js +138 -0
  172. package/dist/services/catalog/types.js.map +1 -0
  173. package/dist/services/documentation-normalization/docUrlUtils.js +88 -0
  174. package/dist/services/documentation-normalization/docUrlUtils.js.map +1 -0
  175. package/dist/services/error-quality/ErrorQualityService.js +262 -0
  176. package/dist/services/error-quality/ErrorQualityService.js.map +1 -0
  177. package/dist/services/error-quality/analyzers/CredentialAnalyzer.js +260 -0
  178. package/dist/services/error-quality/analyzers/CredentialAnalyzer.js.map +1 -0
  179. package/dist/services/error-quality/analyzers/IssuePredictor.js +380 -0
  180. package/dist/services/error-quality/analyzers/IssuePredictor.js.map +1 -0
  181. package/dist/services/error-quality/analyzers/MockCoverageAnalyzer.js +267 -0
  182. package/dist/services/error-quality/analyzers/MockCoverageAnalyzer.js.map +1 -0
  183. package/dist/services/error-quality/data/ErrorPatternSeeder.js +963 -0
  184. package/dist/services/error-quality/data/ErrorPatternSeeder.js.map +1 -0
  185. package/dist/services/error-quality/index.js +25 -0
  186. package/dist/services/error-quality/index.js.map +1 -0
  187. package/dist/services/error-quality/reports/ReportGenerator.js +343 -0
  188. package/dist/services/error-quality/reports/ReportGenerator.js.map +1 -0
  189. package/dist/services/error-quality/taxonomy/ErrorTaxonomy.js +698 -0
  190. package/dist/services/error-quality/taxonomy/ErrorTaxonomy.js.map +1 -0
  191. package/dist/services/error-quality/types.js +11 -0
  192. package/dist/services/error-quality/types.js.map +1 -0
  193. package/dist/services/progress/ProgressTracker.js +288 -0
  194. package/dist/services/progress/ProgressTracker.js.map +1 -0
  195. package/dist/services/progress/formatters.js +122 -0
  196. package/dist/services/progress/formatters.js.map +1 -0
  197. package/dist/services/progress/index.js +36 -0
  198. package/dist/services/progress/index.js.map +1 -0
  199. package/dist/services/progress/types.js +7 -0
  200. package/dist/services/progress/types.js.map +1 -0
  201. package/dist/services/search/embeddingGenerator.js +112 -0
  202. package/dist/services/search/embeddingGenerator.js.map +1 -0
  203. package/dist/types/aiCapabilities.js +7 -0
  204. package/dist/types/aiCapabilities.js.map +1 -0
  205. package/dist/types/aiConfigSchema.js +7 -0
  206. package/dist/types/aiConfigSchema.js.map +1 -0
  207. package/dist/utils/bannerLogger.js +186 -0
  208. package/dist/utils/bannerLogger.js.map +1 -0
  209. package/dist/utils/bannerService.js +23 -0
  210. package/dist/utils/bannerService.js.map +1 -0
  211. package/dist/utils/bannerServiceAdapter.js +54 -0
  212. package/dist/utils/bannerServiceAdapter.js.map +1 -0
  213. package/dist/utils/batchLogger.js +171 -0
  214. package/dist/utils/batchLogger.js.map +1 -0
  215. package/dist/utils/bottomStickyBanner.js +239 -0
  216. package/dist/utils/bottomStickyBanner.js.map +1 -0
  217. package/dist/utils/credentialMatcher.js +206 -0
  218. package/dist/utils/credentialMatcher.js.map +1 -0
  219. package/dist/utils/credentialNormalizer.js +442 -0
  220. package/dist/utils/credentialNormalizer.js.map +1 -0
  221. package/dist/utils/integratedBannerLogger.js +59 -0
  222. package/dist/utils/integratedBannerLogger.js.map +1 -0
  223. package/dist/utils/n8nSourceGit.js +195 -0
  224. package/dist/utils/n8nSourceGit.js.map +1 -0
  225. package/dist/utils/nodeTypeNormalizer.js +131 -0
  226. package/dist/utils/nodeTypeNormalizer.js.map +1 -0
  227. package/dist/utils/openaiClient.js +397 -0
  228. package/dist/utils/openaiClient.js.map +1 -0
  229. package/dist/utils/productionLogger.js +16 -0
  230. package/dist/utils/productionLogger.js.map +1 -0
  231. package/dist/utils/progressBarBanner.js +132 -0
  232. package/dist/utils/progressBarBanner.js.map +1 -0
  233. package/dist/utils/scriptHeartbeat.js +117 -0
  234. package/dist/utils/scriptHeartbeat.js.map +1 -0
  235. package/dist/utils/scriptLogger.js +125 -0
  236. package/dist/utils/scriptLogger.js.map +1 -0
  237. package/dist/utils/scriptRunner.js +95 -0
  238. package/dist/utils/scriptRunner.js.map +1 -0
  239. package/dist/utils/scriptTimeout.js +128 -0
  240. package/dist/utils/scriptTimeout.js.map +1 -0
  241. package/dist/utils/scriptWrapper.js +219 -0
  242. package/dist/utils/scriptWrapper.js.map +1 -0
  243. package/dist/utils/stickyBanner.js +226 -0
  244. package/dist/utils/stickyBanner.js.map +1 -0
  245. package/dist/utils/terminalSpinner.js +97 -0
  246. package/dist/utils/terminalSpinner.js.map +1 -0
  247. package/dist/utils/threeLineBanner.js +427 -0
  248. package/dist/utils/threeLineBanner.js.map +1 -0
  249. package/dist/utils/validatorCheckpointManager.js +170 -0
  250. package/dist/utils/validatorCheckpointManager.js.map +1 -0
  251. package/dist/utils/validatorConnectionManager.js +124 -0
  252. package/dist/utils/validatorConnectionManager.js.map +1 -0
  253. package/dist/validation/catalog.js +56 -0
  254. package/dist/validation/catalog.js.map +1 -0
  255. package/dist/validation/config/deprecated-nodes.js +234 -0
  256. package/dist/validation/config/deprecated-nodes.js.map +1 -0
  257. package/dist/validation/config/l6-severity.js +227 -0
  258. package/dist/validation/config/l6-severity.js.map +1 -0
  259. package/dist/validation/config/terminal-nodes.js +132 -0
  260. package/dist/validation/config/terminal-nodes.js.map +1 -0
  261. package/dist/validation/config/unreachable-nodes.js +67 -0
  262. package/dist/validation/config/unreachable-nodes.js.map +1 -0
  263. package/dist/validation/core.js +47 -0
  264. package/dist/validation/core.js.map +1 -0
  265. package/dist/validation/docExtraction.js +12 -0
  266. package/dist/validation/docExtraction.js.map +1 -0
  267. package/dist/validation/dryRunMockRunner.js +128 -0
  268. package/dist/validation/dryRunMockRunner.js.map +1 -0
  269. package/dist/validation/fixtureEngine.js +61 -0
  270. package/dist/validation/fixtureEngine.js.map +1 -0
  271. package/dist/validation/index.js +15 -0
  272. package/dist/validation/index.js.map +1 -0
  273. package/dist/validation/k-levels/k2-blockers.js +222 -0
  274. package/dist/validation/k-levels/k2-blockers.js.map +1 -0
  275. package/dist/validation/l1-structure.js +296 -0
  276. package/dist/validation/l1-structure.js.map +1 -0
  277. package/dist/validation/l2-nodes.js +282 -0
  278. package/dist/validation/l2-nodes.js.map +1 -0
  279. package/dist/validation/l3-credentials.js +322 -0
  280. package/dist/validation/l3-credentials.js.map +1 -0
  281. package/dist/validation/l4-connections.js +698 -0
  282. package/dist/validation/l4-connections.js.map +1 -0
  283. package/dist/validation/l5-parameters.js +803 -0
  284. package/dist/validation/l5-parameters.js.map +1 -0
  285. package/dist/validation/l6-checks/ai-tool-variants.js +407 -0
  286. package/dist/validation/l6-checks/ai-tool-variants.js.map +1 -0
  287. package/dist/validation/l6-checks/catalog-checks.js +260 -0
  288. package/dist/validation/l6-checks/catalog-checks.js.map +1 -0
  289. package/dist/validation/l6-checks/data-contracts.js +197 -0
  290. package/dist/validation/l6-checks/data-contracts.js.map +1 -0
  291. package/dist/validation/l6-checks/deprecation.js +133 -0
  292. package/dist/validation/l6-checks/deprecation.js.map +1 -0
  293. package/dist/validation/l6-checks/error-handling.js +193 -0
  294. package/dist/validation/l6-checks/error-handling.js.map +1 -0
  295. package/dist/validation/l6-checks/expression-syntax.js +387 -0
  296. package/dist/validation/l6-checks/expression-syntax.js.map +1 -0
  297. package/dist/validation/l6-checks/flow-integrity.js +504 -0
  298. package/dist/validation/l6-checks/flow-integrity.js.map +1 -0
  299. package/dist/validation/l6-checks/index.js +106 -0
  300. package/dist/validation/l6-checks/index.js.map +1 -0
  301. package/dist/validation/l6-checks/loops.js +370 -0
  302. package/dist/validation/l6-checks/loops.js.map +1 -0
  303. package/dist/validation/l6-checks/performance.js +182 -0
  304. package/dist/validation/l6-checks/performance.js.map +1 -0
  305. package/dist/validation/l6-checks/security.js +273 -0
  306. package/dist/validation/l6-checks/security.js.map +1 -0
  307. package/dist/validation/l6-patterns.js +472 -0
  308. package/dist/validation/l6-patterns.js.map +1 -0
  309. package/dist/validation/mockLevelResolver.js +95 -0
  310. package/dist/validation/mockLevelResolver.js.map +1 -0
  311. package/dist/validation/n8nApiClient.js +21 -0
  312. package/dist/validation/n8nApiClient.js.map +1 -0
  313. package/dist/validation/n8nCli.js +87 -0
  314. package/dist/validation/n8nCli.js.map +1 -0
  315. package/dist/validation/types.js +8 -0
  316. package/dist/validation/types.js.map +1 -0
  317. package/dist/validation/usageStats.js +82 -0
  318. package/dist/validation/usageStats.js.map +1 -0
  319. package/package.json +274 -0
@@ -0,0 +1,281 @@
1
+ /**
2
+ * Checkpoint Manager Service
3
+ *
4
+ * Enhanced checkpoint/resume capability for long-running pipeline operations.
5
+ * Saves full state to database for reliable resume after interruptions.
6
+ *
7
+ * **Extends shared-utilities patterns:**
8
+ * - Follows shared-utilities CheckpointManager concepts
9
+ * - Enhanced for pipeline operations with full state tracking
10
+ * - Supports arrays of processed/failed items (not just last ID)
11
+ * - Detailed progress metrics (not just counts)
12
+ * - Full state restoration for complex operations
13
+ *
14
+ * **Integration:**
15
+ * - Integrates with banner service for progress display
16
+ * - Works with script runner for automatic checkpoint management
17
+ * - Reports checkpoint progress to banner service when provided
18
+ *
19
+ * Features:
20
+ * - Save checkpoint state to database
21
+ * - Load checkpoint state
22
+ * - Update checkpoint progress
23
+ * - Clear checkpoints
24
+ * - List checkpoints
25
+ * - Automatic state persistence
26
+ * - Banner service integration (optional)
27
+ *
28
+ * @example
29
+ * ```typescript
30
+ * const checkpointManager = new CheckpointManager();
31
+ *
32
+ * // Save checkpoint
33
+ * await checkpointManager.saveCheckpoint({
34
+ * key: 'node-embeddings-v1',
35
+ * pipelineType: 'embedding',
36
+ * state: { processed: 100, success: 95, failed: 5 },
37
+ * processedItems: ['node1', 'node2'],
38
+ * failedItems: ['node3'],
39
+ * progress: { total: 1000, processed: 100 }
40
+ * });
41
+ *
42
+ * // Load checkpoint
43
+ * const checkpoint = await checkpointManager.loadCheckpoint('node-embeddings-v1');
44
+ * if (checkpoint) {
45
+ * console.log(`Resuming from checkpoint: ${checkpoint.progress.processed} items processed`);
46
+ * }
47
+ * ```
48
+ */
49
+ import { validatorQuery } from '../db/validatorPostgresClient.js';
50
+ export class CheckpointManager {
51
+ bannerService;
52
+ /**
53
+ * Create a new CheckpointManager
54
+ *
55
+ * @param bannerService Optional banner service for progress display
56
+ */
57
+ constructor(bannerService) {
58
+ this.bannerService = bannerService;
59
+ }
60
+ /**
61
+ * Set banner service for progress reporting
62
+ *
63
+ * @param bannerService Banner service instance
64
+ */
65
+ setBannerService(bannerService) {
66
+ this.bannerService = bannerService;
67
+ }
68
+ /**
69
+ * Save a checkpoint to the database
70
+ *
71
+ * Creates a new checkpoint or updates existing one with same key.
72
+ * Reports progress to banner service if provided.
73
+ *
74
+ * @param data Checkpoint data to save
75
+ * @returns Saved checkpoint
76
+ */
77
+ async saveCheckpoint(data) {
78
+ const { key, pipelineType, state, processedItems = [], failedItems = [], progress = {} } = data;
79
+ const result = await validatorQuery(`
80
+ INSERT INTO validator.pipeline_checkpoints (
81
+ checkpoint_key,
82
+ pipeline_type,
83
+ state,
84
+ processed_items,
85
+ failed_items,
86
+ progress
87
+ )
88
+ VALUES ($1, $2, $3::jsonb, $4, $5, $6::jsonb)
89
+ ON CONFLICT (checkpoint_key) DO UPDATE SET
90
+ pipeline_type = EXCLUDED.pipeline_type,
91
+ state = EXCLUDED.state,
92
+ processed_items = EXCLUDED.processed_items,
93
+ failed_items = EXCLUDED.failed_items,
94
+ progress = EXCLUDED.progress,
95
+ updated_at = NOW()
96
+ RETURNING
97
+ id::text,
98
+ checkpoint_key as key,
99
+ pipeline_type as "pipelineType",
100
+ state,
101
+ processed_items as "processedItems",
102
+ failed_items as "failedItems",
103
+ progress,
104
+ created_at as "createdAt",
105
+ updated_at as "updatedAt"
106
+ `, [key, pipelineType, JSON.stringify(state), processedItems, failedItems, JSON.stringify(progress)]);
107
+ const row = Array.isArray(result) ? result[0] : result.rows[0];
108
+ const saved = {
109
+ id: row.id,
110
+ key: row.key,
111
+ pipelineType: row.pipelineType,
112
+ state: row.state,
113
+ processedItems: row.processedItems || [],
114
+ failedItems: row.failedItems || [],
115
+ progress: row.progress || {},
116
+ createdAt: row.createdAt,
117
+ updatedAt: row.updatedAt,
118
+ };
119
+ // Report checkpoint progress to banner service if available
120
+ if (this.bannerService && saved.progress) {
121
+ const processed = saved.progress.processed || (saved.processedItems || []).length;
122
+ this.bannerService.setCheckpoint(processed);
123
+ }
124
+ return saved;
125
+ }
126
+ /**
127
+ * Load a checkpoint from the database
128
+ *
129
+ * @param key Checkpoint key
130
+ * @returns Checkpoint if found, null otherwise
131
+ */
132
+ async loadCheckpoint(key) {
133
+ const result = await validatorQuery(`
134
+ SELECT
135
+ id::text,
136
+ checkpoint_key as key,
137
+ pipeline_type as "pipelineType",
138
+ state,
139
+ processed_items as "processedItems",
140
+ failed_items as "failedItems",
141
+ progress,
142
+ created_at as "createdAt",
143
+ updated_at as "updatedAt"
144
+ FROM validator.pipeline_checkpoints
145
+ WHERE checkpoint_key = $1
146
+ `, [key]);
147
+ const rows = Array.isArray(result) ? result : result.rows;
148
+ if (rows.length === 0) {
149
+ return null;
150
+ }
151
+ const row = rows[0];
152
+ return {
153
+ id: row.id,
154
+ key: row.key,
155
+ pipelineType: row.pipelineType,
156
+ state: row.state,
157
+ processedItems: row.processedItems || [],
158
+ failedItems: row.failedItems || [],
159
+ progress: row.progress || {},
160
+ createdAt: row.createdAt,
161
+ updatedAt: row.updatedAt,
162
+ };
163
+ }
164
+ /**
165
+ * Update checkpoint progress without changing state
166
+ *
167
+ * Useful for updating progress metrics during processing.
168
+ * Reports progress to banner service if provided.
169
+ *
170
+ * @param key Checkpoint key
171
+ * @param progress Progress metrics to update
172
+ */
173
+ async updateProgress(key, progress) {
174
+ await validatorQuery(`
175
+ UPDATE validator.pipeline_checkpoints
176
+ SET progress = COALESCE(progress, '{}'::jsonb) || $1::jsonb,
177
+ updated_at = NOW()
178
+ WHERE checkpoint_key = $2
179
+ `, [JSON.stringify(progress), key]);
180
+ // Report checkpoint progress to banner service if available
181
+ if (this.bannerService && progress.processed !== undefined) {
182
+ this.bannerService.setCheckpoint(progress.processed);
183
+ }
184
+ }
185
+ /**
186
+ * Add processed items to checkpoint
187
+ *
188
+ * @param key Checkpoint key
189
+ * @param itemIds Item IDs to add
190
+ */
191
+ async addProcessedItems(key, itemIds) {
192
+ await validatorQuery(`
193
+ UPDATE validator.pipeline_checkpoints
194
+ SET processed_items = array_cat(COALESCE(processed_items, '{}'), $1),
195
+ updated_at = NOW()
196
+ WHERE checkpoint_key = $2
197
+ `, [itemIds, key]);
198
+ }
199
+ /**
200
+ * Add failed items to checkpoint
201
+ *
202
+ * @param key Checkpoint key
203
+ * @param itemIds Item IDs to add
204
+ */
205
+ async addFailedItems(key, itemIds) {
206
+ await validatorQuery(`
207
+ UPDATE validator.pipeline_checkpoints
208
+ SET failed_items = array_cat(COALESCE(failed_items, '{}'), $1),
209
+ updated_at = NOW()
210
+ WHERE checkpoint_key = $2
211
+ `, [itemIds, key]);
212
+ }
213
+ /**
214
+ * Clear a checkpoint
215
+ *
216
+ * @param key Checkpoint key
217
+ */
218
+ async clearCheckpoint(key) {
219
+ await validatorQuery(`
220
+ DELETE FROM validator.pipeline_checkpoints
221
+ WHERE checkpoint_key = $1
222
+ `, [key]);
223
+ }
224
+ /**
225
+ * List all checkpoints
226
+ *
227
+ * @param pipelineType Optional filter by pipeline type
228
+ * @returns Array of checkpoints
229
+ */
230
+ async listCheckpoints(pipelineType) {
231
+ let query = `
232
+ SELECT
233
+ id::text,
234
+ checkpoint_key as key,
235
+ pipeline_type as "pipelineType",
236
+ state,
237
+ processed_items as "processedItems",
238
+ failed_items as "failedItems",
239
+ progress,
240
+ created_at as "createdAt",
241
+ updated_at as "updatedAt"
242
+ FROM validator.pipeline_checkpoints
243
+ `;
244
+ const params = [];
245
+ if (pipelineType) {
246
+ query += ` WHERE pipeline_type = $1`;
247
+ params.push(pipelineType);
248
+ }
249
+ query += ` ORDER BY updated_at DESC`;
250
+ const result = await validatorQuery(query, params);
251
+ const rows = Array.isArray(result) ? result : result.rows;
252
+ return rows.map((row) => ({
253
+ id: row.id,
254
+ key: row.key,
255
+ pipelineType: row.pipelineType,
256
+ state: row.state,
257
+ processedItems: row.processedItems || [],
258
+ failedItems: row.failedItems || [],
259
+ progress: row.progress || {},
260
+ createdAt: row.createdAt,
261
+ updatedAt: row.updatedAt,
262
+ }));
263
+ }
264
+ /**
265
+ * Check if a checkpoint exists
266
+ *
267
+ * @param key Checkpoint key
268
+ * @returns True if checkpoint exists
269
+ */
270
+ async checkpointExists(key) {
271
+ const result = await validatorQuery(`
272
+ SELECT EXISTS(
273
+ SELECT 1 FROM validator.pipeline_checkpoints
274
+ WHERE checkpoint_key = $1
275
+ ) as exists
276
+ `, [key]);
277
+ const row = Array.isArray(result) ? result[0] : result.rows[0];
278
+ return row.exists;
279
+ }
280
+ }
281
+ //# sourceMappingURL=CheckpointManager.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"CheckpointManager.js","sourceRoot":"","sources":["../../src/services/CheckpointManager.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,211 @@
1
+ /**
2
+ * Cost Calculator Service
3
+ *
4
+ * Unified cost calculation for embedding generation scripts.
5
+ * Replaces duplicate cost tracking code across multiple files.
6
+ *
7
+ * Features:
8
+ * - Accurate token estimation
9
+ * - Cost calculation for OpenAI API
10
+ * - Support for different models/pricing
11
+ * - Formatted cost output
12
+ *
13
+ * @example
14
+ * ```typescript
15
+ * const calculator = new CostCalculator();
16
+ *
17
+ * // Estimate tokens before API call
18
+ * const estimatedTokens = calculator.estimateTokens(text);
19
+ * logger.info('Estimated cost', { cost: calculator.estimateCost(estimatedTokens) });
20
+ *
21
+ * // Track actual usage after API call
22
+ * calculator.addTokens(response.usage.total_tokens);
23
+ *
24
+ * // Get totals
25
+ * logger.info('Cost summary', {
26
+ * total_tokens: calculator.getTotalTokens(),
27
+ * total_cost: calculator.getTotalCost(),
28
+ * formatted: calculator.getFormattedCost(),
29
+ * });
30
+ * ```
31
+ */
32
+ import { logger } from '@tsvika58/shared-utilities/logging';
33
+ /**
34
+ * OpenAI API Pricing (as of 2024)
35
+ */
36
+ export const OPENAI_PRICING = {
37
+ // Embedding models
38
+ 'text-embedding-3-small': 0.00002, // $0.02 per 1M tokens
39
+ 'text-embedding-3-large': 0.00013, // $0.13 per 1M tokens
40
+ 'text-embedding-ada-002': 0.00010, // $0.10 per 1M tokens
41
+ // GPT models (for reference)
42
+ 'gpt-4-turbo': 0.01, // $10 per 1M input tokens
43
+ 'gpt-4': 0.03, // $30 per 1M input tokens
44
+ 'gpt-3.5-turbo': 0.0005, // $0.50 per 1M input tokens
45
+ };
46
+ export class CostCalculator {
47
+ totalTokens = 0;
48
+ itemsProcessed = 0;
49
+ costPer1K;
50
+ model;
51
+ constructor(config = {}) {
52
+ this.model = config.model || 'text-embedding-3-small';
53
+ this.costPer1K = config.costPer1K || OPENAI_PRICING[this.model] || 0.00002;
54
+ }
55
+ /**
56
+ * Add tokens to the total count
57
+ *
58
+ * @param tokenCount Number of tokens used
59
+ */
60
+ addTokens(tokenCount) {
61
+ this.totalTokens += tokenCount;
62
+ this.itemsProcessed++;
63
+ }
64
+ /**
65
+ * Estimate tokens for a text string
66
+ *
67
+ * Uses a simple heuristic: ~4 characters per token for English text
68
+ * This is a rough estimate - actual tokenization may vary
69
+ *
70
+ * @param text Text to estimate
71
+ * @returns Estimated token count
72
+ */
73
+ estimateTokens(text) {
74
+ // Average: ~4 characters per token for English
75
+ // Add 10% buffer for safety
76
+ const estimate = Math.ceil((text.length / 4) * 1.1);
77
+ return Math.max(estimate, 1); // Minimum 1 token
78
+ }
79
+ /**
80
+ * Estimate cost for a given token count
81
+ *
82
+ * @param tokenCount Number of tokens
83
+ * @returns Estimated cost in dollars
84
+ */
85
+ estimateCost(tokenCount) {
86
+ return (tokenCount / 1000) * this.costPer1K;
87
+ }
88
+ /**
89
+ * Estimate cost for a text string
90
+ *
91
+ * @param text Text to estimate
92
+ * @returns Estimated cost in dollars
93
+ */
94
+ estimateTextCost(text) {
95
+ const tokens = this.estimateTokens(text);
96
+ return this.estimateCost(tokens);
97
+ }
98
+ /**
99
+ * Get total tokens used
100
+ *
101
+ * @returns Total token count
102
+ */
103
+ getTotalTokens() {
104
+ return this.totalTokens;
105
+ }
106
+ /**
107
+ * Get total cost
108
+ *
109
+ * @returns Total cost in dollars
110
+ */
111
+ getTotalCost() {
112
+ return (this.totalTokens / 1000) * this.costPer1K;
113
+ }
114
+ /**
115
+ * Get formatted cost string
116
+ *
117
+ * @param decimals Number of decimal places (default: 4)
118
+ * @returns Formatted cost (e.g., "$0.0025")
119
+ */
120
+ getFormattedCost(decimals = 4) {
121
+ return `$${this.getTotalCost().toFixed(decimals)}`;
122
+ }
123
+ /**
124
+ * Get formatted token count with thousands separators
125
+ *
126
+ * @returns Formatted token count (e.g., "125,000")
127
+ */
128
+ getFormattedTokens() {
129
+ return this.totalTokens.toLocaleString();
130
+ }
131
+ /**
132
+ * Get average tokens per item
133
+ *
134
+ * @returns Average tokens
135
+ */
136
+ getAvgTokensPerItem() {
137
+ if (this.itemsProcessed === 0)
138
+ return 0;
139
+ return this.totalTokens / this.itemsProcessed;
140
+ }
141
+ /**
142
+ * Get average cost per item
143
+ *
144
+ * @returns Average cost in dollars
145
+ */
146
+ getAvgCostPerItem() {
147
+ if (this.itemsProcessed === 0)
148
+ return 0;
149
+ return this.getTotalCost() / this.itemsProcessed;
150
+ }
151
+ /**
152
+ * Get number of items processed
153
+ *
154
+ * @returns Item count
155
+ */
156
+ getItemsProcessed() {
157
+ return this.itemsProcessed;
158
+ }
159
+ /**
160
+ * Get complete cost summary
161
+ *
162
+ * @returns Cost summary object
163
+ */
164
+ getSummary() {
165
+ return {
166
+ totalTokens: this.totalTokens,
167
+ totalCost: this.getTotalCost(),
168
+ avgTokensPerItem: this.getAvgTokensPerItem(),
169
+ avgCostPerItem: this.getAvgCostPerItem(),
170
+ itemsProcessed: this.itemsProcessed,
171
+ };
172
+ }
173
+ /**
174
+ * Reset all counters
175
+ */
176
+ reset() {
177
+ this.totalTokens = 0;
178
+ this.itemsProcessed = 0;
179
+ }
180
+ /**
181
+ * Get model name
182
+ *
183
+ * @returns Model name
184
+ */
185
+ getModel() {
186
+ return this.model;
187
+ }
188
+ /**
189
+ * Get cost per 1K tokens
190
+ *
191
+ * @returns Cost rate
192
+ */
193
+ getCostPer1K() {
194
+ return this.costPer1K;
195
+ }
196
+ /**
197
+ * Print cost summary to console
198
+ */
199
+ printSummary() {
200
+ const summary = this.getSummary();
201
+ logger.info('Cost Summary', {
202
+ model: this.model,
203
+ total_tokens: this.getFormattedTokens(),
204
+ total_cost: this.getFormattedCost(),
205
+ items_processed: summary.itemsProcessed > 0 ? summary.itemsProcessed.toLocaleString() : undefined,
206
+ avg_tokens_per_item: summary.itemsProcessed > 0 ? Math.round(summary.avgTokensPerItem).toLocaleString() : undefined,
207
+ avg_cost_per_item: summary.itemsProcessed > 0 ? `$${summary.avgCostPerItem.toFixed(6)}` : undefined,
208
+ });
209
+ }
210
+ }
211
+ //# sourceMappingURL=CostCalculator.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"CostCalculator.js","sourceRoot":"","sources":["../../src/services/CostCalculator.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,68 @@
1
+ /**
2
+ * Embedding Cache Service
3
+ *
4
+ * Caches query embeddings to avoid regenerating them for repeated queries.
5
+ * Reduces API calls and improves latency for common queries.
6
+ */
7
+ import NodeCache from 'node-cache';
8
+ export class EmbeddingCache {
9
+ cache;
10
+ constructor() {
11
+ const ttl = process.env.EMBEDDING_CACHE_TTL
12
+ ? Number(process.env.EMBEDDING_CACHE_TTL)
13
+ : 604800; // Default: 7 days (query embeddings are deterministic, database is static)
14
+ const maxKeys = process.env.EMBEDDING_CACHE_MAX_SIZE
15
+ ? Number(process.env.EMBEDDING_CACHE_MAX_SIZE)
16
+ : 1000; // Default: 1000 queries
17
+ this.cache = new NodeCache({
18
+ stdTTL: ttl,
19
+ checkperiod: 600, // Check for expired keys every 10 minutes
20
+ useClones: false, // Don't clone arrays (faster, but be careful with mutations)
21
+ maxKeys: maxKeys,
22
+ });
23
+ }
24
+ /**
25
+ * Get cached embedding for a query
26
+ */
27
+ get(query) {
28
+ const key = this.getKey(query);
29
+ return this.cache.get(key);
30
+ }
31
+ /**
32
+ * Cache an embedding for a query
33
+ */
34
+ set(query, embedding) {
35
+ const key = this.getKey(query);
36
+ this.cache.set(key, embedding);
37
+ }
38
+ /**
39
+ * Check if a query is cached
40
+ */
41
+ has(query) {
42
+ const key = this.getKey(query);
43
+ return this.cache.has(key);
44
+ }
45
+ /**
46
+ * Get cache statistics
47
+ */
48
+ stats() {
49
+ return this.cache.getStats();
50
+ }
51
+ /**
52
+ * Clear all cached embeddings
53
+ */
54
+ flush() {
55
+ this.cache.flushAll();
56
+ }
57
+ /**
58
+ * Generate cache key from query
59
+ */
60
+ getKey(query) {
61
+ // Normalize query: lowercase, trim, remove extra whitespace
62
+ const normalized = query.toLowerCase().trim().replace(/\s+/g, ' ');
63
+ return `embedding:${normalized}`;
64
+ }
65
+ }
66
+ // Singleton instance
67
+ export const embeddingCache = new EmbeddingCache();
68
+ //# sourceMappingURL=EmbeddingCache.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"EmbeddingCache.js","sourceRoot":"","sources":["../../src/services/EmbeddingCache.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,SAAS,MAAM,YAAY,CAAC;AAEnC,MAAM,OAAO,cAAc;IACjB,KAAK,CAAY;IAEzB;QACE,MAAM,GAAG,GAAG,OAAO,CAAC,GAAG,CAAC,mBAAmB;YACzC,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,mBAAmB,CAAC;YACzC,CAAC,CAAC,MAAM,CAAC,CAAC,2EAA2E;QAEvF,MAAM,OAAO,GAAG,OAAO,CAAC,GAAG,CAAC,wBAAwB;YAClD,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,wBAAwB,CAAC;YAC9C,CAAC,CAAC,IAAI,CAAC,CAAC,wBAAwB;QAElC,IAAI,CAAC,KAAK,GAAG,IAAI,SAAS,CAAC;YACzB,MAAM,EAAE,GAAG;YACX,WAAW,EAAE,GAAG,EAAE,0CAA0C;YAC5D,SAAS,EAAE,KAAK,EAAE,6DAA6D;YAC/E,OAAO,EAAE,OAAO;SACjB,CAAC,CAAC;IACL,CAAC;IAED;;OAEG;IACH,GAAG,CAAC,KAAa;QACf,MAAM,GAAG,GAAG,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;QAC/B,OAAO,IAAI,CAAC,KAAK,CAAC,GAAG,CAAW,GAAG,CAAC,CAAC;IACvC,CAAC;IAED;;OAEG;IACH,GAAG,CAAC,KAAa,EAAE,SAAmB;QACpC,MAAM,GAAG,GAAG,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;QAC/B,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,GAAG,EAAE,SAAS,CAAC,CAAC;IACjC,CAAC;IAED;;OAEG;IACH,GAAG,CAAC,KAAa;QACf,MAAM,GAAG,GAAG,IAAI,CAAC,MAAM,CAAC,KAAK,CAAC,CAAC;QAC/B,OAAO,IAAI,CAAC,KAAK,CAAC,GAAG,CAAC,GAAG,CAAC,CAAC;IAC7B,CAAC;IAED;;OAEG;IACH,KAAK;QACH,OAAO,IAAI,CAAC,KAAK,CAAC,QAAQ,EAAE,CAAC;IAC/B,CAAC;IAED;;OAEG;IACH,KAAK;QACH,IAAI,CAAC,KAAK,CAAC,QAAQ,EAAE,CAAC;IACxB,CAAC;IAED;;OAEG;IACK,MAAM,CAAC,KAAa;QAC1B,4DAA4D;QAC5D,MAAM,UAAU,GAAG,KAAK,CAAC,WAAW,EAAE,CAAC,IAAI,EAAE,CAAC,OAAO,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;QACnE,OAAO,aAAa,UAAU,EAAE,CAAC;IACnC,CAAC;CACF;AAED,qBAAqB;AACrB,MAAM,CAAC,MAAM,cAAc,GAAG,IAAI,cAAc,EAAE,CAAC"}