n8n-io/n8n · error · Error
Invalid file type
Error message
Invalid file type
What it means
Plain `Error('Invalid file type')` thrown at e2e.controller.ts:417 by the heap-snapshot download route when `req.params.filename` (after `path.basename`) does not end with `.heapsnapshot`. This controller is test-only — it hard-exits the process unless running under E2E (see top of file). The thrown `Error` is not a typed n8n error and will be serialized to a 500 by the generic response handler.
Source
Thrown at packages/cli/src/controllers/e2e.controller.ts:417
sizeBytes: stats.size,
sizeMB: Math.round(stats.size / 1024 / 1024),
};
}
private heapSnapshotPaths = new Map<string, string>();
/**
* Download a heap snapshot file as a stream.
* The response-helper pipes Readable streams directly to the response.
*/
@Get('/heap-snapshot/:filename', { skipAuth: true })
downloadHeapSnapshot(req: Request) {
const fs = require('node:fs') as typeof nodeFs;
const path = require('node:path') as typeof nodePath;
const filename = path.basename(req.params.filename);
if (!filename.endsWith('.heapsnapshot')) {
throw new Error('Invalid file type');
}
// Look up the full path stored during POST, or try cwd
const filePath = this.heapSnapshotPaths.get(filename) ?? path.resolve(filename);
if (!fs.existsSync(filePath)) {
throw new Error(`Snapshot not found: ${filename} (tried ${filePath})`);
}
return fs.createReadStream(filePath);
}
// --- Per-spec backend V8 coverage (DEVP-370) -----------------------------
// Lets the Playwright coverage fixture attribute this main process's V8
// coverage to the spec that produced it, so backend source files land in the
// E2E impact map (today the map is frontend-only). Test-only: the whole
// controller hard-exits outside E2E (see top of file).
//
// Uses `Profiler.getBestEffortCoverage` (NON-draining) + a server-sideView on GitHub (pinned to 5ac6606e81)
Solutions
- Pass a filename ending in `.heapsnapshot` produced by the POST heap-snapshot route.
- Use the filename exactly as stored in `heapSnapshotPaths` (set during POST).
- If writing a test fixture, assert the extension before constructing the URL.
Example fix
// before GET /e2e/heap-snapshot/dump.json // 500 Invalid file type // after GET /e2e/heap-snapshot/dump.heapsnapshot
Defensive patterns
Strategy: validation
Validate before calling
function assertHeapFile(name: string) {
if (!name.endsWith('.heapsnapshot')) throw new TypeError('Invalid file type');
} Type guard
const isHeapSnapshotFile = (f: unknown): f is string =>
typeof f === 'string' && f.endsWith('.heapsnapshot'); Prevention
- Use only filenames returned by the POST /e2e/heap-snapshot route.
- Assert the `.heapsnapshot` extension in test fixtures before constructing URLs.
- Remember this controller exists only in E2E mode — it never runs in production.
When it happens
Trigger: In E2E/test mode only: hitting `GET /e2e/heap-snapshot/<filename>` with a filename whose extension isn't `.heapsnapshot` — e.g. `.json`, `.txt`, or no extension. Cannot occur in production because the controller aborts startup outside E2E.
Common situations: Playwright fixtures building the wrong URL; manual curl during local E2E runs; typos in fixture file paths.
Related errors
- Snapshot not found: ${filename} (tried ${filePath})
- Invalid invite URL
- The invitation was likely either deleted or already claimed
- Invalid request
- error.message
AI-assisted analysis of n8n-io/n8n@5ac6606e81 (2026-08-12).
Data as JSON: /api/errors/0c680fb811022d49.
Report an issue: GitHub.