{"record":{"id":"44e25a257921d3ba","repo":"janhq/jan","slug":"invalid-path-or-file-path","errorCode":null,"errorMessage":"Invalid path or file ${path}","messagePattern":"Invalid path or file (.+?)","errorType":"validation","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"extensions/llamacpp-extension/src/index.ts","lineNumber":2859,"sourceCode":"\n    // Match prefix (optional), llama, main (optional), version (b####-hash),\n    // optional cudart-llama, bin, backend details\n    // Examples:\n    // - k_llama-main-b4314-09c61e1-bin-win-cuda-12.8-x64-avx2.zip\n    // - ik_llama-main-b4314-09c61e1-cudart-llama-bin-win-cuda-12.8-x64-avx512.zip\n    // - llama-b7037-bin-win-cuda-12.4-x64.zip (legacy format)\n    const re =\n      /^(.+?[-_])?llama(?:-main)?-(b\\d+(?:-[a-f0-9]+)?)(?:-cudart-llama)?-bin-(.+?)\\.(?:tar\\.gz|zip)$/\n\n    const archiveName = await basename(path)\n    logger.info(`Installing backend from path: ${path}`)\n\n    if (\n      !(await fs.existsSync(path)) ||\n      (!path.endsWith('tar.gz') && !path.endsWith('zip'))\n    ) {\n      logger.error(`Invalid path or file ${path}`)\n      throw new Error(`Invalid path or file ${path}`)\n    }\n\n    const match = re.exec(archiveName)\n\n    if (!match) {\n      throw new Error(\n        `Failed to parse archive name: ${archiveName}. Expected format: [Optional prefix-]llama-<version>-bin-<backend>.(tar.gz|zip)`\n      )\n    }\n\n    const [, prefix, version, backend] = match\n\n    if (!version || !backend) {\n      throw new Error(`Invalid backend archive name: ${archiveName}`)\n    }\n\n    // Include prefix in the backend identifier if present\n    const backendIdentifier = prefix ? `${prefix}${backend}` : backend","sourceCodeStart":2841,"sourceCodeEnd":2877,"githubUrl":"https://github.com/janhq/jan/blob/fad3f12a147d138388a66f0d92a02b2675f65294/extensions/llamacpp-extension/src/index.ts#L2841-L2877","documentation":"Input validation at the start of the install-from-archive method: the path must exist on disk AND end in either '.tar.gz' or '.zip'. If either condition fails, the method throws before attempting any decompression or parsing.","triggerScenarios":"The user-supplied path points to a non-existent file; the file exists but has a different extension (.7z, .tar.xz, .exe, no extension); the path has a typo; the file was deleted between selection and installation.","commonSituations":"User selects a .7z or .tar.xz archive that the extension does not support; file picker was pointed at a directory instead of an archive; a download was interrupted and the partial file has a .tmp extension.","solutions":["Ensure the archive is a .tar.gz (Linux/macOS) or .zip (Windows) file matching the expected naming convention.","Verify the file exists at the given path before invoking the install method.","If you have a different archive format, re-package or re-download in a supported format."],"exampleFix":null,"handlingStrategy":"validation","validationCode":"import fs from 'node:fs'\n\nfunction isValidArchivePath(path: string): boolean {\n  return fs.existsSync(path) && (path.endsWith('.tar.gz') || path.endsWith('.zip'))\n}\n\n// Before calling install:\nif (!isValidArchivePath(path)) {\n  throw new Error(`Path must be an existing .tar.gz or .zip file: ${path}`)\n}","typeGuard":"function isSupportedArchivePath(path: string): boolean {\n  return path.endsWith('.tar.gz') || path.endsWith('.zip')\n}","tryCatchPattern":null,"preventionTips":["Filter the file picker in the UI to only show .zip and .tar.gz files.","Validate the path immediately after user selection, not just at install time."],"tags":["backend","validation","archive","file-path","typescript"],"backgroundTag":null,"analyzedSha":"fad3f12a147d138388a66f0d92a02b2675f65294","analyzedAt":"2026-08-12T20:33:47.516Z","schemaVersion":2},"datasetVersion":"2026-08-12T23:17:12.415Z"}