DEV Community

Caleb Collins-Parks for 15Five Engineering Blog

Posted on • Updated on

How to (temporarily!) ignore errors during a TypeScript migration

Update: You might want to skip this approach and use ts-migrate instead. It can automatically migrate your JS to TS and add @ts-expect-error comments to type errors you need to resolve by hand.


Last year at 15Five we started migrating our frontend react codebase to TypeScript. I went wild with regexes and Vscode's search/replace all feature, adding types and changing syntax in mass. But regex can only get you so far. There was still thousands of type errors, with each type needing to be reviewed manually. Some were easy to fix, others were much harder. This was going to take a lot of time. Time that I didn't have - my responsibility was DevOps after all, and I was migrating code to TypeScript in my free time. Frontend engineers also worked on the migration but they needed time to ship features.

I could've abandoned the migration and came back to it later. But without validation in our CI, untyped code would sneak in and leave a even bigger problem in the future. Luckily I came across tsc-silent!

GitHub logo evolution-gaming / tsc-silent

`tsc` with `--suppress` flag

tsc-silent

The purpose of the wrapper is to execute TypeScript compiler but suppress some error messages coming from certain files/folders. For example, this can be used to enable noImplicitAny in some parts of the project while keeping it disabled in others.

Installing

npm install -g tsc-silent
Enter fullscreen mode Exit fullscreen mode

Usage

tsc-silent --project <path> [--suppress config | --suppressConfig path] [--compiler path] [--watch]

Synopsis

--project, -p    Path to tsconfig.json
--compiler       Path to typescript.js
                 By default, uses `./node_modules/typescript/lib/typescript.js`
--suppress       Suppressed erros.
                 E.g. `--suppress 7017@src/js/ 2322,2339,2344@/src/legacy/`.

--suppressConfig Path to supressed errors config.
                 See documentation for examples.

--watch, -w      Run in watch mode.

--stats          Print number of suppressed errors per path and error code.

Suppress config

You have to pass either --suppress or --suppressConfig.

--suppress

Let's ignore error 7017 in src/js/ directory and errors 2322, 2339, 2344 in /src/legacy/:

tsc-silent -p tsconfig.json --suppress 7017@/src/js/ 2322,2339,2344@/src/legacy/
Enter fullscreen mode Exit fullscreen mode

or, ignore all errors in /src/legacy/ folder

tsc-silent -p tsconfig.json --suppress
Enter fullscreen mode Exit fullscreen mode

Tsc-silent lets you ignore certain TypeScript errors. By ignoring the errors that came from code not yet migrated, I could add TypeScript to our CI without error! For the errors that were fixed, tsc-silent would raise an error if they came back again.

This was quite easy to configure:

yarn tsc-silent --project tsconfig.json --suppress 2339,7006,2345,2739,2532,2307,7031,2741,2554,7053,7005,2740,2538,2531,2551,2571,2533,2305,2322,7015,2305,2722,7034,2724,2349,7016,1208,2749,2604,2363,2362,2605,2555,2464,2525,2559,2362@ff/static/modules 2305@node_modules --stats
Enter fullscreen mode Exit fullscreen mode

At this point you might be thinking "Darn, that's a lot of errors you're ignoring! Isn't that bad practice? Is it even worth it if so many errors are ignored"?

A valid concern, but even catching just a few errors is better than catching no errors at all. And this is the dumb approach - our resident code ninja (or "Frontend-related human being" as he humbly calls himself) Razh came up with a much smarter solution.

By passing in a configuration file to tsc-silent, we can choose what errors are ignored on which paths!

yarn tsc-silent --project tsconfig.json --suppressConfig tsc-silent.config.js --stats
Enter fullscreen mode Exit fullscreen mode

tsc-silent.config.js

module.exports = {
  suppress: [
    {
      pathRegExp: '/ff/static/modules/components',
      codes: [2322, 2339, 2345, 2362, 2363, 2532, 2555, 2739, 2769, 7016],
    },
    {
      pathRegExp: '/ff/static/modules/realtime_feedback',
      codes: [2322, 2345, 2769],
    },
    # other suppressions not shown
  ]
}
Enter fullscreen mode Exit fullscreen mode

Now for new folders we have full TypeScript error checking! For old folders we can be more selective about what errors we ignore too. As a bonus the tsc-silent output gives you information on exactly how many errors are left that you need to fix if you use the --stats option. In the example below you can see that there are a couple errors with only 1 instance left - those would be easy targets to fix and start validating against.

  {
    "codes": {
      "2322": 4,
      "2339": 2,
      "2345": 3,
      "2362": 2,
      "2363": 2,
      "2555": 1,
      "2739": 2,
      "2769": 11,
      "7016": 1
    },
    "pathRegExp": "/\\/ff\\/static\\/modules\\/components/",
    "total": 28
  },
Enter fullscreen mode Exit fullscreen mode

In conclusion, if you're migrating a large project to typescript tsc-silent can be quite useful. It lets you validate errors in CI even when your migration is not finished yet. Just don't use it as a excuse to ignore errors forever - there's a reason TypeScript raises an error, and even if it's not a bug it's still good to fix to increase the quality of your code. Someday we will finish up our migration and our need for tsc-silent will be gone. Until then, it's served us well.

Top comments (6)

Collapse
 
pengeszikra profile image
Peter Vivo

Hi! Are you know some tsc-silence solution which don't modify the code, just hide selected ts error from IDE (VSCode) ?

I using pipeline operator for js (react, webpack, babel, eslint) 2 years long, and now I add typescript to project, and everything is fine, even I can use pipeline operator in typescript just, mark as error (but everything compiled fine so two pre give same result):

import {FC} from 'react';
const jlog = data => JSON.stringify(data, null, 2);
const FooDebug:FC = () => {
 const foo = { name: 'foo', content: 42 }
 return (
  <section>
    <pre>{jlog(foo)}</pre>
    <pre>{foo |> jlog}</pre> 
  </section>
 );
}
Enter fullscreen mode Exit fullscreen mode
foo |> jlog
// The right-hand side of an arithmetic operation must be of type 'any', 'number', 'bigint' or an enum type.ts(2363)
Enter fullscreen mode Exit fullscreen mode
Collapse
 
caleb15 profile image
Caleb Collins-Parks

Not that I know of, sorry.

Collapse
 
nicoowr profile image
Nicoowr

Hey thanks for your article! Do you now if there is the opposite package, which could keep only specific errors?

Collapse
 
caleb15 profile image
Caleb Collins-Parks

I don't know if such a package exists but you could jury-rig something up like this:

tsc > typescript_errors.txt
MY_ERRORS=$(cat typescript_errors.tst | grep yourErrorId)
if MY_ERRORS: exit 1

(the above is pseudocode, you'd have to change it around a bit it to get it to work)

Collapse
 
nicoowr profile image
Nicoowr

Thanks I'll try this out!

Collapse
 
zanio profile image
ANIEFIOK AKPAN

Thanks very much. Exactly what i was looking for!