{"record":{"id":"c0021ae99ef740d0","repo":"abhigyanpatwari/GitNexus","slug":"source-must-be-a-file-or-directory-path","errorCode":null,"errorMessage":"${source} must be a file or directory path.","messagePattern":"(.+?) must be a file or directory path\\.","errorType":"validation","errorClass":"GitNexusRcError","httpStatus":null,"severity":"error","filePath":"gitnexus/src/cli/analyze-config.ts","lineNumber":235,"sourceCode":"  switch (kind) {\n    case 'boolean':\n      if (typeof value !== 'boolean') {\n        throw new GitNexusRcError(`${source} must be a boolean (true/false).`);\n      }\n      return value;\n    case 'boolean-negate':\n      if (typeof value !== 'boolean') {\n        throw new GitNexusRcError(`${source} must be a boolean (true/false).`);\n      }\n      return !value;\n    case 'branch':\n      if (typeof value !== 'string') {\n        throw new GitNexusRcError(`${source} must be a string branch name.`);\n      }\n      return validateBranchName(value, source);\n    case 'path': {\n      if (typeof value !== 'string') {\n        throw new GitNexusRcError(`${source} must be a file or directory path.`);\n      }\n      const trimmed = value.trim();\n      if (!trimmed) {\n        throw new GitNexusRcError(`${source} must not be empty.`);\n      }\n      assertNoHiddenChars(trimmed, source);\n      return trimmed;\n    }\n    case 'string': {\n      if (typeof value !== 'string') {\n        throw new GitNexusRcError(`${source} must be a string.`);\n      }\n      const trimmed = value.trim();\n      if (!trimmed) {\n        throw new GitNexusRcError(`${source} must not be empty.`);\n      }\n      assertNoHiddenChars(trimmed, source);\n      // `name` flows into the generated AGENTS.md/CLAUDE.md as `**${name}**` and","sourceCodeStart":217,"sourceCodeEnd":253,"githubUrl":"https://github.com/abhigyanpatwari/GitNexus/blob/52924ef12c2290ceee4612526a828ec4cdf2047f/gitnexus/src/cli/analyze-config.ts#L217-L253","documentation":"GitNexusRcError thrown by normalizeValue in analyze-config.ts when a `.gitnexusrc` option declared as type 'path' receives a non-string value (number, boolean, object, etc.). The config loader only accepts strings for path-typed options because paths are later trimmed, checked for hidden characters, and resolved relative to the repo root. The `source` placeholder names the option/origin so you know which key is bad.","triggerScenarios":"Loading .gitnexusrc / analyze config where a 'path'-kind option (e.g. an output or ignore path key) is set to a number, boolean, null, array or object instead of a string, e.g. `maxFileSize: 100` placed under a path option, or `output: true`.","commonSituations":"Hand-editing .gitnexusrc and quoting/typing mistakes (unquoted numbers, YAML/JSON5 coercing values), copying an option value from another tool where booleans/numbers are valid, or programmatically building a config object with the wrong field.","solutions":["Open .gitnexusrc (or the config source indicated by `source`) and change the offending option to a quoted string path, e.g. \"dist\" or \"src/output\".","Check for YAML/JSON type coercion: quote values that look like numbers or booleans if they are meant as paths.","If the value comes from a generated config, fix the generator/template to emit strings for path options.","Run `npx tsc --noEmit` or the config schema validation if you build the config in TypeScript to catch non-string values before runtime."],"exampleFix":"// before (.gitnexusrc)\noutput: docs/wiki\nmaxFileSize: 5242880   // number assigned to a path-typed option\n\n// after (.gitnexusrc)\noutput: \"docs/wiki\"\nmaxFileSize: \"build/cache\"  // any path option must be a string","handlingStrategy":"validation","validationCode":"function assertPathOption(value: unknown, source: string): void {\n  if (typeof value !== 'string') {\n    throw new Error(`${source} must be a file or directory path (string), got ${typeof value}`);\n  }\n}\n// run over every path-typed key of the parsed .gitnexusrc before invoking analyze","typeGuard":"function isPathOption(v: unknown): v is string {\n  return typeof v === 'string' && v.trim().length > 0;\n}","tryCatchPattern":"try {\n  await loadAnalyzeConfigStrict(repoRoot);\n} catch (e) {\n  if (e instanceof GitNexusRcError) {\n    console.error(`Config error: ${e.message}`);\n    process.exitCode = 1; // fix the named key in .gitnexusrc\n  } else throw e;\n}","preventionTips":["Quote all path values in .gitnexusrc so YAML/JSON never coerces them to numbers or booleans.","Add a pre-commit schema check (zod/ajv) for the rc file's path-typed keys.","Keep generator scripts strongly typed so path options are emitted as strings."],"tags":["config","validation","type-error","gitnexusrc"],"backgroundTag":"invalid-config-value-type","analyzedSha":"52924ef12c2290ceee4612526a828ec4cdf2047f","analyzedAt":"2026-09-01T13:15:02.810Z","contentChangedAt":"2026-09-01T13:15:02.810Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}