@juspay/neurolink 7.6.0 → 7.7.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 (136) hide show
  1. package/CHANGELOG.md +14 -2
  2. package/README.md +79 -4
  3. package/dist/cli/commands/config.d.ts +275 -3
  4. package/dist/cli/commands/config.js +121 -0
  5. package/dist/cli/commands/mcp.js +77 -28
  6. package/dist/cli/factories/commandFactory.js +359 -6
  7. package/dist/core/analytics.js +7 -27
  8. package/dist/core/baseProvider.js +43 -4
  9. package/dist/core/constants.d.ts +46 -0
  10. package/dist/core/constants.js +47 -0
  11. package/dist/core/dynamicModels.d.ts +16 -4
  12. package/dist/core/dynamicModels.js +130 -26
  13. package/dist/core/evaluation.js +5 -1
  14. package/dist/core/evaluationProviders.d.ts +6 -2
  15. package/dist/core/evaluationProviders.js +41 -125
  16. package/dist/core/factory.d.ts +5 -0
  17. package/dist/core/factory.js +62 -50
  18. package/dist/core/modelConfiguration.d.ts +246 -0
  19. package/dist/core/modelConfiguration.js +775 -0
  20. package/dist/core/types.d.ts +22 -3
  21. package/dist/core/types.js +5 -1
  22. package/dist/factories/providerRegistry.js +3 -3
  23. package/dist/index.d.ts +1 -1
  24. package/dist/index.js +1 -1
  25. package/dist/lib/core/analytics.js +7 -27
  26. package/dist/lib/core/baseProvider.js +43 -4
  27. package/dist/lib/core/constants.d.ts +46 -0
  28. package/dist/lib/core/constants.js +47 -0
  29. package/dist/lib/core/dynamicModels.d.ts +16 -4
  30. package/dist/lib/core/dynamicModels.js +130 -26
  31. package/dist/lib/core/evaluation.js +5 -1
  32. package/dist/lib/core/evaluationProviders.d.ts +6 -2
  33. package/dist/lib/core/evaluationProviders.js +41 -125
  34. package/dist/lib/core/factory.d.ts +5 -0
  35. package/dist/lib/core/factory.js +63 -50
  36. package/dist/lib/core/modelConfiguration.d.ts +246 -0
  37. package/dist/lib/core/modelConfiguration.js +775 -0
  38. package/dist/lib/core/types.d.ts +22 -3
  39. package/dist/lib/core/types.js +5 -1
  40. package/dist/lib/factories/providerRegistry.js +3 -3
  41. package/dist/lib/index.d.ts +1 -1
  42. package/dist/lib/index.js +1 -1
  43. package/dist/lib/mcp/factory.d.ts +5 -5
  44. package/dist/lib/mcp/factory.js +2 -2
  45. package/dist/lib/mcp/servers/utilities/utilityServer.d.ts +1 -1
  46. package/dist/lib/mcp/servers/utilities/utilityServer.js +1 -1
  47. package/dist/lib/mcp/toolRegistry.js +2 -2
  48. package/dist/lib/neurolink.d.ts +168 -12
  49. package/dist/lib/neurolink.js +685 -123
  50. package/dist/lib/providers/anthropic.js +52 -2
  51. package/dist/lib/providers/googleAiStudio.js +4 -0
  52. package/dist/lib/providers/googleVertex.d.ts +75 -9
  53. package/dist/lib/providers/googleVertex.js +365 -46
  54. package/dist/lib/providers/huggingFace.d.ts +52 -11
  55. package/dist/lib/providers/huggingFace.js +180 -42
  56. package/dist/lib/providers/litellm.d.ts +9 -9
  57. package/dist/lib/providers/litellm.js +103 -16
  58. package/dist/lib/providers/ollama.d.ts +52 -17
  59. package/dist/lib/providers/ollama.js +276 -68
  60. package/dist/lib/sdk/toolRegistration.d.ts +42 -0
  61. package/dist/lib/sdk/toolRegistration.js +269 -27
  62. package/dist/lib/telemetry/telemetryService.d.ts +6 -0
  63. package/dist/lib/telemetry/telemetryService.js +38 -3
  64. package/dist/lib/types/contextTypes.d.ts +75 -11
  65. package/dist/lib/types/contextTypes.js +227 -1
  66. package/dist/lib/types/domainTypes.d.ts +62 -0
  67. package/dist/lib/types/domainTypes.js +5 -0
  68. package/dist/lib/types/generateTypes.d.ts +52 -0
  69. package/dist/lib/types/index.d.ts +1 -0
  70. package/dist/lib/types/mcpTypes.d.ts +1 -1
  71. package/dist/lib/types/mcpTypes.js +1 -1
  72. package/dist/lib/types/streamTypes.d.ts +14 -0
  73. package/dist/lib/types/universalProviderOptions.d.ts +1 -1
  74. package/dist/lib/utils/errorHandling.d.ts +142 -0
  75. package/dist/lib/utils/errorHandling.js +316 -0
  76. package/dist/lib/utils/factoryProcessing.d.ts +74 -0
  77. package/dist/lib/utils/factoryProcessing.js +588 -0
  78. package/dist/lib/utils/optionsConversion.d.ts +54 -0
  79. package/dist/lib/utils/optionsConversion.js +126 -0
  80. package/dist/lib/utils/optionsUtils.d.ts +246 -0
  81. package/dist/lib/utils/optionsUtils.js +960 -0
  82. package/dist/lib/utils/providerHealth.d.ts +107 -0
  83. package/dist/lib/utils/providerHealth.js +507 -0
  84. package/dist/lib/utils/providerUtils.d.ts +17 -0
  85. package/dist/lib/utils/providerUtils.js +271 -16
  86. package/dist/lib/utils/timeout.js +1 -1
  87. package/dist/lib/utils/tokenLimits.d.ts +33 -0
  88. package/dist/lib/utils/tokenLimits.js +118 -0
  89. package/dist/mcp/factory.d.ts +5 -5
  90. package/dist/mcp/factory.js +2 -2
  91. package/dist/mcp/servers/utilities/utilityServer.d.ts +1 -1
  92. package/dist/mcp/servers/utilities/utilityServer.js +1 -1
  93. package/dist/mcp/toolRegistry.js +2 -2
  94. package/dist/neurolink.d.ts +168 -12
  95. package/dist/neurolink.js +685 -123
  96. package/dist/providers/anthropic.js +52 -2
  97. package/dist/providers/googleAiStudio.js +4 -0
  98. package/dist/providers/googleVertex.d.ts +75 -9
  99. package/dist/providers/googleVertex.js +365 -46
  100. package/dist/providers/huggingFace.d.ts +52 -11
  101. package/dist/providers/huggingFace.js +181 -43
  102. package/dist/providers/litellm.d.ts +9 -9
  103. package/dist/providers/litellm.js +103 -16
  104. package/dist/providers/ollama.d.ts +52 -17
  105. package/dist/providers/ollama.js +276 -68
  106. package/dist/sdk/toolRegistration.d.ts +42 -0
  107. package/dist/sdk/toolRegistration.js +269 -27
  108. package/dist/telemetry/telemetryService.d.ts +6 -0
  109. package/dist/telemetry/telemetryService.js +38 -3
  110. package/dist/types/contextTypes.d.ts +75 -11
  111. package/dist/types/contextTypes.js +227 -2
  112. package/dist/types/domainTypes.d.ts +62 -0
  113. package/dist/types/domainTypes.js +5 -0
  114. package/dist/types/generateTypes.d.ts +52 -0
  115. package/dist/types/index.d.ts +1 -0
  116. package/dist/types/mcpTypes.d.ts +1 -1
  117. package/dist/types/mcpTypes.js +1 -1
  118. package/dist/types/streamTypes.d.ts +14 -0
  119. package/dist/types/universalProviderOptions.d.ts +1 -1
  120. package/dist/types/universalProviderOptions.js +0 -1
  121. package/dist/utils/errorHandling.d.ts +142 -0
  122. package/dist/utils/errorHandling.js +316 -0
  123. package/dist/utils/factoryProcessing.d.ts +74 -0
  124. package/dist/utils/factoryProcessing.js +588 -0
  125. package/dist/utils/optionsConversion.d.ts +54 -0
  126. package/dist/utils/optionsConversion.js +126 -0
  127. package/dist/utils/optionsUtils.d.ts +246 -0
  128. package/dist/utils/optionsUtils.js +960 -0
  129. package/dist/utils/providerHealth.d.ts +107 -0
  130. package/dist/utils/providerHealth.js +507 -0
  131. package/dist/utils/providerUtils.d.ts +17 -0
  132. package/dist/utils/providerUtils.js +271 -16
  133. package/dist/utils/timeout.js +1 -1
  134. package/dist/utils/tokenLimits.d.ts +33 -0
  135. package/dist/utils/tokenLimits.js +118 -0
  136. package/package.json +2 -2
@@ -4,6 +4,7 @@
4
4
  */
5
5
  import { AIProviderFactory } from "../core/factory.js";
6
6
  import { logger } from "./logger.js";
7
+ import { ProviderHealthChecker } from "./providerHealth.js";
7
8
  /**
8
9
  * Get the best available provider based on real-time availability checks
9
10
  * Enhanced version consolidated from providerUtils-fixed.ts
@@ -11,12 +12,39 @@ import { logger } from "./logger.js";
11
12
  * @returns The best provider name to use
12
13
  */
13
14
  export async function getBestProvider(requestedProvider) {
14
- // 🔧 FIX: Check for explicit default provider in env
15
+ // Check requested provider FIRST - explicit user choice overrides defaults
16
+ if (requestedProvider && requestedProvider !== "auto") {
17
+ // For explicit provider requests, check health first
18
+ try {
19
+ const health = await ProviderHealthChecker.checkProviderHealth(requestedProvider, { includeConnectivityTest: false, cacheResults: true });
20
+ if (health.isHealthy) {
21
+ logger.debug(`[getBestProvider] Using healthy explicitly requested provider: ${requestedProvider}`);
22
+ return requestedProvider;
23
+ }
24
+ else {
25
+ logger.warn(`[getBestProvider] Requested provider ${requestedProvider} is unhealthy, finding alternative`, { error: health.error });
26
+ }
27
+ }
28
+ catch (error) {
29
+ logger.warn(`[getBestProvider] Health check failed for ${requestedProvider}, using anyway`, { error: error instanceof Error ? error.message : String(error) });
30
+ return requestedProvider; // Return anyway for explicit requests
31
+ }
32
+ }
33
+ // Use health checker to get best available provider
34
+ const healthyProvider = await ProviderHealthChecker.getBestHealthyProvider();
35
+ if (healthyProvider) {
36
+ logger.debug(`[getBestProvider] Selected healthy provider: ${healthyProvider}`);
37
+ return healthyProvider;
38
+ }
39
+ // Fallback to legacy provider checking if health system fails
40
+ logger.warn("[getBestProvider] Health system failed, falling back to legacy checking");
41
+ // Check for explicit default provider in env (only when no provider requested)
15
42
  if (process.env.DEFAULT_PROVIDER &&
16
43
  (await isProviderAvailable(process.env.DEFAULT_PROVIDER))) {
44
+ logger.debug(`[getBestProvider] Using default provider from env: ${process.env.DEFAULT_PROVIDER}`);
17
45
  return process.env.DEFAULT_PROVIDER;
18
46
  }
19
- // 🔧 FIX: Special case for Ollama - prioritize local when available
47
+ // Special case for Ollama - prioritize local when available
20
48
  if (process.env.OLLAMA_BASE_URL && process.env.OLLAMA_MODEL) {
21
49
  try {
22
50
  if (await isProviderAvailable("ollama")) {
@@ -28,26 +56,26 @@ export async function getBestProvider(requestedProvider) {
28
56
  // Fall through to cloud providers
29
57
  }
30
58
  }
59
+ /**
60
+ * Provider priority order rationale:
61
+ * - Vertex (Google Cloud AI) is prioritized first for its enterprise-grade reliability and advanced model capabilities.
62
+ * - Google AI follows as second priority for comprehensive Google AI ecosystem support.
63
+ * - OpenAI maintains high priority due to its consistent reliability and broad model support.
64
+ * - Other providers are ordered based on a combination of reliability, feature set, and historical performance in our use cases.
65
+ * - Ollama is kept as a fallback for local deployments when available.
66
+ * Please update this comment if the order is changed in the future, and document the rationale for maintainability.
67
+ */
31
68
  const providers = [
32
- "google-ai",
69
+ "vertex", // Prioritize Google Cloud AI (Vertex) first
70
+ "google-ai", // Google AI ecosystem support
71
+ "openai", // Reliable with broad model support
33
72
  "anthropic",
34
- "openai",
35
- "mistral",
36
- "vertex",
73
+ "bedrock",
37
74
  "azure",
75
+ "mistral",
38
76
  "huggingface",
39
- "bedrock",
40
77
  "ollama", // Keep as fallback
41
78
  ];
42
- if (requestedProvider && requestedProvider !== "auto") {
43
- if (await isProviderAvailable(requestedProvider)) {
44
- logger.debug(`[getBestProvider] Using requested provider: ${requestedProvider}`);
45
- return requestedProvider;
46
- }
47
- else {
48
- logger.warn(`[getBestProvider] Requested provider '${requestedProvider}' is not available. Falling back to auto-selection.`);
49
- }
50
- }
51
79
  for (const provider of providers) {
52
80
  if (await isProviderAvailable(provider)) {
53
81
  logger.debug(`[getBestProvider] Selected provider: ${provider}`);
@@ -92,9 +120,236 @@ async function isProviderAvailable(providerName) {
92
120
  return false;
93
121
  }
94
122
  }
123
+ /**
124
+ * Google Cloud Project ID validation regex
125
+ * Format requirements:
126
+ * - Must start with a lowercase letter
127
+ * - Can contain lowercase letters, numbers, and hyphens
128
+ * - Must end with a lowercase letter or number
129
+ * - Total length must be 6-30 characters
130
+ */
131
+ const GOOGLE_CLOUD_PROJECT_ID_REGEX = /^[a-z][a-z0-9-]{4,28}[a-z0-9]$/;
132
+ /**
133
+ * Validate environment variable values for a provider
134
+ * Addresses GitHub Copilot comment about adding environment variable validation
135
+ * @param provider - Provider name to validate
136
+ * @returns Validation result with detailed information
137
+ */
138
+ export function validateProviderEnvVars(provider) {
139
+ const result = {
140
+ isValid: true,
141
+ missingVars: [],
142
+ invalidVars: [],
143
+ warnings: [],
144
+ };
145
+ switch (provider.toLowerCase()) {
146
+ case "bedrock":
147
+ case "amazon":
148
+ case "aws":
149
+ validateAwsCredentials(result);
150
+ break;
151
+ case "vertex":
152
+ case "googlevertex":
153
+ case "google":
154
+ case "gemini":
155
+ validateVertexCredentials(result);
156
+ break;
157
+ case "openai":
158
+ case "gpt":
159
+ validateOpenAICredentials(result);
160
+ break;
161
+ case "anthropic":
162
+ case "claude":
163
+ validateAnthropicCredentials(result);
164
+ break;
165
+ case "azure":
166
+ case "azureOpenai":
167
+ validateAzureCredentials(result);
168
+ break;
169
+ case "google-ai":
170
+ case "google-studio":
171
+ validateGoogleAICredentials(result);
172
+ break;
173
+ case "huggingface":
174
+ case "hugging-face":
175
+ case "hf":
176
+ validateHuggingFaceCredentials(result);
177
+ break;
178
+ case "mistral":
179
+ case "mistral-ai":
180
+ case "mistralai":
181
+ validateMistralCredentials(result);
182
+ break;
183
+ case "ollama":
184
+ case "local":
185
+ case "local-ollama":
186
+ // Ollama doesn't require environment variables
187
+ break;
188
+ case "litellm":
189
+ // LiteLLM validation can be added if needed
190
+ break;
191
+ default:
192
+ result.isValid = false;
193
+ result.warnings.push(`Unknown provider: ${provider}`);
194
+ }
195
+ result.isValid =
196
+ result.missingVars.length === 0 && result.invalidVars.length === 0;
197
+ return result;
198
+ }
199
+ /**
200
+ * Validate AWS credentials with flexible validation
201
+ * Note: AWS credential formats can vary, so validation is kept reasonably flexible
202
+ */
203
+ function validateAwsCredentials(result) {
204
+ const accessKeyId = process.env.AWS_ACCESS_KEY_ID;
205
+ const secretAccessKey = process.env.AWS_SECRET_ACCESS_KEY;
206
+ const region = process.env.AWS_REGION || process.env.AWS_DEFAULT_REGION;
207
+ if (!accessKeyId) {
208
+ result.missingVars.push("AWS_ACCESS_KEY_ID");
209
+ }
210
+ else if (!/^[A-Z0-9]{16,}$/.test(accessKeyId)) {
211
+ // Flexible validation: at least 16 uppercase alphanumeric characters
212
+ result.invalidVars.push("AWS_ACCESS_KEY_ID (should be uppercase alphanumeric characters, typically 20 chars)");
213
+ }
214
+ if (!secretAccessKey) {
215
+ result.missingVars.push("AWS_SECRET_ACCESS_KEY");
216
+ }
217
+ else if (!/^[A-Za-z0-9+/]{30,}$/.test(secretAccessKey)) {
218
+ // Flexible validation: at least 30 base64 characters (can vary in length)
219
+ result.invalidVars.push("AWS_SECRET_ACCESS_KEY (should be base64 characters, typically 40+ chars)");
220
+ }
221
+ if (!region) {
222
+ result.warnings.push("AWS_REGION not set, will use default region");
223
+ }
224
+ }
225
+ /**
226
+ * Validate Google Vertex credentials
227
+ */
228
+ function validateVertexCredentials(result) {
229
+ const projectId = process.env.GOOGLE_CLOUD_PROJECT_ID ||
230
+ process.env.VERTEX_PROJECT_ID ||
231
+ process.env.GOOGLE_VERTEX_PROJECT ||
232
+ process.env.GOOGLE_CLOUD_PROJECT;
233
+ const hasCredentials = process.env.GOOGLE_APPLICATION_CREDENTIALS ||
234
+ process.env.GOOGLE_SERVICE_ACCOUNT_KEY ||
235
+ (process.env.GOOGLE_AUTH_CLIENT_EMAIL &&
236
+ process.env.GOOGLE_AUTH_PRIVATE_KEY);
237
+ if (!projectId) {
238
+ result.missingVars.push("GOOGLE_CLOUD_PROJECT_ID (or variant)");
239
+ }
240
+ else if (!GOOGLE_CLOUD_PROJECT_ID_REGEX.test(projectId)) {
241
+ result.invalidVars.push("Project ID format invalid (must be 6-30 lowercase letters, digits, hyphens)");
242
+ }
243
+ if (!hasCredentials) {
244
+ result.missingVars.push("Google credentials (GOOGLE_APPLICATION_CREDENTIALS or explicit auth)");
245
+ }
246
+ if (process.env.GOOGLE_AUTH_CLIENT_EMAIL &&
247
+ !isValidEmail(process.env.GOOGLE_AUTH_CLIENT_EMAIL)) {
248
+ result.invalidVars.push("GOOGLE_AUTH_CLIENT_EMAIL (invalid email format)");
249
+ }
250
+ }
251
+ /**
252
+ * Validate OpenAI credentials
253
+ */
254
+ function validateOpenAICredentials(result) {
255
+ const apiKey = process.env.OPENAI_API_KEY;
256
+ if (!apiKey) {
257
+ result.missingVars.push("OPENAI_API_KEY");
258
+ }
259
+ else if (!/^sk-[A-Za-z0-9]{48,}$/.test(apiKey)) {
260
+ result.invalidVars.push("OPENAI_API_KEY (should start with 'sk-' followed by 48+ characters)");
261
+ }
262
+ }
263
+ /**
264
+ * Validate Anthropic credentials
265
+ */
266
+ function validateAnthropicCredentials(result) {
267
+ const apiKey = process.env.ANTHROPIC_API_KEY;
268
+ if (!apiKey) {
269
+ result.missingVars.push("ANTHROPIC_API_KEY");
270
+ }
271
+ else if (!/^sk-ant-[A-Za-z0-9-_]{95,}$/.test(apiKey)) {
272
+ result.invalidVars.push("ANTHROPIC_API_KEY (should start with 'sk-ant-' followed by 95+ characters)");
273
+ }
274
+ }
275
+ /**
276
+ * Validate Azure credentials
277
+ */
278
+ function validateAzureCredentials(result) {
279
+ const apiKey = process.env.AZURE_OPENAI_API_KEY;
280
+ const endpoint = process.env.AZURE_OPENAI_ENDPOINT;
281
+ if (!apiKey) {
282
+ result.missingVars.push("AZURE_OPENAI_API_KEY");
283
+ }
284
+ else if (!/^[a-f0-9]{32}$/.test(apiKey)) {
285
+ result.invalidVars.push("AZURE_OPENAI_API_KEY (should be 32 hexadecimal characters)");
286
+ }
287
+ if (!endpoint) {
288
+ result.missingVars.push("AZURE_OPENAI_ENDPOINT");
289
+ }
290
+ else if (!isValidUrl(endpoint)) {
291
+ result.invalidVars.push("AZURE_OPENAI_ENDPOINT (should be a valid HTTPS URL)");
292
+ }
293
+ }
294
+ /**
295
+ * Validate Google AI credentials
296
+ */
297
+ function validateGoogleAICredentials(result) {
298
+ const apiKey = process.env.GOOGLE_AI_API_KEY || process.env.GOOGLE_GENERATIVE_AI_API_KEY;
299
+ if (!apiKey) {
300
+ result.missingVars.push("GOOGLE_AI_API_KEY (or GOOGLE_GENERATIVE_AI_API_KEY)");
301
+ }
302
+ else if (!/^[A-Za-z0-9_-]{39}$/.test(apiKey)) {
303
+ result.invalidVars.push("GOOGLE_AI_API_KEY (should be 39 alphanumeric characters with dashes/underscores)");
304
+ }
305
+ }
306
+ /**
307
+ * Validate HuggingFace credentials
308
+ */
309
+ function validateHuggingFaceCredentials(result) {
310
+ const apiKey = process.env.HUGGINGFACE_API_KEY || process.env.HF_TOKEN;
311
+ if (!apiKey) {
312
+ result.missingVars.push("HUGGINGFACE_API_KEY (or HF_TOKEN)");
313
+ }
314
+ else if (!/^hf_[A-Za-z0-9]{37}$/.test(apiKey)) {
315
+ result.invalidVars.push("HUGGINGFACE_API_KEY (should start with 'hf_' followed by 37 characters)");
316
+ }
317
+ }
318
+ /**
319
+ * Validate Mistral credentials
320
+ */
321
+ function validateMistralCredentials(result) {
322
+ const apiKey = process.env.MISTRAL_API_KEY;
323
+ if (!apiKey) {
324
+ result.missingVars.push("MISTRAL_API_KEY");
325
+ }
326
+ else if (!/^[A-Za-z0-9]{32,}$/.test(apiKey)) {
327
+ result.invalidVars.push("MISTRAL_API_KEY (should be 32+ alphanumeric characters)");
328
+ }
329
+ }
330
+ /**
331
+ * Helper function to validate email format
332
+ */
333
+ function isValidEmail(email) {
334
+ const emailRegex = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
335
+ return emailRegex.test(email);
336
+ }
337
+ /**
338
+ * Helper function to validate URL format
339
+ */
340
+ function isValidUrl(url) {
341
+ try {
342
+ const parsedUrl = new URL(url);
343
+ return parsedUrl.protocol === "https:";
344
+ }
345
+ catch {
346
+ return false;
347
+ }
348
+ }
95
349
  /**
96
350
  * Check if a provider has the minimum required environment variables
97
351
  * NOTE: This only checks if variables exist, not if they're valid
352
+ * For validation, use validateProviderEnvVars instead
98
353
  * @param provider - Provider name to check
99
354
  * @returns True if the provider has required environment variables
100
355
  */
@@ -82,7 +82,7 @@ export const DEFAULT_TIMEOUTS = {
82
82
  openai: "30s", // OpenAI typically responds quickly
83
83
  bedrock: "45s", // AWS can be slower, especially for cold starts
84
84
  vertex: "60s", // Google Cloud can be slower
85
- anthropic: "30s", // Direct Anthropic API is fast
85
+ anthropic: "60s", // Increased timeout for Anthropic API stability
86
86
  azure: "30s", // Azure OpenAI similar to OpenAI
87
87
  "google-ai": "30s", // Google AI Studio is fast
88
88
  huggingface: "2m", // Open source models vary significantly
@@ -0,0 +1,33 @@
1
+ /**
2
+ * Provider-specific token limit utilities
3
+ * Provides safe maxTokens values based on provider and model capabilities
4
+ */
5
+ import { PROVIDER_MAX_TOKENS } from "../core/constants.js";
6
+ /**
7
+ * Get the safe maximum tokens for a provider and model
8
+ */
9
+ export declare function getSafeMaxTokens(provider: keyof typeof PROVIDER_MAX_TOKENS | string, model?: string, requestedMaxTokens?: number): number;
10
+ /**
11
+ * Validate if maxTokens is safe for a provider/model combination
12
+ */
13
+ export declare function validateMaxTokens(provider: keyof typeof PROVIDER_MAX_TOKENS | string, model?: string, maxTokens?: number): {
14
+ isValid: boolean;
15
+ recommendedMaxTokens: number;
16
+ warning?: string;
17
+ };
18
+ /**
19
+ * Get provider-specific token limit recommendations
20
+ */
21
+ export declare function getTokenLimitRecommendations(provider: string): {
22
+ conservative: number;
23
+ balanced: number;
24
+ maximum: number;
25
+ models: Record<string, number>;
26
+ };
27
+ /**
28
+ * Get all provider limits summary
29
+ */
30
+ export declare function getAllProviderLimits(): Record<string, {
31
+ default: number;
32
+ models: Record<string, number>;
33
+ }>;
@@ -0,0 +1,118 @@
1
+ /**
2
+ * Provider-specific token limit utilities
3
+ * Provides safe maxTokens values based on provider and model capabilities
4
+ */
5
+ import { PROVIDER_MAX_TOKENS, DEFAULT_MAX_TOKENS } from "../core/constants.js";
6
+ import { logger } from "./logger.js";
7
+ /**
8
+ * Get the safe maximum tokens for a provider and model
9
+ */
10
+ export function getSafeMaxTokens(provider, model, requestedMaxTokens) {
11
+ // Get provider-specific limits
12
+ const providerLimits = PROVIDER_MAX_TOKENS[provider];
13
+ if (!providerLimits) {
14
+ logger.warn(`Unknown provider ${provider}, using default maxTokens limit`);
15
+ return Math.min(requestedMaxTokens || DEFAULT_MAX_TOKENS, PROVIDER_MAX_TOKENS.default);
16
+ }
17
+ // Get model-specific limit or provider default
18
+ let maxLimit;
19
+ if (model &&
20
+ typeof providerLimits === "object" &&
21
+ providerLimits[model]) {
22
+ maxLimit = providerLimits[model];
23
+ }
24
+ else if (typeof providerLimits === "object" &&
25
+ providerLimits.default) {
26
+ maxLimit = providerLimits.default;
27
+ }
28
+ else if (typeof providerLimits === "number") {
29
+ maxLimit = providerLimits;
30
+ }
31
+ else {
32
+ maxLimit = PROVIDER_MAX_TOKENS.default;
33
+ }
34
+ // If no specific maxTokens requested, return the provider limit
35
+ if (!requestedMaxTokens) {
36
+ return maxLimit;
37
+ }
38
+ // If requested maxTokens exceeds the limit, use the limit and warn
39
+ if (requestedMaxTokens > maxLimit) {
40
+ logger.warn(`Requested maxTokens ${requestedMaxTokens} exceeds ${provider}/${model} limit of ${maxLimit}. Using ${maxLimit} instead.`);
41
+ return maxLimit;
42
+ }
43
+ // Use the requested value if it's within limits
44
+ return requestedMaxTokens;
45
+ }
46
+ /**
47
+ * Validate if maxTokens is safe for a provider/model combination
48
+ */
49
+ export function validateMaxTokens(provider, model, maxTokens) {
50
+ const safeMaxTokens = getSafeMaxTokens(provider, model, maxTokens);
51
+ if (!maxTokens) {
52
+ return {
53
+ isValid: true,
54
+ recommendedMaxTokens: safeMaxTokens,
55
+ };
56
+ }
57
+ const isValid = maxTokens <= safeMaxTokens;
58
+ return {
59
+ isValid,
60
+ recommendedMaxTokens: safeMaxTokens,
61
+ warning: !isValid
62
+ ? `maxTokens ${maxTokens} exceeds ${provider}/${model} limit of ${safeMaxTokens}`
63
+ : undefined,
64
+ };
65
+ }
66
+ /**
67
+ * Get provider-specific token limit recommendations
68
+ */
69
+ export function getTokenLimitRecommendations(provider) {
70
+ const providerLimits = PROVIDER_MAX_TOKENS[provider];
71
+ if (!providerLimits || typeof providerLimits === "number") {
72
+ const limit = typeof providerLimits === "number"
73
+ ? providerLimits
74
+ : PROVIDER_MAX_TOKENS.default;
75
+ return {
76
+ conservative: Math.floor(limit * 0.5),
77
+ balanced: Math.floor(limit * 0.75),
78
+ maximum: limit,
79
+ models: {},
80
+ };
81
+ }
82
+ const modelLimits = Object.entries(providerLimits)
83
+ .filter(([key]) => key !== "default")
84
+ .map(([_, limit]) => limit);
85
+ const maxLimit = Math.max(...modelLimits, providerLimits.default || 0);
86
+ const minLimit = Math.min(...modelLimits, providerLimits.default || maxLimit);
87
+ return {
88
+ conservative: Math.floor(minLimit * 0.5),
89
+ balanced: Math.floor(((minLimit + maxLimit) / 2) * 0.75),
90
+ maximum: maxLimit,
91
+ models: Object.fromEntries(Object.entries(providerLimits).filter(([key]) => key !== "default")),
92
+ };
93
+ }
94
+ /**
95
+ * Get all provider limits summary
96
+ */
97
+ export function getAllProviderLimits() {
98
+ const result = {};
99
+ for (const [provider, limits] of Object.entries(PROVIDER_MAX_TOKENS)) {
100
+ if (provider === "default") {
101
+ continue;
102
+ }
103
+ if (typeof limits === "number") {
104
+ result[provider] = {
105
+ default: limits,
106
+ models: {},
107
+ };
108
+ }
109
+ else {
110
+ const { default: defaultLimit, ...models } = limits;
111
+ result[provider] = {
112
+ default: defaultLimit || PROVIDER_MAX_TOKENS.default,
113
+ models: models,
114
+ };
115
+ }
116
+ }
117
+ return result;
118
+ }
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * NeuroLink MCP Server Factory
3
3
  * Factory-First Architecture: MCP servers create tools for internal orchestration
4
- * Compatible with Lighthouse MCP patterns for seamless migration
4
+ * Compatible with MCP patterns for seamless integration
5
5
  */
6
6
  import { z } from "zod";
7
7
  import type { ExecutionContext } from "./contracts/mcpContract.js";
@@ -11,7 +11,7 @@ import type { ExecutionContext } from "./contracts/mcpContract.js";
11
11
  export type MCPServerCategory = "aiProviders" | "frameworks" | "development" | "business" | "content" | "data" | "integrations" | "automation" | "analysis" | "custom";
12
12
  /**
13
13
  * Tool execution context - Rich context passed to every tool execution
14
- * Following Lighthouse's pattern for rich tool context
14
+ * Following standard patterns for rich tool context
15
15
  * Extends ExecutionContext for compatibility
16
16
  */
17
17
  export interface NeuroLinkExecutionContext extends ExecutionContext {
@@ -71,7 +71,7 @@ export interface ToolResult {
71
71
  };
72
72
  }
73
73
  /**
74
- * MCP Tool Interface - Lighthouse compatible with NeuroLink enhancements
74
+ * MCP Tool Interface - Standard compatible with NeuroLink enhancements
75
75
  */
76
76
  export interface NeuroLinkMCPTool {
77
77
  name: string;
@@ -86,7 +86,7 @@ export interface NeuroLinkMCPTool {
86
86
  metadata?: Record<string, unknown>;
87
87
  }
88
88
  /**
89
- * MCP Server Interface - Lighthouse compatible
89
+ * MCP Server Interface - Standard compatible
90
90
  */
91
91
  export interface NeuroLinkMCPServer {
92
92
  id: string;
@@ -118,7 +118,7 @@ export interface MCPServerConfig {
118
118
  /**
119
119
  * Create MCP Server Factory Function
120
120
  *
121
- * Core factory function for creating Lighthouse-compatible MCP servers.
121
+ * Core factory function for creating MCP servers.
122
122
  * Follows Factory-First architecture where tools are internal implementation.
123
123
  *
124
124
  * @param config Server configuration with minimal required fields
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * NeuroLink MCP Server Factory
3
3
  * Factory-First Architecture: MCP servers create tools for internal orchestration
4
- * Compatible with Lighthouse MCP patterns for seamless migration
4
+ * Compatible with MCP patterns for seamless integration
5
5
  */
6
6
  import { z } from "zod";
7
7
  /**
@@ -34,7 +34,7 @@ const ServerConfigSchema = z.object({
34
34
  /**
35
35
  * Create MCP Server Factory Function
36
36
  *
37
- * Core factory function for creating Lighthouse-compatible MCP servers.
37
+ * Core factory function for creating MCP servers.
38
38
  * Follows Factory-First architecture where tools are internal implementation.
39
39
  *
40
40
  * @param config Server configuration with minimal required fields
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * NeuroLink Utility Server
3
- * Provides general utility tools following Lighthouse patterns
3
+ * Provides general utility tools following standard patterns
4
4
  */
5
5
  /**
6
6
  * Utility Server - General utility tools
@@ -1,6 +1,6 @@
1
1
  /**
2
2
  * NeuroLink Utility Server
3
- * Provides general utility tools following Lighthouse patterns
3
+ * Provides general utility tools following standard patterns
4
4
  */
5
5
  import { z } from "zod";
6
6
  import { createMCPServer } from "../../factory.js";
@@ -19,7 +19,7 @@ export class MCPToolRegistry extends MCPRegistry {
19
19
  * Register all direct tools from directAgentTools
20
20
  */
21
21
  registerDirectTools() {
22
- registryLogger.info("Auto-registering direct tools...");
22
+ registryLogger.debug("Auto-registering direct tools...");
23
23
  for (const [toolName, toolDef] of Object.entries(directAgentTools)) {
24
24
  const toolId = `direct.${toolName}`;
25
25
  const toolInfo = {
@@ -67,7 +67,7 @@ export class MCPToolRegistry extends MCPRegistry {
67
67
  });
68
68
  registryLogger.debug(`Registered direct tool: ${toolName} as ${toolId}`);
69
69
  }
70
- registryLogger.info(`Auto-registered ${Object.keys(directAgentTools).length} direct tools`);
70
+ registryLogger.debug(`Auto-registered ${Object.keys(directAgentTools).length} direct tools`);
71
71
  }
72
72
  /**
73
73
  * Register a server with its tools (updated signature)