@juspay/neurolink 10.6.0 → 10.6.2

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 (151) hide show
  1. package/CHANGELOG.md +8 -0
  2. package/dist/adapters/video/vertexVideoHandler.js +4 -1
  3. package/dist/agent/directTools.d.ts +2 -2
  4. package/dist/agent/orchestration/orchestrator.js +2 -0
  5. package/dist/auth/errors.d.ts +1 -1
  6. package/dist/auth/middleware/AuthMiddleware.d.ts +1 -1
  7. package/dist/auth/providers/BaseAuthProvider.d.ts +1 -1
  8. package/dist/auth/providers/auth0.js +1 -1
  9. package/dist/auth/providers/betterAuth.js +1 -1
  10. package/dist/auth/providers/clerk.js +1 -1
  11. package/dist/auth/providers/firebase.js +1 -1
  12. package/dist/auth/providers/jwt.js +1 -1
  13. package/dist/auth/providers/oauth2.js +1 -1
  14. package/dist/auth/providers/supabase.js +1 -1
  15. package/dist/auth/providers/workos.js +1 -1
  16. package/dist/browser/neurolink.min.js +338 -338
  17. package/dist/cli/commands/proxy.js +2 -0
  18. package/dist/cli/commands/rag.js +2 -4
  19. package/dist/cli/factories/commandFactory.js +3 -2
  20. package/dist/cli/loop/conversationSelector.js +4 -6
  21. package/dist/client/auth.js +2 -7
  22. package/dist/client/reactHooks.js +2 -2
  23. package/dist/client/reactHooks.tsx +5 -10
  24. package/dist/core/baseProvider.d.ts +1 -1
  25. package/dist/core/baseProvider.js +16 -6
  26. package/dist/core/factory.d.ts +4 -3
  27. package/dist/core/modules/GenerationHandler.d.ts +1 -1
  28. package/dist/core/modules/GenerationHandler.js +7 -5
  29. package/dist/core/modules/TelemetryHandler.js +2 -2
  30. package/dist/core/toolExecutionRecorder.d.ts +1 -1
  31. package/dist/core/toolExecutionRecorder.js +1 -2
  32. package/dist/evaluation/errors/EvaluationError.d.ts +1 -1
  33. package/dist/evaluation/scorers/rule/contentSimilarityScorer.js +2 -0
  34. package/dist/evaluation/scorers/rule/formatScorer.js +1 -1
  35. package/dist/factories/providerFactory.d.ts +4 -3
  36. package/dist/factories/providerRegistry.d.ts +9 -4
  37. package/dist/factories/providerRegistry.js +9 -4
  38. package/dist/features/ppt/slideGenerator.js +6 -5
  39. package/dist/features/ppt/utils.d.ts +2 -1
  40. package/dist/features/ppt/utils.js +1 -0
  41. package/dist/lib/adapters/video/vertexVideoHandler.js +4 -1
  42. package/dist/lib/agent/orchestration/orchestrator.js +2 -0
  43. package/dist/lib/auth/providers/auth0.js +1 -1
  44. package/dist/lib/auth/providers/betterAuth.js +1 -1
  45. package/dist/lib/auth/providers/clerk.js +1 -1
  46. package/dist/lib/auth/providers/firebase.js +1 -1
  47. package/dist/lib/auth/providers/jwt.js +1 -1
  48. package/dist/lib/auth/providers/oauth2.js +1 -1
  49. package/dist/lib/auth/providers/supabase.js +1 -1
  50. package/dist/lib/auth/providers/workos.js +1 -1
  51. package/dist/lib/client/auth.js +2 -7
  52. package/dist/lib/client/reactHooks.js +2 -2
  53. package/dist/lib/core/baseProvider.d.ts +1 -1
  54. package/dist/lib/core/baseProvider.js +16 -6
  55. package/dist/lib/core/factory.d.ts +4 -3
  56. package/dist/lib/core/modules/GenerationHandler.d.ts +1 -1
  57. package/dist/lib/core/modules/GenerationHandler.js +7 -5
  58. package/dist/lib/core/modules/TelemetryHandler.js +2 -2
  59. package/dist/lib/core/toolExecutionRecorder.d.ts +1 -1
  60. package/dist/lib/core/toolExecutionRecorder.js +1 -2
  61. package/dist/lib/evaluation/scorers/rule/contentSimilarityScorer.js +2 -0
  62. package/dist/lib/evaluation/scorers/rule/formatScorer.js +1 -1
  63. package/dist/lib/factories/providerFactory.d.ts +4 -3
  64. package/dist/lib/factories/providerRegistry.d.ts +9 -4
  65. package/dist/lib/factories/providerRegistry.js +9 -4
  66. package/dist/lib/features/ppt/slideGenerator.js +6 -5
  67. package/dist/lib/features/ppt/utils.d.ts +2 -1
  68. package/dist/lib/features/ppt/utils.js +1 -0
  69. package/dist/lib/mcp/elicitationProtocol.js +1 -1
  70. package/dist/lib/mcp/mcpRegistryClient.js +1 -1
  71. package/dist/lib/middleware/utils/guardrailsUtils.js +1 -1
  72. package/dist/lib/neurolink.js +15 -7
  73. package/dist/lib/processors/document/ExcelProcessor.js +5 -1
  74. package/dist/lib/processors/media/index.js +0 -10
  75. package/dist/lib/providers/amazonBedrock.js +4 -5
  76. package/dist/lib/providers/amazonSagemaker.d.ts +18 -0
  77. package/dist/lib/providers/amazonSagemaker.js +9 -3
  78. package/dist/lib/providers/anthropic.js +6 -1
  79. package/dist/lib/providers/googleAiStudio.js +5 -12
  80. package/dist/lib/providers/googleVertex.js +26 -5
  81. package/dist/lib/providers/openaiChatCompletionsBase.js +2 -0
  82. package/dist/lib/providers/sagemaker/errors.js +2 -1
  83. package/dist/lib/proxy/proxyFetch.js +6 -2
  84. package/dist/lib/rag/ChunkerFactory.js +1 -1
  85. package/dist/lib/rag/chunking/semanticChunker.js +1 -2
  86. package/dist/lib/rag/document/MDocument.js +1 -2
  87. package/dist/lib/rag/document/loaders.js +16 -3
  88. package/dist/lib/rag/pipeline/RAGPipeline.js +1 -2
  89. package/dist/lib/rag/retrieval/hybridSearch.js +1 -2
  90. package/dist/lib/rag/retrieval/vectorQueryTool.js +1 -2
  91. package/dist/lib/sdk/toolRegistration.js +6 -2
  92. package/dist/lib/server/middleware/cache.d.ts +4 -0
  93. package/dist/lib/server/middleware/cache.js +7 -3
  94. package/dist/lib/server/middleware/validation.js +2 -1
  95. package/dist/lib/server/utils/redaction.js +31 -39
  96. package/dist/lib/server/websocket/WebSocketHandler.js +3 -3
  97. package/dist/lib/services/server/ai/observability/instrumentation.js +8 -5
  98. package/dist/lib/types/classifierRouter.d.ts +2 -1
  99. package/dist/lib/types/providers.d.ts +22 -2
  100. package/dist/lib/utils/pdfProcessor.js +2 -0
  101. package/dist/lib/utils/safeFetch.js +20 -0
  102. package/dist/lib/utils/schemaConversion.d.ts +1 -1
  103. package/dist/lib/utils/schemaConversion.js +5 -1
  104. package/dist/lib/workflow/config.d.ts +1 -1
  105. package/dist/lib/workflow/config.js +1 -1
  106. package/dist/lib/workflow/core/workflowRegistry.js +1 -1
  107. package/dist/lib/workflow/core/workflowRunner.js +1 -1
  108. package/dist/lib/workflow/utils/workflowMetrics.d.ts +1 -1
  109. package/dist/lib/workflow/utils/workflowMetrics.js +1 -1
  110. package/dist/mcp/elicitationProtocol.js +1 -1
  111. package/dist/mcp/mcpRegistryClient.js +1 -1
  112. package/dist/middleware/utils/guardrailsUtils.js +1 -1
  113. package/dist/neurolink.js +15 -7
  114. package/dist/processors/document/ExcelProcessor.js +5 -1
  115. package/dist/processors/media/index.js +0 -10
  116. package/dist/providers/amazonBedrock.js +4 -5
  117. package/dist/providers/amazonSagemaker.d.ts +18 -0
  118. package/dist/providers/amazonSagemaker.js +9 -3
  119. package/dist/providers/anthropic.js +6 -1
  120. package/dist/providers/googleAiStudio.js +5 -12
  121. package/dist/providers/googleVertex.js +26 -5
  122. package/dist/providers/openaiChatCompletionsBase.js +2 -0
  123. package/dist/providers/sagemaker/errors.js +2 -1
  124. package/dist/proxy/proxyFetch.js +6 -2
  125. package/dist/rag/ChunkerFactory.js +1 -1
  126. package/dist/rag/chunking/semanticChunker.js +1 -2
  127. package/dist/rag/document/MDocument.js +1 -2
  128. package/dist/rag/document/loaders.js +16 -3
  129. package/dist/rag/pipeline/RAGPipeline.js +1 -2
  130. package/dist/rag/retrieval/hybridSearch.js +1 -2
  131. package/dist/rag/retrieval/vectorQueryTool.js +1 -2
  132. package/dist/sdk/toolRegistration.js +6 -2
  133. package/dist/server/middleware/cache.d.ts +4 -0
  134. package/dist/server/middleware/cache.js +7 -3
  135. package/dist/server/middleware/validation.js +2 -1
  136. package/dist/server/utils/redaction.js +31 -39
  137. package/dist/server/websocket/WebSocketHandler.js +3 -3
  138. package/dist/services/server/ai/observability/instrumentation.js +8 -5
  139. package/dist/types/classifierRouter.d.ts +2 -1
  140. package/dist/types/providers.d.ts +22 -2
  141. package/dist/utils/pdfProcessor.js +2 -0
  142. package/dist/utils/safeFetch.js +20 -0
  143. package/dist/utils/schemaConversion.d.ts +1 -1
  144. package/dist/utils/schemaConversion.js +5 -1
  145. package/dist/workflow/config.d.ts +2 -2
  146. package/dist/workflow/config.js +1 -1
  147. package/dist/workflow/core/workflowRegistry.js +1 -1
  148. package/dist/workflow/core/workflowRunner.js +1 -1
  149. package/dist/workflow/utils/workflowMetrics.d.ts +1 -1
  150. package/dist/workflow/utils/workflowMetrics.js +1 -1
  151. package/package.json +1 -1
@@ -1439,6 +1439,8 @@ export async function createProxyStartApp(params) {
1439
1439
  params: c.req.param(),
1440
1440
  body,
1441
1441
  rawBody,
1442
+ // The proxy runtime exposes only the structural slice of NeuroLink the
1443
+ // routes use; narrow (overlap-checked) to the full class for ServerContext.
1442
1444
  neurolink: params.neurolink,
1443
1445
  toolRegistry: params.neurolink.getToolRegistry(),
1444
1446
  timestamp: Date.now(),
@@ -500,8 +500,7 @@ function createIndexCommand() {
500
500
  }
501
501
  const embeddingProvider = await ProviderFactory.createProvider(embeddingProviderName, embeddingModelName);
502
502
  // Verify the provider has an embed method
503
- if (typeof embeddingProvider.embed !==
504
- "function") {
503
+ if (typeof embeddingProvider.embed !== "function") {
505
504
  spinner.fail(chalk.red(`Provider ${embeddingProviderName} with model ${embeddingModelName} does not support embeddings. ` +
506
505
  `Please use an embedding model like text-embedding-004 (Vertex) or text-embedding-3-small (OpenAI).`));
507
506
  process.exit(1);
@@ -643,8 +642,7 @@ function createQueryCommand() {
643
642
  }
644
643
  const embeddingProvider = await ProviderFactory.createProvider(embeddingProviderName, embeddingModelName);
645
644
  // Verify the provider has an embed method
646
- if (typeof embeddingProvider.embed !==
647
- "function") {
645
+ if (typeof embeddingProvider.embed !== "function") {
648
646
  spinner.fail(chalk.red(`Provider ${embeddingProviderName} with model ${embeddingModelName} does not support embeddings. ` +
649
647
  `Please use an embedding model like text-embedding-004 (Vertex) or text-embedding-3-small (OpenAI).`));
650
648
  process.exit(1);
@@ -1483,9 +1483,10 @@ export class CLICommandFactory {
1483
1483
  analyticsText += ` Cost: $${analytics.cost.toFixed(5)}\n`;
1484
1484
  }
1485
1485
  // Response time with fallback handling for requestDuration vs responseTime
1486
+ const analyticsRecord = analytics;
1486
1487
  const duration = analytics.requestDuration ||
1487
- analytics.responseTime ||
1488
- analytics.duration;
1488
+ analyticsRecord.responseTime ||
1489
+ analyticsRecord.duration;
1489
1490
  if (duration && typeof duration === "number") {
1490
1491
  const timeInSeconds = (duration / 1000).toFixed(1);
1491
1492
  analyticsText += ` Time: ${timeInSeconds}s\n`;
@@ -20,10 +20,7 @@ export class ConversationSelector {
20
20
  */
21
21
  async initializeRedis() {
22
22
  if (!this.redisClient) {
23
- // Cast is necessary: createRedisClient returns the ioredis client type which
24
- // does not structurally match our CliRedisClient interface due to overloaded
25
- // method signatures. The runtime value is fully compatible.
26
- this.redisClient = (await createRedisClient(this.redisConfig));
23
+ this.redisClient = await createRedisClient(this.redisConfig);
27
24
  }
28
25
  }
29
26
  /**
@@ -161,8 +158,9 @@ export class ConversationSelector {
161
158
  value: "NEW_CONVERSATION",
162
159
  short: "New Conversation",
163
160
  },
164
- // Cast is intentional: inquirer's Separator type is not exported cleanly
165
- // and does not overlap with MenuChoice, but inquirer accepts it at runtime.
161
+ // Cast is intentional: inquirer's Separator (type: string) narrows to the
162
+ // MenuChoice separator variant (type: "separator"); inquirer accepts it
163
+ // at runtime.
166
164
  new inquirer.Separator(),
167
165
  ];
168
166
  for (const conversation of conversations.slice(0, LOOP_DISPLAY_LIMITS.MAX_CONVERSATIONS)) {
@@ -121,13 +121,8 @@ export class OAuth2TokenManager {
121
121
  throw new OAuth2Error(`OAuth2 token request failed: ${response.status}`, response.status, errorText);
122
122
  }
123
123
  const data = (await response.json());
124
- this.token =
125
- data.accessToken ||
126
- data.access_token ||
127
- "";
128
- const expiresIn = data.expiresIn ||
129
- data.expires_in ||
130
- 3600;
124
+ this.token = data.accessToken || data.access_token || "";
125
+ const expiresIn = data.expiresIn ?? data.expires_in ?? 3600;
131
126
  this.tokenExpiry = Date.now() + expiresIn * 1000;
132
127
  if (!this.token) {
133
128
  throw new OAuth2Error("OAuth2 response missing access token", 200, JSON.stringify(data));
@@ -758,8 +758,8 @@ export function useVoice(options = {}) {
758
758
  if (typeof window === "undefined") {
759
759
  return null;
760
760
  }
761
- const SpeechRecognitionCtor = window.SpeechRecognition ||
762
- window.webkitSpeechRecognition;
761
+ const speechWindow = window;
762
+ const SpeechRecognitionCtor = speechWindow.SpeechRecognition || speechWindow.webkitSpeechRecognition;
763
763
  if (!SpeechRecognitionCtor) {
764
764
  return null;
765
765
  }
@@ -997,17 +997,12 @@ export function useVoice(options: UseVoiceOptions = {}): UseVoiceReturn {
997
997
  return null;
998
998
  }
999
999
 
1000
+ const speechWindow = window as typeof window & {
1001
+ SpeechRecognition?: { new (): SpeechRecognitionInternal };
1002
+ webkitSpeechRecognition?: { new (): SpeechRecognitionInternal };
1003
+ };
1000
1004
  const SpeechRecognitionCtor =
1001
- (
1002
- window as unknown as {
1003
- SpeechRecognition?: { new (): SpeechRecognitionInternal };
1004
- }
1005
- ).SpeechRecognition ||
1006
- (
1007
- window as unknown as {
1008
- webkitSpeechRecognition?: { new (): SpeechRecognitionInternal };
1009
- }
1010
- ).webkitSpeechRecognition;
1005
+ speechWindow.SpeechRecognition || speechWindow.webkitSpeechRecognition;
1011
1006
 
1012
1007
  if (!SpeechRecognitionCtor) {
1013
1008
  return null;
@@ -294,7 +294,7 @@ export declare abstract class BaseProvider implements AIProvider {
294
294
  /**
295
295
  * Get AI SDK model with middleware applied
296
296
  * This method wraps the base model with any configured middleware
297
- * TODO: Implement global level middlewares that can be used
297
+ * TODO(#1179): Implement global level middlewares that can be used
298
298
  */
299
299
  protected getAISDKModelWithMiddleware(options?: TextGenerationOptions | StreamOptions): Promise<LanguageModel>;
300
300
  /**
@@ -27,6 +27,18 @@ import { TelemetryHandler } from "./modules/TelemetryHandler.js";
27
27
  import { ToolsManager } from "./modules/ToolsManager.js";
28
28
  import { Utilities } from "./modules/Utilities.js";
29
29
  import { generateText } from "../utils/generation.js";
30
+ /**
31
+ * Read the consumer-facing lifecycle callbacks buried inside a request's
32
+ * middleware blob. The parameter is `unknown` on purpose: request options
33
+ * arrive as several structurally-unrelated shapes (StreamOptions,
34
+ * TextGenerationOptions), and the lifecycle branch is an optional add-on
35
+ * none of them declare — a single structural view keeps the read cast-free
36
+ * at every call site.
37
+ */
38
+ function getLifecycleMiddlewareConfig(options) {
39
+ return options?.middleware
40
+ ?.middlewareConfig?.lifecycle?.config;
41
+ }
30
42
  /**
31
43
  * Abstract base class for all AI providers
32
44
  * Tools are integrated as first-class citizens - always available by default
@@ -39,7 +51,7 @@ export class BaseProvider {
39
51
  modelName;
40
52
  providerName;
41
53
  defaultTimeout = 30000; // 30 seconds
42
- middlewareOptions; // TODO: Implement global level middlewares that can be used
54
+ middlewareOptions; // TODO(#1179): Implement global level middlewares that can be used
43
55
  // Tools are conditionally included based on centralized configuration
44
56
  directTools = shouldDisableBuiltinTools()
45
57
  ? {}
@@ -279,8 +291,7 @@ export class BaseProvider {
279
291
  * underlying transport.
280
292
  */
281
293
  wrapStreamWithLifecycleCallbacks(result, options) {
282
- const lifecycle = options
283
- ?.middleware?.middlewareConfig?.lifecycle?.config;
294
+ const lifecycle = getLifecycleMiddlewareConfig(options);
284
295
  if (!lifecycle?.onChunk && !lifecycle?.onFinish && !lifecycle?.onError) {
285
296
  return result;
286
297
  }
@@ -376,8 +387,7 @@ export class BaseProvider {
376
387
  if (hasLifecycleErrorFired(err)) {
377
388
  return;
378
389
  }
379
- const lifecycle = options
380
- ?.middleware?.middlewareConfig?.lifecycle?.config;
390
+ const lifecycle = getLifecycleMiddlewareConfig(options);
381
391
  const onError = lifecycle?.onError;
382
392
  if (!onError) {
383
393
  return;
@@ -1295,7 +1305,7 @@ export class BaseProvider {
1295
1305
  /**
1296
1306
  * Get AI SDK model with middleware applied
1297
1307
  * This method wraps the base model with any configured middleware
1298
- * TODO: Implement global level middlewares that can be used
1308
+ * TODO(#1179): Implement global level middlewares that can be used
1299
1309
  */
1300
1310
  async getAISDKModelWithMiddleware(options = {}) {
1301
1311
  // Get the base model
@@ -1,4 +1,5 @@
1
- import type { AIProvider, SupportedModelName, NeurolinkCredentials, UnknownRecord, ProviderPairResult } from "../types/index.js";
1
+ import type { NeuroLink } from "../neurolink.js";
2
+ import type { AIProvider, SupportedModelName, NeurolinkCredentials, ProviderPairResult } from "../types/index.js";
2
3
  import { AIProviderName } from "../constants/enums.js";
3
4
  /**
4
5
  * Factory for creating AI provider instances with centralized configuration
@@ -25,7 +26,7 @@ export declare class AIProviderFactory {
25
26
  * @param region - Optional region override for cloud providers
26
27
  * @returns AIProvider instance
27
28
  */
28
- static createProvider(providerName: string, modelName?: string | null, enableMCP?: boolean, sdk?: UnknownRecord, region?: string, credentials?: NeurolinkCredentials): Promise<AIProvider>;
29
+ static createProvider(providerName: string, modelName?: string | null, enableMCP?: boolean, sdk?: NeuroLink, region?: string, credentials?: NeurolinkCredentials): Promise<AIProvider>;
29
30
  /**
30
31
  * Create a provider instance with specific provider enum and model
31
32
  * @param provider - Provider enum value
@@ -40,7 +41,7 @@ export declare class AIProviderFactory {
40
41
  * @param enableMCP - Optional flag to enable MCP integration (default: true)
41
42
  * @returns AIProvider instance
42
43
  */
43
- static createBestProvider(requestedProvider?: string, modelName?: string | null, enableMCP?: boolean, sdk?: UnknownRecord): Promise<AIProvider>;
44
+ static createBestProvider(requestedProvider?: string, modelName?: string | null, enableMCP?: boolean, sdk?: NeuroLink): Promise<AIProvider>;
44
45
  /**
45
46
  * Create primary and fallback provider instances
46
47
  * @param primaryProvider - Primary provider name
@@ -91,5 +91,5 @@ export declare class GenerationHandler {
91
91
  /**
92
92
  * Analyze AI response structure and log detailed debugging information
93
93
  */
94
- analyzeAIResponse(result: Record<string, unknown>): void;
94
+ analyzeAIResponse(rawResult: unknown): void;
95
95
  }
@@ -693,11 +693,9 @@ export class GenerationHandler {
693
693
  }));
694
694
  }
695
695
  // Extract from steps
696
- if (generateResult.steps &&
697
- Array.isArray(generateResult.steps)) {
696
+ if (generateResult.steps && Array.isArray(generateResult.steps)) {
698
697
  const toolCallArgsMap = new Map();
699
- for (const step of generateResult
700
- .steps || []) {
698
+ for (const step of generateResult.steps || []) {
701
699
  // Collect tool calls and their arguments
702
700
  if (step?.toolCalls && Array.isArray(step.toolCalls)) {
703
701
  for (const toolCall of step.toolCalls) {
@@ -947,7 +945,11 @@ export class GenerationHandler {
947
945
  /**
948
946
  * Analyze AI response structure and log detailed debugging information
949
947
  */
950
- analyzeAIResponse(result) {
948
+ analyzeAIResponse(rawResult) {
949
+ if (rawResult === null || typeof rawResult !== "object") {
950
+ return;
951
+ }
952
+ const result = rawResult;
951
953
  logger.debug("NeuroLink Raw AI Response Analysis", {
952
954
  provider: this.providerName,
953
955
  model: this.modelName,
@@ -189,10 +189,10 @@ export class TelemetryHandler {
189
189
  return;
190
190
  }
191
191
  const sessionId = options.context?.sessionId ||
192
- options.sessionId ||
192
+ ("sessionId" in options ? options.sessionId : undefined) ||
193
193
  `session-${nanoid()}`;
194
194
  const userId = options.context?.userId ||
195
- options.userId;
195
+ ("userId" in options ? options.userId : undefined);
196
196
  try {
197
197
  await this.neurolink.storeToolExecutions(sessionId, userId, toolCalls, toolResults, currentTime);
198
198
  }
@@ -56,7 +56,7 @@ export declare class ToolExecutionRecorder {
56
56
  * enumerable on purpose: downstream stages spread options (`{...options}`)
57
57
  * and the recorder must survive into the provider loops.
58
58
  */
59
- attachTo(options: Record<string, unknown>): void;
59
+ attachTo(options: object): void;
60
60
  /** Retrieve the recorder a request is carrying, if any. */
61
61
  static from(options: unknown): ToolExecutionRecorder | undefined;
62
62
  }
@@ -147,8 +147,7 @@ export class ToolExecutionRecorder {
147
147
  const wrapped = Object.create(null);
148
148
  for (const [name, tool] of Object.entries(tools)) {
149
149
  const execute = tool.execute;
150
- if (typeof execute !== "function" ||
151
- execute[RECORDER_WRAPPED]) {
150
+ if (typeof execute !== "function" || execute[RECORDER_WRAPPED]) {
152
151
  wrapped[name] = tool;
153
152
  continue;
154
153
  }
@@ -65,7 +65,7 @@ export declare const evaluationErrors: {
65
65
  /** Rate limit hit during evaluation */
66
66
  readonly RATE_LIMIT_ERROR: "RATE_LIMIT_ERROR";
67
67
  };
68
- create: (code: "EVALUATION_FAILED" | "PARSE_ERROR" | "STRATEGY_NOT_FOUND" | "PROVIDER_ERROR" | "CONFIGURATION_ERROR" | "CUSTOM_EVALUATOR_ERROR" | "BATCH_EVALUATION_ERROR" | "AGGREGATION_ERROR" | "REGISTRY_ERROR" | "MAX_RETRIES_EXCEEDED" | "TIMEOUT_ERROR" | "RATE_LIMIT_ERROR", message: string, options?: {
68
+ create: (code: "PROVIDER_ERROR" | "CONFIGURATION_ERROR" | "EVALUATION_FAILED" | "PARSE_ERROR" | "STRATEGY_NOT_FOUND" | "CUSTOM_EVALUATOR_ERROR" | "BATCH_EVALUATION_ERROR" | "AGGREGATION_ERROR" | "REGISTRY_ERROR" | "MAX_RETRIES_EXCEEDED" | "TIMEOUT_ERROR" | "RATE_LIMIT_ERROR", message: string, options?: {
69
69
  retryable?: boolean;
70
70
  details?: Record<string, unknown>;
71
71
  cause?: Error;
@@ -270,6 +270,8 @@ export class ContentSimilarityScorer extends BaseScorer {
270
270
  const metrics = this._similarityConfig.metrics ?? [
271
271
  this._similarityConfig.metric ?? "jaccard",
272
272
  ];
273
+ // Intersected with JsonObject so the rows are JSON-typed at the source
274
+ // and flow into result metadata without a cast.
273
275
  const details = [];
274
276
  for (const metric of metrics) {
275
277
  const score = this._calculateSimilarity(input.response, reference, metric);
@@ -396,7 +396,7 @@ export class FormatScorer extends BaseRuleScorer {
396
396
  // First check if it's valid JSON
397
397
  try {
398
398
  JSON.parse(text);
399
- // TODO: Implement full JSON Schema validation
399
+ // TODO(#1179): Implement full JSON Schema validation
400
400
  // For now, just check it's valid JSON
401
401
  return { passed: true, score: 1.0 };
402
402
  }
@@ -1,5 +1,6 @@
1
+ import type { NeuroLink } from "../neurolink.js";
1
2
  import type { AIProviderName } from "../constants/enums.js";
2
- import type { AIProvider, NeurolinkCredentials, ProviderConstructor, ProviderRegistration, UnknownRecord } from "../types/index.js";
3
+ import type { AIProvider, NeurolinkCredentials, ProviderConstructor, ProviderRegistration } from "../types/index.js";
3
4
  /**
4
5
  * True Factory Pattern implementation for AI Providers
5
6
  * Uses registration-based approach to eliminate switch statements
@@ -18,7 +19,7 @@ export declare class ProviderFactory {
18
19
  * @param providerName - Provider name (optional, uses NEUROLINK_PROVIDER env var or 'vertex' as default)
19
20
  * @param modelName - Model name (optional, uses provider-specific env var or registry default)
20
21
  */
21
- static createProvider(providerName?: AIProviderName | string, modelName?: string, sdk?: UnknownRecord, region?: string, credentials?: NeurolinkCredentials): Promise<AIProvider>;
22
+ static createProvider(providerName?: AIProviderName | string, modelName?: string, sdk?: NeuroLink, region?: string, credentials?: NeurolinkCredentials): Promise<AIProvider>;
22
23
  /**
23
24
  * Check if a provider is registered
24
25
  */
@@ -52,7 +53,7 @@ export declare class ProviderFactory {
52
53
  * Create the best available provider for the given name
53
54
  * Used by NeuroLink SDK for streaming and generation
54
55
  */
55
- static createBestProvider(providerName: AIProviderName | string, modelName?: string, enableMCP?: boolean, sdk?: UnknownRecord, credentials?: NeurolinkCredentials): Promise<AIProvider>;
56
+ static createBestProvider(providerName: AIProviderName | string, modelName?: string, enableMCP?: boolean, sdk?: NeuroLink, credentials?: NeurolinkCredentials): Promise<AIProvider>;
56
57
  }
57
58
  /**
58
59
  * Helper function to create providers with backward compatibility
@@ -28,10 +28,15 @@ export declare class ProviderRegistry {
28
28
  /**
29
29
  * Internal registration implementation
30
30
  *
31
- * This method is a flat list of 13 provider registrations. Each registration
32
- * is self-contained and extracting helpers would add indirection without
33
- * reducing complexity the function is long because there are many providers,
34
- * not because any single registration is complex.
31
+ * Flat list of ProviderFactory.registerProvider() calls. Providers load via
32
+ * dynamic import() of ../providers/<module>.js only - never static imports
33
+ * (avoids circular dependencies; see CLAUDE.md).
34
+ *
35
+ * Not registered (by design): index.ts, providerTypeUtils.ts,
36
+ * anthropicBaseProvider.ts (legacy; anthropic.ts is live),
37
+ * googleNativeGemini3.ts (shared helpers). Filename != provider ID
38
+ * (e.g. amazonBedrock -> "bedrock"); static scanners that miss dynamic
39
+ * imports may false-positive (Pattern Analysis #1178).
35
40
  */
36
41
  private static _doRegister;
37
42
  /**
@@ -47,10 +47,15 @@ export class ProviderRegistry {
47
47
  /**
48
48
  * Internal registration implementation
49
49
  *
50
- * This method is a flat list of 13 provider registrations. Each registration
51
- * is self-contained and extracting helpers would add indirection without
52
- * reducing complexity the function is long because there are many providers,
53
- * not because any single registration is complex.
50
+ * Flat list of ProviderFactory.registerProvider() calls. Providers load via
51
+ * dynamic import() of ../providers/<module>.js only - never static imports
52
+ * (avoids circular dependencies; see CLAUDE.md).
53
+ *
54
+ * Not registered (by design): index.ts, providerTypeUtils.ts,
55
+ * anthropicBaseProvider.ts (legacy; anthropic.ts is live),
56
+ * googleNativeGemini3.ts (shared helpers). Filename != provider ID
57
+ * (e.g. amazonBedrock -> "bedrock"); static scanners that miss dynamic
58
+ * imports may false-positive (Pattern Analysis #1178).
54
59
  */
55
60
  // eslint-disable-next-line max-lines-per-function
56
61
  static async _doRegister() {
@@ -23,11 +23,12 @@ export async function loadPptxGenJS() {
23
23
  }
24
24
  try {
25
25
  const mod = await import(/* @vite-ignore */ "pptxgenjs");
26
- // ESM/CJS interop: pptxgenjs v4 may double-wrap the default export
27
- const Ctor = typeof mod.default === "function"
28
- ? mod.default
29
- : mod.default
30
- .default;
26
+ // ESM/CJS interop: pptxgenjs v4 may double-wrap the default export.
27
+ // The runtime shape is genuinely dynamic, so probe it as `unknown`.
28
+ const rawDefault = mod.default;
29
+ const Ctor = typeof rawDefault === "function"
30
+ ? rawDefault
31
+ : rawDefault.default;
31
32
  _pptxGenJS = Ctor;
32
33
  return _pptxGenJS;
33
34
  }
@@ -5,6 +5,7 @@
5
5
  *
6
6
  * @module ppt/utils
7
7
  */
8
+ import type { NeuroLink } from "../../neurolink.js";
8
9
  import type { PPTGenerationContext, AspectRatioOption, EffectivePPTProviderResult, ImageValidationResult, TextSegment, LogoConfig, GenerateOptions } from "../../types/index.js";
9
10
  /**
10
11
  * Extract PPT generation context from GenerateOptions
@@ -18,7 +19,7 @@ export declare const PPT_VALID_PROVIDERS: readonly string[];
18
19
  /**
19
20
  * Get an effective PPT provider - handles all orchestration logic
20
21
  */
21
- export declare function getEffectivePPTProvider(currentProvider: unknown, currentProviderName: string, currentModelName: string, neurolink?: unknown): Promise<EffectivePPTProviderResult>;
22
+ export declare function getEffectivePPTProvider(currentProvider: unknown, currentProviderName: string, currentModelName: string, neurolink?: NeuroLink): Promise<EffectivePPTProviderResult>;
22
23
  /**
23
24
  * Generate output file path for PPT
24
25
  */
@@ -99,6 +99,7 @@ export async function getEffectivePPTProvider(currentProvider, currentProviderNa
99
99
  const { ErrorFactory } = await import("../../utils/errorHandling.js");
100
100
  const normalizedProvider = currentProviderName.toLowerCase();
101
101
  if (PPT_VALID_PROVIDERS.includes(normalizedProvider)) {
102
+ // Single assertion from `unknown` — the shape is probed defensively below.
102
103
  const providerInstance = currentProvider;
103
104
  const actualModelName = currentModelName ||
104
105
  providerInstance?.modelName ||
@@ -151,7 +151,10 @@ async function getAccessToken() {
151
151
  try {
152
152
  // google-auth-library is a transitive dependency from @google-cloud/vertexai
153
153
  // Using dynamic import with type assertion for runtime resolution
154
- const googleAuthLib = (await import("google-auth-library"));
154
+ const googleAuthLib = (await import(
155
+ // Widening the literal to `string` skips compile-time module resolution
156
+ // (the package is an untyped transitive dependency).
157
+ "google-auth-library"));
155
158
  const auth = new googleAuthLib.GoogleAuth({
156
159
  keyFilename: process.env.GOOGLE_APPLICATION_CREDENTIALS,
157
160
  scopes: ["https://www.googleapis.com/auth/cloud-platform"],
@@ -24,6 +24,8 @@ export class NetworkOrchestrator {
24
24
  config;
25
25
  emitter;
26
26
  executionQueue = [];
27
+ // `void` admits the resolved placeholder used by streamNetwork to track
28
+ // an in-flight stream; only .size/.set/.delete are ever used on this map.
27
29
  activeExecutions = new Map();
28
30
  constructor(neurolink, config) {
29
31
  this.neurolink = neurolink;
@@ -137,7 +137,7 @@ export class Auth0Provider extends BaseAuthProvider {
137
137
  };
138
138
  return {
139
139
  valid: true,
140
- payload: payload,
140
+ payload,
141
141
  user,
142
142
  expiresAt: new Date(auth0Payload.exp * 1000),
143
143
  tokenType: "jwt",
@@ -84,7 +84,7 @@ export class BetterAuthProvider extends BaseAuthProvider {
84
84
  };
85
85
  return {
86
86
  valid: true,
87
- payload: payload,
87
+ payload,
88
88
  user,
89
89
  expiresAt: payload.exp ? new Date(payload.exp * 1000) : undefined,
90
90
  tokenType: "jwt",
@@ -117,7 +117,7 @@ export class ClerkProvider extends BaseAuthProvider {
117
117
  };
118
118
  return {
119
119
  valid: true,
120
- payload: payload,
120
+ payload,
121
121
  user,
122
122
  expiresAt: payload.exp ? new Date(payload.exp * 1000) : undefined,
123
123
  tokenType: "jwt",
@@ -73,7 +73,7 @@ export class FirebaseAuthProvider extends BaseAuthProvider {
73
73
  const user = this.payloadToUser(payload);
74
74
  return {
75
75
  valid: true,
76
- payload: payload,
76
+ payload,
77
77
  user,
78
78
  expiresAt: payload.exp ? new Date(payload.exp * 1000) : undefined,
79
79
  tokenType: "jwt",
@@ -134,7 +134,7 @@ export class JWTProvider extends BaseAuthProvider {
134
134
  };
135
135
  return {
136
136
  valid: true,
137
- payload: payload,
137
+ payload,
138
138
  user,
139
139
  expiresAt: payload.exp ? new Date(payload.exp * 1000) : undefined,
140
140
  tokenType: "jwt",
@@ -140,7 +140,7 @@ export class OAuth2Provider extends BaseAuthProvider {
140
140
  };
141
141
  return {
142
142
  valid: true,
143
- payload: payload,
143
+ payload,
144
144
  user,
145
145
  expiresAt: payload.exp ? new Date(payload.exp * 1000) : undefined,
146
146
  tokenType: "jwt",
@@ -77,7 +77,7 @@ export class SupabaseAuthProvider extends BaseAuthProvider {
77
77
  const user = this.payloadToUser(payload);
78
78
  return {
79
79
  valid: true,
80
- payload: payload,
80
+ payload,
81
81
  user,
82
82
  expiresAt: payload.exp ? new Date(payload.exp * 1000) : undefined,
83
83
  tokenType: "jwt",
@@ -99,7 +99,7 @@ export class WorkOSProvider extends BaseAuthProvider {
99
99
  };
100
100
  return {
101
101
  valid: true,
102
- payload: payload,
102
+ payload,
103
103
  user,
104
104
  expiresAt: payload.exp ? new Date(payload.exp * 1000) : undefined,
105
105
  tokenType: "jwt",
@@ -121,13 +121,8 @@ export class OAuth2TokenManager {
121
121
  throw new OAuth2Error(`OAuth2 token request failed: ${response.status}`, response.status, errorText);
122
122
  }
123
123
  const data = (await response.json());
124
- this.token =
125
- data.accessToken ||
126
- data.access_token ||
127
- "";
128
- const expiresIn = data.expiresIn ||
129
- data.expires_in ||
130
- 3600;
124
+ this.token = data.accessToken || data.access_token || "";
125
+ const expiresIn = data.expiresIn ?? data.expires_in ?? 3600;
131
126
  this.tokenExpiry = Date.now() + expiresIn * 1000;
132
127
  if (!this.token) {
133
128
  throw new OAuth2Error("OAuth2 response missing access token", 200, JSON.stringify(data));
@@ -758,8 +758,8 @@ export function useVoice(options = {}) {
758
758
  if (typeof window === "undefined") {
759
759
  return null;
760
760
  }
761
- const SpeechRecognitionCtor = window.SpeechRecognition ||
762
- window.webkitSpeechRecognition;
761
+ const speechWindow = window;
762
+ const SpeechRecognitionCtor = speechWindow.SpeechRecognition || speechWindow.webkitSpeechRecognition;
763
763
  if (!SpeechRecognitionCtor) {
764
764
  return null;
765
765
  }
@@ -294,7 +294,7 @@ export declare abstract class BaseProvider implements AIProvider {
294
294
  /**
295
295
  * Get AI SDK model with middleware applied
296
296
  * This method wraps the base model with any configured middleware
297
- * TODO: Implement global level middlewares that can be used
297
+ * TODO(#1179): Implement global level middlewares that can be used
298
298
  */
299
299
  protected getAISDKModelWithMiddleware(options?: TextGenerationOptions | StreamOptions): Promise<LanguageModel>;
300
300
  /**