@vasperacapital/vaspera-shared 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.
@@ -0,0 +1,341 @@
1
+ "use strict";
2
+ var __defProp = Object.defineProperty;
3
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
4
+ var __getOwnPropNames = Object.getOwnPropertyNames;
5
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
6
+ var __export = (target, all) => {
7
+ for (var name in all)
8
+ __defProp(target, name, { get: all[name], enumerable: true });
9
+ };
10
+ var __copyProps = (to, from, except, desc) => {
11
+ if (from && typeof from === "object" || typeof from === "function") {
12
+ for (let key of __getOwnPropNames(from))
13
+ if (!__hasOwnProp.call(to, key) && key !== except)
14
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
15
+ }
16
+ return to;
17
+ };
18
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
19
+
20
+ // src/errors/index.ts
21
+ var errors_exports = {};
22
+ __export(errors_exports, {
23
+ ErrorCodes: () => ErrorCodes,
24
+ Errors: () => Errors,
25
+ VasperaApiError: () => VasperaApiError,
26
+ createError: () => createError,
27
+ createErrorResponse: () => createErrorResponse
28
+ });
29
+ module.exports = __toCommonJS(errors_exports);
30
+
31
+ // src/errors/codes.ts
32
+ var ErrorCodes = {
33
+ // Authentication Errors (VPM-AUTH-XXX)
34
+ AUTH: {
35
+ REQUIRED: {
36
+ code: "VPM-AUTH-001",
37
+ message: "Authentication required",
38
+ httpStatus: 401
39
+ },
40
+ INVALID_TOKEN: {
41
+ code: "VPM-AUTH-002",
42
+ message: "Invalid or expired authentication token",
43
+ httpStatus: 401
44
+ },
45
+ INSUFFICIENT_PERMISSIONS: {
46
+ code: "VPM-AUTH-003",
47
+ message: "Insufficient permissions for this action",
48
+ httpStatus: 403
49
+ },
50
+ SESSION_EXPIRED: {
51
+ code: "VPM-AUTH-004",
52
+ message: "Session has expired, please login again",
53
+ httpStatus: 401
54
+ },
55
+ MFA_REQUIRED: {
56
+ code: "VPM-AUTH-005",
57
+ message: "Multi-factor authentication required",
58
+ httpStatus: 403
59
+ }
60
+ },
61
+ // API Key Errors (VPM-API-KEY-XXX)
62
+ API_KEY: {
63
+ REQUIRED: {
64
+ code: "VPM-API-KEY-001",
65
+ message: "API key is required",
66
+ httpStatus: 401
67
+ },
68
+ INVALID: {
69
+ code: "VPM-API-KEY-002",
70
+ message: "Invalid API key",
71
+ httpStatus: 401
72
+ },
73
+ REVOKED: {
74
+ code: "VPM-API-KEY-003",
75
+ message: "API key has been revoked",
76
+ httpStatus: 401
77
+ },
78
+ EXPIRED: {
79
+ code: "VPM-API-KEY-004",
80
+ message: "API key has expired",
81
+ httpStatus: 401
82
+ },
83
+ RATE_LIMITED: {
84
+ code: "VPM-API-KEY-005",
85
+ message: "API key rate limit exceeded",
86
+ httpStatus: 429
87
+ },
88
+ QUOTA_EXCEEDED: {
89
+ code: "VPM-API-KEY-006",
90
+ message: "Monthly usage quota exceeded",
91
+ httpStatus: 429
92
+ }
93
+ },
94
+ // MCP Tool Errors (VPM-MCP-XXX)
95
+ MCP: {
96
+ TOOL_NOT_FOUND: {
97
+ code: "VPM-MCP-001",
98
+ message: "Requested tool not found",
99
+ httpStatus: 404
100
+ },
101
+ INVALID_ARGUMENTS: {
102
+ code: "VPM-MCP-002",
103
+ message: "Invalid tool arguments provided",
104
+ httpStatus: 400
105
+ },
106
+ EXECUTION_FAILED: {
107
+ code: "VPM-MCP-003",
108
+ message: "Tool execution failed",
109
+ httpStatus: 500
110
+ },
111
+ TIMEOUT: {
112
+ code: "VPM-MCP-004",
113
+ message: "Tool execution timed out",
114
+ httpStatus: 504
115
+ },
116
+ LLM_ERROR: {
117
+ code: "VPM-MCP-005",
118
+ message: "AI model returned an error",
119
+ httpStatus: 502
120
+ },
121
+ CONTEXT_TOO_LARGE: {
122
+ code: "VPM-MCP-006",
123
+ message: "Input context exceeds maximum size",
124
+ httpStatus: 413
125
+ }
126
+ },
127
+ // Billing Errors (VPM-BILLING-XXX)
128
+ BILLING: {
129
+ NO_SUBSCRIPTION: {
130
+ code: "VPM-BILLING-001",
131
+ message: "No active subscription found",
132
+ httpStatus: 402
133
+ },
134
+ SUBSCRIPTION_EXPIRED: {
135
+ code: "VPM-BILLING-002",
136
+ message: "Subscription has expired",
137
+ httpStatus: 402
138
+ },
139
+ PAYMENT_FAILED: {
140
+ code: "VPM-BILLING-003",
141
+ message: "Payment processing failed",
142
+ httpStatus: 402
143
+ },
144
+ FEATURE_NOT_INCLUDED: {
145
+ code: "VPM-BILLING-004",
146
+ message: "Feature not included in current plan",
147
+ httpStatus: 403
148
+ },
149
+ UPGRADE_REQUIRED: {
150
+ code: "VPM-BILLING-005",
151
+ message: "Plan upgrade required for this action",
152
+ httpStatus: 403
153
+ }
154
+ },
155
+ // Integration Errors (VPM-INT-XXX)
156
+ INTEGRATION: {
157
+ NOT_CONNECTED: {
158
+ code: "VPM-INT-001",
159
+ message: "Integration not connected",
160
+ httpStatus: 400
161
+ },
162
+ TOKEN_EXPIRED: {
163
+ code: "VPM-INT-002",
164
+ message: "Integration token expired, reconnection required",
165
+ httpStatus: 401
166
+ },
167
+ REFRESH_FAILED: {
168
+ code: "VPM-INT-003",
169
+ message: "Failed to refresh integration token",
170
+ httpStatus: 502
171
+ },
172
+ API_ERROR: {
173
+ code: "VPM-INT-004",
174
+ message: "External integration API error",
175
+ httpStatus: 502
176
+ },
177
+ RATE_LIMITED: {
178
+ code: "VPM-INT-005",
179
+ message: "Integration rate limit exceeded",
180
+ httpStatus: 429
181
+ }
182
+ },
183
+ // Validation Errors (VPM-VAL-XXX)
184
+ VALIDATION: {
185
+ REQUIRED_FIELD: {
186
+ code: "VPM-VAL-001",
187
+ message: "Required field missing",
188
+ httpStatus: 400
189
+ },
190
+ INVALID_FORMAT: {
191
+ code: "VPM-VAL-002",
192
+ message: "Invalid field format",
193
+ httpStatus: 400
194
+ },
195
+ OUT_OF_RANGE: {
196
+ code: "VPM-VAL-003",
197
+ message: "Value out of allowed range",
198
+ httpStatus: 400
199
+ },
200
+ INVALID_JSON: {
201
+ code: "VPM-VAL-004",
202
+ message: "Invalid JSON in request body",
203
+ httpStatus: 400
204
+ }
205
+ },
206
+ // System Errors (VPM-SYS-XXX)
207
+ SYSTEM: {
208
+ INTERNAL_ERROR: {
209
+ code: "VPM-SYS-001",
210
+ message: "Internal server error",
211
+ httpStatus: 500
212
+ },
213
+ DATABASE_ERROR: {
214
+ code: "VPM-SYS-002",
215
+ message: "Database operation failed",
216
+ httpStatus: 500
217
+ },
218
+ SERVICE_UNAVAILABLE: {
219
+ code: "VPM-SYS-003",
220
+ message: "Service temporarily unavailable",
221
+ httpStatus: 503
222
+ },
223
+ MAINTENANCE_MODE: {
224
+ code: "VPM-SYS-004",
225
+ message: "System is under maintenance",
226
+ httpStatus: 503
227
+ }
228
+ }
229
+ };
230
+
231
+ // src/errors/factory.ts
232
+ function generateRequestId() {
233
+ return `req_${Date.now().toString(36)}_${Math.random().toString(36).slice(2, 9)}`;
234
+ }
235
+ function createError(errorDef, details, requestId) {
236
+ return {
237
+ code: errorDef.code,
238
+ message: errorDef.message,
239
+ details,
240
+ timestamp: (/* @__PURE__ */ new Date()).toISOString(),
241
+ requestId: requestId || generateRequestId(),
242
+ docUrl: `https://docs.vaspera.pm/errors/${errorDef.code}`
243
+ };
244
+ }
245
+ function createErrorResponse(errorDef, details, requestId) {
246
+ return {
247
+ response: {
248
+ success: false,
249
+ error: createError(errorDef, details, requestId)
250
+ },
251
+ status: errorDef.httpStatus
252
+ };
253
+ }
254
+ function getNextResetDate() {
255
+ const now = /* @__PURE__ */ new Date();
256
+ const nextMonth = new Date(now.getFullYear(), now.getMonth() + 1, 1);
257
+ return nextMonth.toISOString();
258
+ }
259
+ var Errors = {
260
+ authRequired: (requestId) => createErrorResponse(ErrorCodes.AUTH.REQUIRED, void 0, requestId),
261
+ invalidApiKey: (requestId) => createErrorResponse(ErrorCodes.API_KEY.INVALID, void 0, requestId),
262
+ apiKeyRevoked: (requestId) => createErrorResponse(ErrorCodes.API_KEY.REVOKED, void 0, requestId),
263
+ apiKeyExpired: (requestId) => createErrorResponse(ErrorCodes.API_KEY.EXPIRED, void 0, requestId),
264
+ rateLimited: (retryAfter, requestId) => createErrorResponse(
265
+ ErrorCodes.API_KEY.RATE_LIMITED,
266
+ { retryAfterSeconds: retryAfter },
267
+ requestId
268
+ ),
269
+ quotaExceeded: (currentUsage, limit, requestId) => createErrorResponse(
270
+ ErrorCodes.API_KEY.QUOTA_EXCEEDED,
271
+ { currentUsage, limit, resetDate: getNextResetDate() },
272
+ requestId
273
+ ),
274
+ toolNotFound: (toolName, requestId) => createErrorResponse(
275
+ ErrorCodes.MCP.TOOL_NOT_FOUND,
276
+ { tool: toolName },
277
+ requestId
278
+ ),
279
+ toolExecutionFailed: (toolName, reason, requestId) => createErrorResponse(
280
+ ErrorCodes.MCP.EXECUTION_FAILED,
281
+ { tool: toolName, reason },
282
+ requestId
283
+ ),
284
+ toolTimeout: (toolName, timeoutMs, requestId) => createErrorResponse(
285
+ ErrorCodes.MCP.TIMEOUT,
286
+ { tool: toolName, timeoutMs },
287
+ requestId
288
+ ),
289
+ validationFailed: (field, reason, requestId) => createErrorResponse(
290
+ ErrorCodes.VALIDATION.REQUIRED_FIELD,
291
+ { field, reason },
292
+ requestId
293
+ ),
294
+ invalidFormat: (field, expected, requestId) => createErrorResponse(
295
+ ErrorCodes.VALIDATION.INVALID_FORMAT,
296
+ { field, expected },
297
+ requestId
298
+ ),
299
+ internalError: (message, requestId) => createErrorResponse(
300
+ ErrorCodes.SYSTEM.INTERNAL_ERROR,
301
+ message ? { message } : void 0,
302
+ requestId
303
+ ),
304
+ databaseError: (operation, requestId) => createErrorResponse(
305
+ ErrorCodes.SYSTEM.DATABASE_ERROR,
306
+ { operation },
307
+ requestId
308
+ ),
309
+ integrationNotConnected: (provider, requestId) => createErrorResponse(
310
+ ErrorCodes.INTEGRATION.NOT_CONNECTED,
311
+ { provider },
312
+ requestId
313
+ ),
314
+ subscriptionRequired: (feature, requiredTier, requestId) => createErrorResponse(
315
+ ErrorCodes.BILLING.FEATURE_NOT_INCLUDED,
316
+ { feature, requiredTier },
317
+ requestId
318
+ )
319
+ };
320
+ var VasperaApiError = class extends Error {
321
+ errorDef;
322
+ details;
323
+ constructor(errorDef, details) {
324
+ super(errorDef.message);
325
+ this.name = "VasperaApiError";
326
+ this.errorDef = errorDef;
327
+ this.details = details;
328
+ }
329
+ toResponse(requestId) {
330
+ return createErrorResponse(this.errorDef, this.details, requestId);
331
+ }
332
+ };
333
+ // Annotate the CommonJS export names for ESM import in node:
334
+ 0 && (module.exports = {
335
+ ErrorCodes,
336
+ Errors,
337
+ VasperaApiError,
338
+ createError,
339
+ createErrorResponse
340
+ });
341
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"sources":["../../src/errors/index.ts","../../src/errors/codes.ts","../../src/errors/factory.ts"],"sourcesContent":["export { ErrorCodes } from './codes.js';\nexport type { ErrorDefinition, ErrorCodeType } from './codes.js';\n\nexport {\n createError,\n createErrorResponse,\n Errors,\n VasperaApiError,\n} from './factory.js';\nexport type { VasperaError, ErrorResponse } from './factory.js';\n","export interface ErrorDefinition {\n code: string;\n message: string;\n httpStatus: number;\n}\n\nexport const ErrorCodes = {\n // Authentication Errors (VPM-AUTH-XXX)\n AUTH: {\n REQUIRED: {\n code: 'VPM-AUTH-001',\n message: 'Authentication required',\n httpStatus: 401,\n },\n INVALID_TOKEN: {\n code: 'VPM-AUTH-002',\n message: 'Invalid or expired authentication token',\n httpStatus: 401,\n },\n INSUFFICIENT_PERMISSIONS: {\n code: 'VPM-AUTH-003',\n message: 'Insufficient permissions for this action',\n httpStatus: 403,\n },\n SESSION_EXPIRED: {\n code: 'VPM-AUTH-004',\n message: 'Session has expired, please login again',\n httpStatus: 401,\n },\n MFA_REQUIRED: {\n code: 'VPM-AUTH-005',\n message: 'Multi-factor authentication required',\n httpStatus: 403,\n },\n },\n\n // API Key Errors (VPM-API-KEY-XXX)\n API_KEY: {\n REQUIRED: {\n code: 'VPM-API-KEY-001',\n message: 'API key is required',\n httpStatus: 401,\n },\n INVALID: {\n code: 'VPM-API-KEY-002',\n message: 'Invalid API key',\n httpStatus: 401,\n },\n REVOKED: {\n code: 'VPM-API-KEY-003',\n message: 'API key has been revoked',\n httpStatus: 401,\n },\n EXPIRED: {\n code: 'VPM-API-KEY-004',\n message: 'API key has expired',\n httpStatus: 401,\n },\n RATE_LIMITED: {\n code: 'VPM-API-KEY-005',\n message: 'API key rate limit exceeded',\n httpStatus: 429,\n },\n QUOTA_EXCEEDED: {\n code: 'VPM-API-KEY-006',\n message: 'Monthly usage quota exceeded',\n httpStatus: 429,\n },\n },\n\n // MCP Tool Errors (VPM-MCP-XXX)\n MCP: {\n TOOL_NOT_FOUND: {\n code: 'VPM-MCP-001',\n message: 'Requested tool not found',\n httpStatus: 404,\n },\n INVALID_ARGUMENTS: {\n code: 'VPM-MCP-002',\n message: 'Invalid tool arguments provided',\n httpStatus: 400,\n },\n EXECUTION_FAILED: {\n code: 'VPM-MCP-003',\n message: 'Tool execution failed',\n httpStatus: 500,\n },\n TIMEOUT: {\n code: 'VPM-MCP-004',\n message: 'Tool execution timed out',\n httpStatus: 504,\n },\n LLM_ERROR: {\n code: 'VPM-MCP-005',\n message: 'AI model returned an error',\n httpStatus: 502,\n },\n CONTEXT_TOO_LARGE: {\n code: 'VPM-MCP-006',\n message: 'Input context exceeds maximum size',\n httpStatus: 413,\n },\n },\n\n // Billing Errors (VPM-BILLING-XXX)\n BILLING: {\n NO_SUBSCRIPTION: {\n code: 'VPM-BILLING-001',\n message: 'No active subscription found',\n httpStatus: 402,\n },\n SUBSCRIPTION_EXPIRED: {\n code: 'VPM-BILLING-002',\n message: 'Subscription has expired',\n httpStatus: 402,\n },\n PAYMENT_FAILED: {\n code: 'VPM-BILLING-003',\n message: 'Payment processing failed',\n httpStatus: 402,\n },\n FEATURE_NOT_INCLUDED: {\n code: 'VPM-BILLING-004',\n message: 'Feature not included in current plan',\n httpStatus: 403,\n },\n UPGRADE_REQUIRED: {\n code: 'VPM-BILLING-005',\n message: 'Plan upgrade required for this action',\n httpStatus: 403,\n },\n },\n\n // Integration Errors (VPM-INT-XXX)\n INTEGRATION: {\n NOT_CONNECTED: {\n code: 'VPM-INT-001',\n message: 'Integration not connected',\n httpStatus: 400,\n },\n TOKEN_EXPIRED: {\n code: 'VPM-INT-002',\n message: 'Integration token expired, reconnection required',\n httpStatus: 401,\n },\n REFRESH_FAILED: {\n code: 'VPM-INT-003',\n message: 'Failed to refresh integration token',\n httpStatus: 502,\n },\n API_ERROR: {\n code: 'VPM-INT-004',\n message: 'External integration API error',\n httpStatus: 502,\n },\n RATE_LIMITED: {\n code: 'VPM-INT-005',\n message: 'Integration rate limit exceeded',\n httpStatus: 429,\n },\n },\n\n // Validation Errors (VPM-VAL-XXX)\n VALIDATION: {\n REQUIRED_FIELD: {\n code: 'VPM-VAL-001',\n message: 'Required field missing',\n httpStatus: 400,\n },\n INVALID_FORMAT: {\n code: 'VPM-VAL-002',\n message: 'Invalid field format',\n httpStatus: 400,\n },\n OUT_OF_RANGE: {\n code: 'VPM-VAL-003',\n message: 'Value out of allowed range',\n httpStatus: 400,\n },\n INVALID_JSON: {\n code: 'VPM-VAL-004',\n message: 'Invalid JSON in request body',\n httpStatus: 400,\n },\n },\n\n // System Errors (VPM-SYS-XXX)\n SYSTEM: {\n INTERNAL_ERROR: {\n code: 'VPM-SYS-001',\n message: 'Internal server error',\n httpStatus: 500,\n },\n DATABASE_ERROR: {\n code: 'VPM-SYS-002',\n message: 'Database operation failed',\n httpStatus: 500,\n },\n SERVICE_UNAVAILABLE: {\n code: 'VPM-SYS-003',\n message: 'Service temporarily unavailable',\n httpStatus: 503,\n },\n MAINTENANCE_MODE: {\n code: 'VPM-SYS-004',\n message: 'System is under maintenance',\n httpStatus: 503,\n },\n },\n} as const;\n\nexport type ErrorCodeType =\n (typeof ErrorCodes)[keyof typeof ErrorCodes][keyof (typeof ErrorCodes)[keyof typeof ErrorCodes]];\n","import type { ErrorDefinition } from './codes.js';\nimport { ErrorCodes } from './codes.js';\n\nexport interface VasperaError {\n code: string;\n message: string;\n details?: Record<string, unknown>;\n timestamp: string;\n requestId: string;\n docUrl?: string;\n}\n\nexport interface ErrorResponse {\n success: false;\n error: VasperaError;\n}\n\nfunction generateRequestId(): string {\n return `req_${Date.now().toString(36)}_${Math.random().toString(36).slice(2, 9)}`;\n}\n\nexport function createError(\n errorDef: ErrorDefinition,\n details?: Record<string, unknown>,\n requestId?: string\n): VasperaError {\n return {\n code: errorDef.code,\n message: errorDef.message,\n details,\n timestamp: new Date().toISOString(),\n requestId: requestId || generateRequestId(),\n docUrl: `https://docs.vaspera.pm/errors/${errorDef.code}`,\n };\n}\n\nexport function createErrorResponse(\n errorDef: ErrorDefinition,\n details?: Record<string, unknown>,\n requestId?: string\n): { response: ErrorResponse; status: number } {\n return {\n response: {\n success: false,\n error: createError(errorDef, details, requestId),\n },\n status: errorDef.httpStatus,\n };\n}\n\nfunction getNextResetDate(): string {\n const now = new Date();\n const nextMonth = new Date(now.getFullYear(), now.getMonth() + 1, 1);\n return nextMonth.toISOString();\n}\n\n// Pre-built error creators for common cases\nexport const Errors = {\n authRequired: (requestId?: string) =>\n createErrorResponse(ErrorCodes.AUTH.REQUIRED, undefined, requestId),\n\n invalidApiKey: (requestId?: string) =>\n createErrorResponse(ErrorCodes.API_KEY.INVALID, undefined, requestId),\n\n apiKeyRevoked: (requestId?: string) =>\n createErrorResponse(ErrorCodes.API_KEY.REVOKED, undefined, requestId),\n\n apiKeyExpired: (requestId?: string) =>\n createErrorResponse(ErrorCodes.API_KEY.EXPIRED, undefined, requestId),\n\n rateLimited: (retryAfter: number, requestId?: string) =>\n createErrorResponse(\n ErrorCodes.API_KEY.RATE_LIMITED,\n { retryAfterSeconds: retryAfter },\n requestId\n ),\n\n quotaExceeded: (currentUsage: number, limit: number, requestId?: string) =>\n createErrorResponse(\n ErrorCodes.API_KEY.QUOTA_EXCEEDED,\n { currentUsage, limit, resetDate: getNextResetDate() },\n requestId\n ),\n\n toolNotFound: (toolName: string, requestId?: string) =>\n createErrorResponse(\n ErrorCodes.MCP.TOOL_NOT_FOUND,\n { tool: toolName },\n requestId\n ),\n\n toolExecutionFailed: (toolName: string, reason: string, requestId?: string) =>\n createErrorResponse(\n ErrorCodes.MCP.EXECUTION_FAILED,\n { tool: toolName, reason },\n requestId\n ),\n\n toolTimeout: (toolName: string, timeoutMs: number, requestId?: string) =>\n createErrorResponse(\n ErrorCodes.MCP.TIMEOUT,\n { tool: toolName, timeoutMs },\n requestId\n ),\n\n validationFailed: (field: string, reason: string, requestId?: string) =>\n createErrorResponse(\n ErrorCodes.VALIDATION.REQUIRED_FIELD,\n { field, reason },\n requestId\n ),\n\n invalidFormat: (field: string, expected: string, requestId?: string) =>\n createErrorResponse(\n ErrorCodes.VALIDATION.INVALID_FORMAT,\n { field, expected },\n requestId\n ),\n\n internalError: (message?: string, requestId?: string) =>\n createErrorResponse(\n ErrorCodes.SYSTEM.INTERNAL_ERROR,\n message ? { message } : undefined,\n requestId\n ),\n\n databaseError: (operation: string, requestId?: string) =>\n createErrorResponse(\n ErrorCodes.SYSTEM.DATABASE_ERROR,\n { operation },\n requestId\n ),\n\n integrationNotConnected: (provider: string, requestId?: string) =>\n createErrorResponse(\n ErrorCodes.INTEGRATION.NOT_CONNECTED,\n { provider },\n requestId\n ),\n\n subscriptionRequired: (feature: string, requiredTier: string, requestId?: string) =>\n createErrorResponse(\n ErrorCodes.BILLING.FEATURE_NOT_INCLUDED,\n { feature, requiredTier },\n requestId\n ),\n};\n\n// Custom error class for throwing in API routes\nexport class VasperaApiError extends Error {\n public readonly errorDef: ErrorDefinition;\n public readonly details?: Record<string, unknown>;\n\n constructor(errorDef: ErrorDefinition, details?: Record<string, unknown>) {\n super(errorDef.message);\n this.name = 'VasperaApiError';\n this.errorDef = errorDef;\n this.details = details;\n }\n\n toResponse(requestId?: string): { response: ErrorResponse; status: number } {\n return createErrorResponse(this.errorDef, this.details, requestId);\n }\n}\n"],"mappings":"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","names":[]}
@@ -0,0 +1,310 @@
1
+ // src/errors/codes.ts
2
+ var ErrorCodes = {
3
+ // Authentication Errors (VPM-AUTH-XXX)
4
+ AUTH: {
5
+ REQUIRED: {
6
+ code: "VPM-AUTH-001",
7
+ message: "Authentication required",
8
+ httpStatus: 401
9
+ },
10
+ INVALID_TOKEN: {
11
+ code: "VPM-AUTH-002",
12
+ message: "Invalid or expired authentication token",
13
+ httpStatus: 401
14
+ },
15
+ INSUFFICIENT_PERMISSIONS: {
16
+ code: "VPM-AUTH-003",
17
+ message: "Insufficient permissions for this action",
18
+ httpStatus: 403
19
+ },
20
+ SESSION_EXPIRED: {
21
+ code: "VPM-AUTH-004",
22
+ message: "Session has expired, please login again",
23
+ httpStatus: 401
24
+ },
25
+ MFA_REQUIRED: {
26
+ code: "VPM-AUTH-005",
27
+ message: "Multi-factor authentication required",
28
+ httpStatus: 403
29
+ }
30
+ },
31
+ // API Key Errors (VPM-API-KEY-XXX)
32
+ API_KEY: {
33
+ REQUIRED: {
34
+ code: "VPM-API-KEY-001",
35
+ message: "API key is required",
36
+ httpStatus: 401
37
+ },
38
+ INVALID: {
39
+ code: "VPM-API-KEY-002",
40
+ message: "Invalid API key",
41
+ httpStatus: 401
42
+ },
43
+ REVOKED: {
44
+ code: "VPM-API-KEY-003",
45
+ message: "API key has been revoked",
46
+ httpStatus: 401
47
+ },
48
+ EXPIRED: {
49
+ code: "VPM-API-KEY-004",
50
+ message: "API key has expired",
51
+ httpStatus: 401
52
+ },
53
+ RATE_LIMITED: {
54
+ code: "VPM-API-KEY-005",
55
+ message: "API key rate limit exceeded",
56
+ httpStatus: 429
57
+ },
58
+ QUOTA_EXCEEDED: {
59
+ code: "VPM-API-KEY-006",
60
+ message: "Monthly usage quota exceeded",
61
+ httpStatus: 429
62
+ }
63
+ },
64
+ // MCP Tool Errors (VPM-MCP-XXX)
65
+ MCP: {
66
+ TOOL_NOT_FOUND: {
67
+ code: "VPM-MCP-001",
68
+ message: "Requested tool not found",
69
+ httpStatus: 404
70
+ },
71
+ INVALID_ARGUMENTS: {
72
+ code: "VPM-MCP-002",
73
+ message: "Invalid tool arguments provided",
74
+ httpStatus: 400
75
+ },
76
+ EXECUTION_FAILED: {
77
+ code: "VPM-MCP-003",
78
+ message: "Tool execution failed",
79
+ httpStatus: 500
80
+ },
81
+ TIMEOUT: {
82
+ code: "VPM-MCP-004",
83
+ message: "Tool execution timed out",
84
+ httpStatus: 504
85
+ },
86
+ LLM_ERROR: {
87
+ code: "VPM-MCP-005",
88
+ message: "AI model returned an error",
89
+ httpStatus: 502
90
+ },
91
+ CONTEXT_TOO_LARGE: {
92
+ code: "VPM-MCP-006",
93
+ message: "Input context exceeds maximum size",
94
+ httpStatus: 413
95
+ }
96
+ },
97
+ // Billing Errors (VPM-BILLING-XXX)
98
+ BILLING: {
99
+ NO_SUBSCRIPTION: {
100
+ code: "VPM-BILLING-001",
101
+ message: "No active subscription found",
102
+ httpStatus: 402
103
+ },
104
+ SUBSCRIPTION_EXPIRED: {
105
+ code: "VPM-BILLING-002",
106
+ message: "Subscription has expired",
107
+ httpStatus: 402
108
+ },
109
+ PAYMENT_FAILED: {
110
+ code: "VPM-BILLING-003",
111
+ message: "Payment processing failed",
112
+ httpStatus: 402
113
+ },
114
+ FEATURE_NOT_INCLUDED: {
115
+ code: "VPM-BILLING-004",
116
+ message: "Feature not included in current plan",
117
+ httpStatus: 403
118
+ },
119
+ UPGRADE_REQUIRED: {
120
+ code: "VPM-BILLING-005",
121
+ message: "Plan upgrade required for this action",
122
+ httpStatus: 403
123
+ }
124
+ },
125
+ // Integration Errors (VPM-INT-XXX)
126
+ INTEGRATION: {
127
+ NOT_CONNECTED: {
128
+ code: "VPM-INT-001",
129
+ message: "Integration not connected",
130
+ httpStatus: 400
131
+ },
132
+ TOKEN_EXPIRED: {
133
+ code: "VPM-INT-002",
134
+ message: "Integration token expired, reconnection required",
135
+ httpStatus: 401
136
+ },
137
+ REFRESH_FAILED: {
138
+ code: "VPM-INT-003",
139
+ message: "Failed to refresh integration token",
140
+ httpStatus: 502
141
+ },
142
+ API_ERROR: {
143
+ code: "VPM-INT-004",
144
+ message: "External integration API error",
145
+ httpStatus: 502
146
+ },
147
+ RATE_LIMITED: {
148
+ code: "VPM-INT-005",
149
+ message: "Integration rate limit exceeded",
150
+ httpStatus: 429
151
+ }
152
+ },
153
+ // Validation Errors (VPM-VAL-XXX)
154
+ VALIDATION: {
155
+ REQUIRED_FIELD: {
156
+ code: "VPM-VAL-001",
157
+ message: "Required field missing",
158
+ httpStatus: 400
159
+ },
160
+ INVALID_FORMAT: {
161
+ code: "VPM-VAL-002",
162
+ message: "Invalid field format",
163
+ httpStatus: 400
164
+ },
165
+ OUT_OF_RANGE: {
166
+ code: "VPM-VAL-003",
167
+ message: "Value out of allowed range",
168
+ httpStatus: 400
169
+ },
170
+ INVALID_JSON: {
171
+ code: "VPM-VAL-004",
172
+ message: "Invalid JSON in request body",
173
+ httpStatus: 400
174
+ }
175
+ },
176
+ // System Errors (VPM-SYS-XXX)
177
+ SYSTEM: {
178
+ INTERNAL_ERROR: {
179
+ code: "VPM-SYS-001",
180
+ message: "Internal server error",
181
+ httpStatus: 500
182
+ },
183
+ DATABASE_ERROR: {
184
+ code: "VPM-SYS-002",
185
+ message: "Database operation failed",
186
+ httpStatus: 500
187
+ },
188
+ SERVICE_UNAVAILABLE: {
189
+ code: "VPM-SYS-003",
190
+ message: "Service temporarily unavailable",
191
+ httpStatus: 503
192
+ },
193
+ MAINTENANCE_MODE: {
194
+ code: "VPM-SYS-004",
195
+ message: "System is under maintenance",
196
+ httpStatus: 503
197
+ }
198
+ }
199
+ };
200
+
201
+ // src/errors/factory.ts
202
+ function generateRequestId() {
203
+ return `req_${Date.now().toString(36)}_${Math.random().toString(36).slice(2, 9)}`;
204
+ }
205
+ function createError(errorDef, details, requestId) {
206
+ return {
207
+ code: errorDef.code,
208
+ message: errorDef.message,
209
+ details,
210
+ timestamp: (/* @__PURE__ */ new Date()).toISOString(),
211
+ requestId: requestId || generateRequestId(),
212
+ docUrl: `https://docs.vaspera.pm/errors/${errorDef.code}`
213
+ };
214
+ }
215
+ function createErrorResponse(errorDef, details, requestId) {
216
+ return {
217
+ response: {
218
+ success: false,
219
+ error: createError(errorDef, details, requestId)
220
+ },
221
+ status: errorDef.httpStatus
222
+ };
223
+ }
224
+ function getNextResetDate() {
225
+ const now = /* @__PURE__ */ new Date();
226
+ const nextMonth = new Date(now.getFullYear(), now.getMonth() + 1, 1);
227
+ return nextMonth.toISOString();
228
+ }
229
+ var Errors = {
230
+ authRequired: (requestId) => createErrorResponse(ErrorCodes.AUTH.REQUIRED, void 0, requestId),
231
+ invalidApiKey: (requestId) => createErrorResponse(ErrorCodes.API_KEY.INVALID, void 0, requestId),
232
+ apiKeyRevoked: (requestId) => createErrorResponse(ErrorCodes.API_KEY.REVOKED, void 0, requestId),
233
+ apiKeyExpired: (requestId) => createErrorResponse(ErrorCodes.API_KEY.EXPIRED, void 0, requestId),
234
+ rateLimited: (retryAfter, requestId) => createErrorResponse(
235
+ ErrorCodes.API_KEY.RATE_LIMITED,
236
+ { retryAfterSeconds: retryAfter },
237
+ requestId
238
+ ),
239
+ quotaExceeded: (currentUsage, limit, requestId) => createErrorResponse(
240
+ ErrorCodes.API_KEY.QUOTA_EXCEEDED,
241
+ { currentUsage, limit, resetDate: getNextResetDate() },
242
+ requestId
243
+ ),
244
+ toolNotFound: (toolName, requestId) => createErrorResponse(
245
+ ErrorCodes.MCP.TOOL_NOT_FOUND,
246
+ { tool: toolName },
247
+ requestId
248
+ ),
249
+ toolExecutionFailed: (toolName, reason, requestId) => createErrorResponse(
250
+ ErrorCodes.MCP.EXECUTION_FAILED,
251
+ { tool: toolName, reason },
252
+ requestId
253
+ ),
254
+ toolTimeout: (toolName, timeoutMs, requestId) => createErrorResponse(
255
+ ErrorCodes.MCP.TIMEOUT,
256
+ { tool: toolName, timeoutMs },
257
+ requestId
258
+ ),
259
+ validationFailed: (field, reason, requestId) => createErrorResponse(
260
+ ErrorCodes.VALIDATION.REQUIRED_FIELD,
261
+ { field, reason },
262
+ requestId
263
+ ),
264
+ invalidFormat: (field, expected, requestId) => createErrorResponse(
265
+ ErrorCodes.VALIDATION.INVALID_FORMAT,
266
+ { field, expected },
267
+ requestId
268
+ ),
269
+ internalError: (message, requestId) => createErrorResponse(
270
+ ErrorCodes.SYSTEM.INTERNAL_ERROR,
271
+ message ? { message } : void 0,
272
+ requestId
273
+ ),
274
+ databaseError: (operation, requestId) => createErrorResponse(
275
+ ErrorCodes.SYSTEM.DATABASE_ERROR,
276
+ { operation },
277
+ requestId
278
+ ),
279
+ integrationNotConnected: (provider, requestId) => createErrorResponse(
280
+ ErrorCodes.INTEGRATION.NOT_CONNECTED,
281
+ { provider },
282
+ requestId
283
+ ),
284
+ subscriptionRequired: (feature, requiredTier, requestId) => createErrorResponse(
285
+ ErrorCodes.BILLING.FEATURE_NOT_INCLUDED,
286
+ { feature, requiredTier },
287
+ requestId
288
+ )
289
+ };
290
+ var VasperaApiError = class extends Error {
291
+ errorDef;
292
+ details;
293
+ constructor(errorDef, details) {
294
+ super(errorDef.message);
295
+ this.name = "VasperaApiError";
296
+ this.errorDef = errorDef;
297
+ this.details = details;
298
+ }
299
+ toResponse(requestId) {
300
+ return createErrorResponse(this.errorDef, this.details, requestId);
301
+ }
302
+ };
303
+ export {
304
+ ErrorCodes,
305
+ Errors,
306
+ VasperaApiError,
307
+ createError,
308
+ createErrorResponse
309
+ };
310
+ //# sourceMappingURL=index.mjs.map