jsconfig.json option

checkJs

  • Default false
  • Since TypeScript 2.3

checkJs is the option that makes TypeScript report errors in JavaScript files. With it on, tsc and your editor check every .js file in the project the way they check .ts files, using your JSDoc comments where you have written them and inference everywhere else.

Every jsconfig.json on this site sets it. In TypeScript 5.9, checkJs also turns on allowJs when you leave allowJs out, so "checkJs": true on its own both includes your JavaScript files and checks them.

At a glance

Write "checkJs": true
On the command line --checkJs
Type boolean
Default in TypeScript 5.9 false
TypeScript's description Enable error reporting in type-checked JavaScript files.
In the quick-start setups
Generator, relaxed true
Generator, recommended true
Generator, strict true

The description is quoted from TypeScript's own option list (Apache-2.0); see the notices. The setup values are the checked configs on the quick-start pages. The generator rows are what the jsconfig generator writes at each level.

Examples

profile.js Error confirmed 5.9.3 TypeScript 5.9.3, run 21 October 2026: profile.js(5,15): error TS2551: Property 'toUppercase' does not exist on type 'string'. Did you mean 'toUpperCase'? 6.0.3 TypeScript 6.0.3, run 21 October 2026: the same as 5.9.3. profile.js(5,15): error TS2551: Property 'toUppercase' does not exist on type 'string'. Did you mean 'toUpperCase'? 7.0.2 TypeScript 7.0.2, run 21 October 2026: the same as 5.9.3. profile.js(5,15): error TS2551: Property 'toUppercase' does not exist on type 'string'. Did you mean 'toUpperCase'? checked 21 October 2026
const user = { name: "Ada", role: "admin" };

let label = user.name;
label = label.toUppercase();error TS2551: Property 'toUppercase' does not exist on type 'string'. Did you mean 'toUpperCase'?

export { label };
checkJs on, no annotations at all.
jsconfig.json for this example
{
  "compilerOptions": {
    "checkJs": true,
    "noEmit": true,
    "target": "es2022",
    "module": "nodenext",
    "types": []
  },
  "include": ["*.js"]
}
report.js Error confirmed 5.9.3 TypeScript 5.9.3, run 21 October 2026: report.js(5,22): error TS2551: Property 'lenght' does not exist on type 'string[]'. Did you mean 'length'? 6.0.3 TypeScript 6.0.3, run 21 October 2026: the same as 5.9.3. report.js(5,22): error TS2551: Property 'lenght' does not exist on type 'string[]'. Did you mean 'length'? 7.0.2 TypeScript 7.0.2, run 21 October 2026: the same as 5.9.3. report.js(5,22): error TS2551: Property 'lenght' does not exist on type 'string[]'. Did you mean 'length'? checked 21 October 2026
// @ts-check
const names = ["Ada", "Grace", "Katherine"];

console.log(`${names.lenght} people`);error TS2551: Property 'lenght' does not exist on type 'string[]'. Did you mean 'length'?
One file opted in with // @ts-check.
jsconfig.json for this example
{
  "compilerOptions": {
    "allowJs": true,
    "checkJs": false,
    "noEmit": true,
    "target": "es2022",
    "module": "nodenext",
    "types": []
  },
  "include": ["*.js"]
}

What it catches with no annotations

The first example has no JSDoc in it at all, and the checker still finds the typo. Without annotations, checkJs reports what it can work out from literals, the standard library, and the @types packages you install:

  • misspelled properties and methods, often with a "Did you mean" suggestion
  • calls with too many arguments (in JavaScript, a parameter without a JSDoc type counts as optional, so calls with fewer arguments are allowed)
  • wrong types going into functions that do have types, such as the DOM and Node.js APIs
  • imports of files and exports that do not exist

checkJs, allowJs and // @ts-check

allowJs lets JavaScript files into the program; checkJs decides whether their errors are reported. A config file named jsconfig.json already defaults allowJs to true, and in TypeScript 5.9 checkJs implies it as well, so most JavaScript projects only need checkJs.

You can also opt in one file at a time. A // @ts-check comment at the top of a file checks that file even when checkJs is off, which is how the second example works; // @ts-nocheck at the top of a file skips it when checkJs is on.

For a single line, // @ts-expect-error silences the error on the next line and is itself reported (TS2578) once there is nothing left to silence. // @ts-ignore silences the next line without that check, so it can hide a later, different error.

Switching it on in an existing codebase

In a large JavaScript codebase the first run can report hundreds of errors. A workable order: turn on checkJs without strict, fix or // @ts-nocheck the noisiest files, then turn on strict (or noImplicitAny first) once the count is manageable. The relaxed level of the jsconfig generator is that first step.

Gotchas

  • Set noEmit too. A config file named tsconfig.json with allowJs and no outDir makes tsc try to write output over your own .js files, which fails with TS5055 ("Cannot write file … because it would overwrite input file"). A file named jsconfig.json defaults noEmit to true.
  • checkJs changes what tsc reports and nothing else. Node.js and browsers run the same JavaScript whether it is on or off.
  • Without checkJs (and without // @ts-check), editors still give completions and hovers in .js files but show no type errors, which can look as if everything passes.

Questions

Do I need both allowJs and checkJs?

Not in TypeScript 5.9: checkJs turns on allowJs when you leave allowJs out, and a file named jsconfig.json defaults allowJs to true anyway. Setting both does no harm and makes the intent plain to the next reader.

Is checkJs the same as // @ts-check?

They turn on the same checks. checkJs applies to every JavaScript file in the project; // @ts-check applies to the one file it is written in, and works even when checkJs is off.

Sources

Last reviewed 20 October 2026.