angular/angular-cli · error · FileDoesNotExistException

Path "${path}" does not exist.

Error message

Path "${path}" does not exist.

What it means

FileDoesNotExistException is thrown by Sink validation (via _fileDoesNotExistException) when an Overwrite, Rename, or Delete action targets a path that does not exist. The sink validates every action against the underlying filesystem before committing, so mutating a missing file fails instead of silently no-oping.

Source

Thrown at packages/angular_devkit/schematics/src/sink/sink.ts:59

    Noop;
  postCommitAction: (action: Action) => void | Observable<void> = Noop;
  preCommit: () => void | Observable<void> = Noop;
  postCommit: () => void | Observable<void> = Noop;

  protected abstract _validateFileExists(p: string): Observable<boolean>;

  protected abstract _overwriteFile(path: string, content: Buffer): Observable<void>;
  protected abstract _createFile(path: string, content: Buffer): Observable<void>;
  protected abstract _renameFile(path: string, to: string): Observable<void>;
  protected abstract _deleteFile(path: string): Observable<void>;

  protected abstract _done(): Observable<void>;

  protected _fileAlreadyExistException(path: string): void {
    throw new FileAlreadyExistException(path);
  }
  protected _fileDoesNotExistException(path: string): void {
    throw new FileDoesNotExistException(path);
  }

  protected _validateOverwriteAction(action: OverwriteFileAction): Observable<void> {
    return this._validateFileExists(action.path).pipe(
      map((b) => {
        if (!b) {
          this._fileDoesNotExistException(action.path);
        }
      }),
    );
  }
  protected _validateCreateAction(action: CreateFileAction): Observable<void> {
    return this._validateFileExists(action.path).pipe(
      map((b) => {
        if (b) {
          this._fileAlreadyExistException(action.path);
        }
      }),

View on GitHub (pinned to bb72145f9a)

Solutions

  1. Guard with tree.exists(path) before overwrite/rename/delete and branch accordingly.
  2. Use tree.create() instead of overwrite when the file may legitimately be missing.
  3. Fix path assumptions: derive paths from project config rather than hardcoding, or update the schematic for newer Angular layouts.

Example fix

// before
tree.overwrite('src/app/app.module.ts', newContent);
// after
const modulePath = '/src/app/app.module.ts';
if (tree.exists(modulePath)) {
  tree.overwrite(modulePath, newContent);
}
Defensive patterns

Strategy: validation

Validate before calling

const required = ['/src/app/app.module.ts'];
const missing = required.filter((p) => !tree.exists(p));
if (missing.length) throw new SchematicsException(`Missing: ${missing.join(', ')}`);

Type guard

null

Try / catch

try { host.commit(tree); } catch (e) { if (e instanceof FileDoesNotExistException) { logger.warn(`Skipped missing file: ${e.message}`); } else { throw e; } }

Prevention

When it happens

Trigger: host.commitSingleAction() or commit() with an 'o' (overwrite), 'r' (rename), or 'd' (delete) action whose path is absent from the sink's filesystem; calling sink-level overwrite/rename/delete on a non-existent file.

Common situations: A schematic assumes a file exists (e.g. overwriting src/app/app.component.ts) but the project layout differs (standalone apps, different naming, newer CLI versions); deleting a file that a prior step already removed; renaming after a conditional step skipped creation.

Related errors


AI-assisted analysis of angular/angular-cli@bb72145f9a (2026-08-30). Data as JSON: /api/errors/dc53e0e2c98efd9e. Report an issue: GitHub.