Forked from brdcastro/maestro
"use strict";
/**
* @file Structured error codes for tool results.
*
* Inspired by Claude Code's `validateInput()` errorCode pattern.
* Instead of returning free-text errors, tools return structured objects
* with a numeric code + category so the model can make programmatic decisions.
*
* Code ranges:
* 100–199 Validation (bad input)
* 200–299 Resource (file/asset issues)
* 300–399 Security / Permission
* 400–499 Execution failure
* 500–599 Timeout
* 600–699 Service / Network
* 700–799 Configuration
*/
Object.defineProperty(exports, "__esModule", { value: true });
exports.LINTER_NOT_FOUND = exports.API_ERROR = exports.HTTP_ERROR = exports.SERVICE_UNAVAILABLE = exports.REDOS_TIMEOUT = exports.TIMEOUT = exports.SPAWN_FAILED = exports.KEYNOTE_FAILED = exports.SCRIPT_TRUNCATED = exports.GIT_FAILED = exports.JXA_FAILED = exports.APPLESCRIPT_FAILED = exports.EXEC_FAILED = exports.WRITE_BLOCKED = exports.BLOCKED_PATTERN = exports.TOOL_DISABLED = exports.PATH_DENIED = exports.IO_ERROR = exports.UNSUPPORTED_FORMAT = exports.NO_FILES_FOUND = exports.FILE_IS_BINARY = exports.FILE_TOO_LARGE = exports.FILE_NOT_FOUND = exports.TEXT_NOT_FOUND = exports.MISSING_PARAM = exports.SLIDES_LIMIT = exports.NO_SLIDES = exports.PATTERN_TOO_COMPLEX = exports.MULTIPLE_MATCHES = exports.INVALID_CHARS = exports.EMPTY_INPUT = void 0;
exports.getRecoveryHint = getRecoveryHint;
exports.toolError = toolError;
// ── Validation (100–199) ───────────────────────────────────────────
exports.EMPTY_INPUT = 100;
exports.INVALID_CHARS = 101;
exports.MULTIPLE_MATCHES = 102;
exports.PATTERN_TOO_COMPLEX = 103;
exports.NO_SLIDES = 104;
exports.SLIDES_LIMIT = 105;
exports.MISSING_PARAM = 106;
exports.TEXT_NOT_FOUND = 107;
// ── Resource (200–299) ─────────────────────────────────────────────
exports.FILE_NOT_FOUND = 200;
exports.FILE_TOO_LARGE = 201;
exports.FILE_IS_BINARY = 202;
exports.NO_FILES_FOUND = 203;
exports.UNSUPPORTED_FORMAT = 204;
exports.IO_ERROR = 205;
// ── Security / Permission (300–399) ────────────────────────────────
exports.PATH_DENIED = 300;
exports.TOOL_DISABLED = 301;
exports.BLOCKED_PATTERN = 302;
exports.WRITE_BLOCKED = 303;
// ── Execution failure (400–499) ────────────────────────────────────
exports.EXEC_FAILED = 400;
exports.APPLESCRIPT_FAILED = 401;
exports.JXA_FAILED = 402;
exports.GIT_FAILED = 403;
exports.SCRIPT_TRUNCATED = 404;
exports.KEYNOTE_FAILED = 405;
exports.SPAWN_FAILED = 406;
// ── Timeout (500–599) ──────────────────────────────────────────────
exports.TIMEOUT = 500;
exports.REDOS_TIMEOUT = 501;
// ── Service / Network (600–699) ────────────────────────────────────
exports.SERVICE_UNAVAILABLE = 600;
exports.HTTP_ERROR = 601;
exports.API_ERROR = 602;
// ── Configuration (700–799) ────────────────────────────────────────
exports.LINTER_NOT_FOUND = 700;
function getCategory(code) {
if (code < 200)
return "validation";
if (code < 300)
return "resource";
if (code < 400)
return "security";
if (code < 500)
return "execution";
if (code < 600)
return "timeout";
if (code < 700)
return "service";
return "config";
}
// ── Recovery hints ────────────────────────────────────────────────
// Inline to avoid circular dependency (recoveryHints.ts re-exports this)
const RECOVERY_MAP = {
[100]: "Provide a non-empty value for the required parameter.",
[101]: "Remove invalid characters from the input and try again.",
[102]: "Be more specific — provide additional context to narrow the match to a single occurrence.",
[103]: "Simplify the regex pattern. Avoid nested quantifiers and backreferences.",
[104]: "Provide at least one slide object in the slides array.",
[105]: "Reduce the number of slides to 100 or fewer per call. Split into multiple calls if needed.",
[106]: "Check the tool's parameter list and provide all required values.",
[107]: "The exact text was not found. Re-read the file to check current contents, then adjust your search string.",
[200]: "Verify the file path exists. Use list_directory or find_files to locate the correct path.",
[201]: "Use offset and limit parameters to read a portion of the file instead of the full content.",
[202]: "This is a binary file and cannot be read as text. Use a different approach or tool.",
[203]: "No matching files found. Broaden your search criteria or check the directory path.",
[204]: "This file format is not supported. Convert to a supported format first.",
[205]: "File system error. Check that the path exists and you have permissions.",
[300]: "The path is outside the workspace boundary. Only access files within the project directory.",
[301]: "This tool is disabled in settings. Ask the user to enable it, or use an alternative approach.",
[302]: "This operation contains a blocked pattern for safety. Use the appropriate dedicated tool instead.",
[303]: "Write access is restricted. Ask the user if they want to enable write operations.",
[400]: "The command or script failed. Check the error message for details and fix the issue.",
[401]: "AppleScript execution failed. Check syntax and ensure the target app is running.",
[402]: "JXA script failed. Check JavaScript syntax and API usage.",
[403]: "Git operation failed. Ensure you are in a git repository and the operation is valid.",
[404]: "The script was truncated by output limits. Save it to a file first, then execute via script_file.",
[405]: "Keynote automation failed. Use the build_keynote tool instead of raw AppleScript.",
[406]: "Process spawn failed. Check that the command/runtime exists on this system.",
[500]: "The operation timed out. Try a simpler operation or increase the timeout if possible.",
[501]: "The regex took too long (potential ReDoS). Simplify the pattern to avoid catastrophic backtracking.",
[600]: "The external service is temporarily unavailable. Wait a moment and try again, or use a different approach.",
[601]: "HTTP request failed. Check the URL and try again.",
[602]: "API call failed. Check the endpoint configuration and try again.",
[700]: "The linter binary was not found. Ask the user to install it or check the path in settings.",
};
const CATEGORY_FALLBACKS = {
validation: "Check your input parameters and try again with corrected values.",
resource: "The requested resource was not found or is inaccessible. Verify the path and try again.",
security: "This operation was blocked for security reasons. Use an allowed alternative.",
execution: "Execution failed. Review the error details and try a different approach.",
timeout: "The operation timed out. Try a simpler or shorter operation.",
service: "External service error. Try again or use an offline alternative.",
config: "A configuration issue was detected. Ask the user to check plugin settings.",
};
function getRecoveryHint(code) {
if (RECOVERY_MAP[code])
return RECOVERY_MAP[code];
return CATEGORY_FALLBACKS[getCategory(code)] || "An error occurred. Try a different approach.";
}
/**
* Create a structured error result for a tool.
* Backward-compatible: tools that check `result.error` still work,
* but the model also gets `errorCode`, `category`, and `hint` for smarter recovery.
*/
function toolError(code, message, hint) {
return {
error: message,
errorCode: code,
category: getCategory(code),
hint: hint || getRecoveryHint(code),
};
}
//# sourceMappingURL=errorCodes.js.map