angular/angular-cli · error · Error

Access denied: glob pattern '${pattern}' contains path trave

Error message

Access denied: glob pattern '${pattern}' contains path traversal sequences.

What it means

The MCP host glob() wrapper rejects glob patterns containing '..' outright, before checking cwd or the pattern's base directory. Because glob patterns can traverse directories via wildcard segments, any '..' in the pattern is treated as a path traversal attempt and denied unconditionally.

Source

Thrown at packages/angular/cli/src/commands/mcp/host.ts:365

    },
    stat(path: string) {
      checkPath(path);

      return baseHost.stat(path);
    },
    existsSync(path: string) {
      checkPath(path);

      return baseHost.existsSync(path);
    },
    readFile(path: string, encoding: BufferEncoding) {
      checkPath(path);

      return baseHost.readFile(path, encoding);
    },
    glob(pattern: string, options: { cwd: string }) {
      if (pattern.includes('..')) {
        throw new Error(
          `Access denied: glob pattern '${pattern}' contains path traversal sequences.`,
        );
      }

      checkPath(options.cwd);

      const firstWildcardIndex = pattern.search(/[*?[{]/);
      const basePath = firstWildcardIndex >= 0 ? pattern.substring(0, firstWildcardIndex) : pattern;

      const targetDir = resolve(options.cwd, basePath);
      checkPath(targetDir);

      return baseHost.glob(pattern, options);
    },
    executeNgCommand(
      args: readonly string[],
      options: Parameters<Host['executeNgCommand']>[1] = {},
    ) {

View on GitHub (pinned to bb72145f9a)

Solutions

  1. Remove '..' from the pattern and set cwd to the actual target directory instead.
  2. Anchor the glob at a common root (e.g. cwd set to the workspace root, pattern 'src/**/*.ts').
  3. Ensure the resolved base directory and cwd are inside the allowed MCP roots.

Example fix

// before
host.glob('../shared/**/*.ts', { cwd: workspaceRoot });
// after
host.glob('**/*.ts', { cwd: '/home/dev/my-app/shared' });
Defensive patterns

Strategy: validation

Validate before calling

function safeGlob(pattern: string): string {
  if (pattern.includes('..')) {
    throw new Error(`glob pattern '${pattern}' must not contain '..'`);
  }
  return pattern;
}
const pattern = safeGlob('src/**/*.ts');

Type guard

function isSafeGlobPattern(p: string): p is string {
  return !p.includes('..');
}

Try / catch

try {
  const files = host.glob(pattern, { cwd: workspaceRoot });
} catch (e) {
  if ((e as Error).message.includes('path traversal sequences')) {
    const files = host.glob(pattern.replaceAll(/(^|\/|\\)\.\.($|\/|\\)/g, ''), { cwd: workspaceRoot });
  } else throw e;
}

Prevention

When it happens

Trigger: Calling glob(pattern, { cwd }) where the pattern string contains '..' anywhere (e.g. '../src/**/*.ts' or 'packages/../secret/*').

Common situations: Clients computing relative patterns from a different directory and walking up with '..'; templated patterns built from user input; ported shell glob commands that relied on relative parent paths.

Understand the failure class

Related errors


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