mastra-ai/mastra · error · FileNotFoundError
ENOENT
ENOENT
Error message
File not found: ${path} What it means
readFile throws FileNotFoundError (code ENOENT) when the target path does not exist on disk. The raw Node ENOENT from fs.readFile is translated into this typed error so callers can branch on error.code === 'ENOENT' or instanceof FileNotFoundError. This is one of the most common filesystem errors and usually indicates a wrong path, wrong casing, or a file that was expected to have been created earlier.
Source
Thrown at packages/core/src/workspace/filesystem/local-filesystem.ts:404
this.logger.debug('Reading file', { path: inputPath, encoding: options?.encoding });
await this.ensureReady();
const absolutePath = this.resolvePath(inputPath);
await this.assertPathContained(absolutePath);
try {
const stats = await fs.stat(absolutePath);
if (stats.isDirectory()) {
throw new IsDirectoryError(inputPath);
}
if (options?.encoding) {
return await fs.readFile(absolutePath, { encoding: options.encoding });
}
return await fs.readFile(absolutePath);
} catch (error: unknown) {
if (error instanceof IsDirectoryError) throw error;
if (isEnoentError(error)) {
throw new FileNotFoundError(inputPath);
}
throw error;
}
}
async writeFile(inputPath: string, content: FileContent, options?: WriteOptions): Promise<void> {
const contentSize = Buffer.isBuffer(content) ? content.length : content.length;
this.logger.debug('Writing file', { path: inputPath, size: contentSize, recursive: options?.recursive });
await this.ensureReady();
this.assertWritable('writeFile');
const absolutePath = this.resolvePath(inputPath);
await this.assertPathContained(absolutePath);
// When recursive is explicitly false, verify parent directory exists
if (options?.recursive === false) {
const dir = nodePath.dirname(absolutePath);
const parentPath = nodePath.dirname(inputPath);
try {View on GitHub (pinned to 75dd419e61)
Solutions
- Check existence first with stat or use list to confirm the exact filename (watch casing).
- Create the file before reading it, or return a default/empty value when it is optional.
- Catch FileNotFoundError (code ENOENT) and handle it as 'absent' rather than a hard failure when appropriate.
- Verify the workspace basePath and mount configuration point at the directory that actually contains the file.
Example fix
// before
const cfg = await fs.readFile('config.json', { encoding: 'utf8' }); // throws if missing
// after
let cfg: string;
try {
cfg = await fs.readFile('config.json', { encoding: 'utf8' });
} catch (e) {
if (e instanceof FileNotFoundError) cfg = '{}';
else throw e;
} Defensive patterns
Strategy: try-catch
Validate before calling
try {
await ws.stat(p);
} catch {
return null; // or create the file, depending on semantics
} Type guard
import { FileNotFoundError } from '@mastra/core/workspace/errors';
function isFileNotFoundError(e: unknown): e is FileNotFoundError {
return e instanceof FileNotFoundError ||
(e instanceof Error && 'code' in e && (e as { code?: string }).code === 'ENOENT');
} Try / catch
try {
return await ws.readFile(p, { encoding: 'utf8' });
} catch (e) {
if (isFileNotFoundError(e)) return defaultValue; // optional file
throw e;
} Prevention
- Confirm exact filenames via list/stat — beware case sensitivity.
- Create files before reading them in multi-step flows; check the producing step succeeded.
- Trim and normalize user/model supplied filenames before use.
- Verify basePath and mount config match where the file was actually written.
When it happens
Trigger: readFile (or the 'content' helper) with a path that was never created, was deleted, or has a typo/wrong casing; reading a file expected from a previous workflow step that failed silently; case-sensitive filesystems where 'Config.JSON' ≠ 'config.json'.
Common situations: Agent hallucinates or misremembers a filename; file created in a different basePath or mount than where it's read; CI environment lacks a file present locally; path built from untrimmed user input (whitespace/newline in filename).
Related errors
- ENOENT
- FileNotFoundError: ${path}
- Presets file not found: ${absolutePath}
- MASTRA_ENTRY_FILE_NOT_FOUND
- Failed to copy studio assets from "${studioSource}" to "${st
AI-assisted analysis of mastra-ai/mastra@75dd419e61 (2026-08-30).
Data as JSON: /api/errors/fb7add3b2d05bc76.
Report an issue: GitHub.