{"record":{"id":"dc9e298af1204da1","repo":"heygen-com/hyperframes","slug":"install-failed","errorCode":"install-failed","errorMessage":"Install failed: ${err instanceof Error ? err.message : String(err)}","messagePattern":"Install failed: (.+?)","errorType":"exception","errorClass":"AddError","httpStatus":null,"severity":"error","filePath":"packages/cli/src/commands/add.ts","lineNumber":194,"sourceCode":"// Install a topologically-ordered plan (dependencies first, requested item\n// last). The installer validates every target before any write; a failure on\n// any item surfaces as an install-failed AddError. Returns all written paths.\nasync function installAll(\n  installPlan: RegistryItem[],\n  destDir: string,\n  baseUrl: string | undefined,\n  force: boolean,\n): Promise<{ written: string[]; preserved: string[] }> {\n  const written: string[] = [];\n  const preserved: string[] = [];\n  try {\n    for (const planItem of installPlan) {\n      const result = await installItem(planItem, { destDir, baseUrl, force });\n      written.push(...result.written);\n      preserved.push(...result.preserved);\n    }\n  } catch (err) {\n    throw new AddError(\n      `Install failed: ${err instanceof Error ? err.message : String(err)}`,\n      \"install-failed\",\n    );\n  }\n  return { written, preserved };\n}\n\nexport async function runAdd(opts: RunAddArgs): Promise<RunAddResult> {\n  const projectDir = resolve(opts.projectDir);\n\n  // 1. Load (or write default) project config.\n  let config = loadProjectConfig(projectDir);\n  const hasConfig = existsSync(projectConfigPath(projectDir));\n  if (!hasConfig && existsSync(resolve(projectDir, \"index.html\"))) {\n    writeProjectConfig(projectDir, DEFAULT_PROJECT_CONFIG);\n    config = DEFAULT_PROJECT_CONFIG;\n  }\n","sourceCodeStart":176,"sourceCodeEnd":212,"githubUrl":"https://github.com/heygen-com/hyperframes/blob/c2996c8626135db5253519359d8a063d3bafad8d/packages/cli/src/commands/add.ts#L176-L212","documentation":"AddError with code 'install-failed', thrown by installAll as a catch-all wrapper around the per-item installItem loop. Any error from writing files, creating directories, or item-level validation is re-wrapped so the command surfaces a consistent exit code; the original error message is preserved in the AddError message. Because the installer validates every target before writing, a mid-loop failure still leaves earlier items written.","triggerScenarios":"Filesystem permission denied on destDir, a target path collision that force=false refuses to overwrite, disk full, an EACCES/EPERM on the registry cache, or installItem throwing on a malformed item manifest.","commonSituations":"Running without write permission to the project (read-only mount, root-owned dir); a pre-existing file at the target without --force; symlink or case-collision on case-insensitive filesystems; full disk in CI.","solutions":["Read the inner message in 'Install failed: <inner>' — it names the exact file and filesystem error.","Re-run with --force if the cause is an existing target you intend to overwrite.","Fix permissions on the project directory (chown/chmod) or run from a location you own.","Free disk space or clear the registry cache if the inner error is ENOSPC."],"exampleFix":"# before: existing file blocks the install\n$ hyperframes add my-block   # install-failed: EEXIST ...\n\n# after: explicitly overwrite\n$ hyperframes add my-block --force","handlingStrategy":"try-catch","validationCode":"import { access, constants } from 'node:fs/promises';\nasync function assertWritable(dir: string) {\n  await access(dir, constants.W_OK);\n}\nawait assertWritable(resolve(projectDir));","typeGuard":null,"tryCatchPattern":"try {\n  await runAdd(opts);\n} catch (err) {\n  if (err instanceof AddError && err.code === 'install-failed') {\n    if (/EEXIST/.test(err.message)) opts.force = true;   // retry with --force\n    else throw err;\n  }\n}","preventionTips":["Confirm write permission on the project directory before invoking add.","Pass --force only when you intend to overwrite existing targets.","Free disk space in CI and clear the registry cache periodically."],"tags":["cli","filesystem","install","registry"],"backgroundTag":null,"analyzedSha":"c2996c8626135db5253519359d8a063d3bafad8d","analyzedAt":"2026-08-12T22:18:56.877Z","schemaVersion":2},"datasetVersion":"2026-08-12T23:17:12.415Z"}