angular/components · error · TsconfigParseError

formatDiagnostics([error], fileSystem)

Error message

formatDiagnostics([error], fileSystem)

What it means

After the file exists, parseTsconfigFile calls ts.readConfigFile; if TypeScript reports a reading error (invalid JSON/JSONC syntax, unreadable content), the error is formatted into a human-readable diagnostic and thrown as TsconfigParseError. The tool deliberately never attempts to parse a config that failed to read.

Source

Thrown at src/cdk/schematics/update-tool/utils/parse-tsconfig.ts:41

 *
 * @throws {TsconfigParseError} If the tsconfig could not be read or parsed.
 */
export function parseTsconfigFile(
  tsconfigPath: WorkspacePath,
  fileSystem: FileSystem,
): ts.ParsedCommandLine {
  if (!fileSystem.fileExists(tsconfigPath)) {
    throw new TsconfigParseError(`Tsconfig cannot not be read: ${tsconfigPath}`);
  }

  const {config, error} = ts.readConfigFile(
    tsconfigPath,
    p => fileSystem.read(fileSystem.resolve(p))!,
  );

  // If there is a config reading error, we never attempt to parse the config.
  if (error) {
    throw new TsconfigParseError(formatDiagnostics([error], fileSystem));
  }

  const parsed = ts.parseJsonConfigFileContent(
    config,
    new FileSystemHost(fileSystem),
    dirname(tsconfigPath),
    {},
  );

  // Skip the "No inputs found..." error since we don't want to interrupt the migration if a
  // tsconfig doesn't match a file. This will result in an empty `Program` which is still valid.
  const errors = parsed.errors.filter(diag => diag.code !== NO_INPUTS_ERROR_CODE);

  if (errors.length) {
    throw new TsconfigParseError(formatDiagnostics(errors, fileSystem));
  }

  return parsed;

View on GitHub (pinned to 0411926e7d)

Solutions

  1. Open the tsconfig at the path shown in the diagnostic and fix the JSON/JSONC syntax error reported by the message.
  2. Remove leftover merge-conflict markers or truncated content from the file.
  3. If the file is generated, regenerate it (e.g. via ng update or the CLI) instead of hand-editing.

Example fix

// before (invalid tsconfig)
{
  "compilerOptions": {
    "strict": true
  } // missing closing brace
// after
{
  "compilerOptions": {
    "strict": true
  }
}
Defensive patterns

Strategy: try-catch

Validate before calling

// Pre-validate JSON/JSONC parses cleanly
import {readFileSync} from 'fs';
try {
  readFileSync(tsconfigPath, 'utf8'); // also surfaces unreadable file
  JSON.parse(readFileSync(tsconfigPath, 'utf8').replace(/\/\/.*$/gm, ''));
} catch (e) {
  console.error(`tsconfig at ${tsconfigPath} is unreadable or invalid JSON: ${e.message}`);
}

Try / catch

try {
  const parsed = parseTsconfigFile(path, fileSystem);
} catch (e) {
  if (e instanceof TsconfigParseError) {
    console.error('tsconfig read error, fix the syntax shown in diagnostics:\n' + e.message);
  } else {
    throw e;
  }
}

Prevention

When it happens

Trigger: parseTsconfigFile reaches ts.readConfigFile and the returned `error` is non-null — e.g. the tsconfig contains invalid JSON (trailing content, unquoted comments outside JSONC allowance) or the underlying fileSystem.read fails producing a TS read error.

Common situations: Hand-edited tsconfig.json with a syntax mistake (missing comma/brace, trailing commas in strict JSON contexts), a merge conflict marker left in the file, truncated or empty file, or an extends chain pointing at a broken file.

Related errors


AI-assisted analysis of angular/components@0411926e7d (2026-08-31). Data as JSON: /api/errors/a0380711477704a1. Report an issue: GitHub.