n8n-io/n8n · error · Error

Disk source needs the n8n repo (run from inside it) or…

Error message

Disk source needs the n8n repo (run from inside it) or --workflow-dir; or use --source langtracer.

What it means

When using the default disk source, the CLI resolves the test-case directory from the n8n repo root via `git rev-parse --show-toplevel`. If the script is not running inside a git repo (repoRoot is undefined) AND --workflow-dir is not provided, there is no way to locate test cases on disk. The error at line 492 suggests three concrete alternatives.

Solutions

  1. Run from inside the n8n repo checkout (cd /path/to/n8n first)
  2. Pass --workflow-dir with an explicit path to the test-case JSON directory
  3. Use --source langtracer to pull test cases from a remote suite instead of disk

Example fix

# before (run from /tmp)
pnpm eval:build-mcp-manifest

# after
cd /path/to/n8n && pnpm eval:build-mcp-manifest
Defensive patterns

Strategy: validation

Validate before calling

import { execSync } from 'child_process';
import { existsSync } from 'fs';

let repoRoot: string | undefined;
try {
  repoRoot = execSync('git rev-parse --show-toplevel', { encoding: 'utf-8' }).trim();
} catch { repoRoot = undefined; }

const workflowDir = args.workflowDir ?? (repoRoot ? join(repoRoot, '.../data/workflows') : undefined);
if (!workflowDir) {
  throw new Error('Disk source needs the n8n repo or --workflow-dir; or use --source langtracer.');
}

Prevention

When it happens

Trigger: Running the CLI from a directory that is not inside the n8n git repo, without --workflow-dir, and without --source langtracer. For example, running from /tmp or a non-repo directory.

Common situations: Running from /tmp or a scratch directory. The script was invoked outside the n8n checkout. A CI environment that does a shallow/partial clone without .git. Running from a worktree that lost its git context.

Related errors


AI-assisted analysis of n8n-io/n8n@5ac6606e81 (2026-08-12). Data as JSON: /api/errors/b0d31b9b2c61719f. Report an issue: GitHub.

Appendix: source

Thrown at packages/@n8n/instance-ai/evaluations/cli/build-mcp-manifest.ts:492

			tier: args.tier,
			logger: createLogger(false),
		});
		for (const { fileSlug, testCase } of cases)
			casesBySlug.set(fileSlug, testCase.conversation ?? []);
		if (args.slugs.length > 0) {
			const requested = new Set(args.slugs);
			for (const slug of [...casesBySlug.keys()]) {
				if (!requested.has(slug)) casesBySlug.delete(slug);
			}
		}
	} else {
		const workflowDir =
			args.workflowDir ??
			(repoRoot
				? join(repoRoot, 'packages/@n8n/instance-ai/evaluations/data/workflows')
				: undefined);
		if (!workflowDir) {
			throw new Error(
				'Disk source needs the n8n repo (run from inside it) or --workflow-dir; or use --source langtracer.',
			);
		}
		let slugs = args.slugs.length > 0 ? args.slugs : discoverSlugs(workflowDir);
		if (args.tier) slugs = filterSlugsByTier(workflowDir, slugs, args.tier);
		for (const slug of slugs) {
			const file = join(workflowDir, `${slug}.json`);
			if (!existsSync(file)) {
				console.log(`  [${slug}] skip: scenario file missing`);
				continue;
			}
			casesBySlug.set(slug, testCaseSchema.parse(readJson(file, `test case ${slug}`)).conversation);
		}
	}
	// Drop cases with no user turn to build from (e.g. `replay`-seeded only).
	for (const [slug, conv] of [...casesBySlug]) {
		if (!conv.some((t) => t.role === 'user' && t.text.trim().length > 0)) {
			console.log(`  [${slug}] skip: no user turn to build from`);

View on GitHub (pinned to 5ac6606e81)