abhigyanpatwari/GitNexus · error · InvalidStoragePathError

Repository path must be non-empty.

Error message

Repository path must be non-empty.

What it means

resolveRepoPath validates the raw repository path input before path.resolve. A zero-length (or non-string) value is rejected with InvalidStoragePathError('Repository path must be non-empty.'). Every downstream resolver helper (canonicalRepoPath, defaultStoragePath, resolvedRepoPath, requireDeletableStoragePath) funnels through it, so this fires on the first storage API call with an empty repo path.

Solutions

  1. Supply a valid repository path (e.g. process.cwd() or the project root) to the storage call.
  2. Check the config/env source that should hold the path; fix the empty value before calling.
  3. Add an early guard in your caller to fail with a clear message when the path is empty.
  4. If path comes from argv, validate arg count/presence before invoking storage APIs.

Example fix

// before
const repoPath = config.repoPath ?? '';
const canonical = await canonicalRepoPath(repoPath);
// after
const repoPath = config.repoPath ?? process.cwd();
if (typeof repoPath !== 'string' || repoPath.length === 0) throw new Error('repoPath is required');
const canonical = await canonicalRepoPath(repoPath);
Defensive patterns

Strategy: validation

Validate before calling

if (typeof repoPath !== 'string' || repoPath.trim().length === 0) {
  throw new Error('repoPath is required and must be a non-empty string');
}

Type guard

const isNonEmptyString = (v: unknown): v is string => typeof v === 'string' && v.length > 0;

Try / catch

try {
  return await canonicalRepoPath(repoPath);
} catch (e) {
  if (e instanceof InvalidStoragePathError) throw new Error(`bad repo path input: ${e.message}`);
  throw e;
}

Prevention

When it happens

Trigger: Passing '' (or undefined coerced via String()) as the repoPath argument to canonicalRepoPath/defaultStoragePath/resolvedRepoPath, or a config/env value that resolves to an empty string.

Common situations: Missing or empty CLI flag / config field for the repository path; env var like GITNEXUS_... left unset and defaulted to ''; calling the storage API programmatically before the caller supplied a repo root.

Understand the failure class

Background: "must not be empty", "cannot be empty" — required-field validation errors across open-source libraries — this error's family across 41 libraries.

Related errors


AI-assisted analysis of abhigyanpatwari/GitNexus@ac9a4e9abd (2026-09-15). Data as JSON: /api/errors/96ae02b4efad5f76. Report an issue: GitHub.

Appendix: source

Thrown at gitnexus/src/storage/storage-resolver.ts:175

const samePath = (left: string, right: string): boolean =>
  process.platform === 'win32' ? left.toLowerCase() === right.toLowerCase() : left === right;

const isRepositoryLocalStoragePath = (repoPath: string, storagePath: string): boolean =>
  samePath(comparablePath(defaultStoragePath(repoPath)), comparablePath(storagePath));

const isMissingFilesystemError = (error: unknown): boolean => {
  const code = (error as NodeJS.ErrnoException)?.code;
  return code === 'ENOENT' || code === 'ENOTDIR';
};

const filesystemErrorDetail = (error: unknown): string => {
  const code = (error as NodeJS.ErrnoException)?.code;
  return code ? `${code}: ${(error as Error)?.message ?? String(error)}` : String(error);
};

const resolveRepoPath = (value: string): string => {
  if (typeof value !== 'string' || value.length === 0) {
    throw new InvalidStoragePathError('Repository path must be non-empty.');
  }
  if (value.includes('\0')) {
    throw new InvalidStoragePathError('Repository path must not contain a NUL character.');
  }
  return path.resolve(value);
};

const validateAbsolutePath = (value: string, label: string): string => {
  if (typeof value !== 'string' || value.length === 0) {
    throw new InvalidStoragePathError(`${label} must be an absolute, non-empty path.`);
  }
  if (value.includes('\0')) {
    throw new InvalidStoragePathError(`${label} must not contain a NUL character.`);
  }
  if (!path.isAbsolute(value)) {
    throw new InvalidStoragePathError(`${label} must be an absolute path.`);
  }
  return path.resolve(value);

View on GitHub (pinned to ac9a4e9abd)