What’s New in TypeScript 3.9?

An overview of everything that just went live

Chameera Dulanga
May 26 · 4 min read
Photo by Corinne Kutz on Unsplash

TypeScript just released its second release for the year on May 12. It’s version 3.9, which is now the stable version. In this article, I’m going to point out some of the new and exciting features of TypeScript 3.9.


@ts-expect-error

Let’s take an example where we define a function that takes two strings as parameters.

printName(firstName: string, lastName: string) { 
console.log(firstName);
console.log(lastName);
assert(typeof firstName === "string");
assert(typeof lastName === "string");
}

Usually, TypeScript users will get a helpful red squiggle and an error message when they misuse this function, and JavaScript users will get an assertion error. But what will happen if we write a unit test to check this functionality?

expect(() => { 
printName(1234, 5678);
}).toThrow();

If our test is written in TS, it’ll throw an error like this:

printName(1234, 5678);
// ~~~
// error: Type ‘number’ is not assignable to type ‘string’.

As a solution for this, version 3.9 of TypeScript brings a new feature: // @ts-expect-error comments. If we put this comment before a code line as a prefix, TypeScript won’t report the error. But If there’s no error, TypeScript will inform that there’s an unnecessary comment in our code, like this: Unused '@ts-expect-error' directive.

Another use of this //@ts-expect-error comment is we can use it as a suppression comment. // @ts-ignore is an existing comment that’s used as a suppression comment — the main difference between these two is // @ts-ignore will inform if the following line is error-free.


Speed Improvements

Photo by chuttersnap on Unsplash

With the earlier versions of TypeScript, there were many complaints about the compilations and editing speed with packages like Material-UI.

With the new release, the TypeScript developing team has addressed this issue by optimizing several pathological cases involving large unions, intersections, conditional types, and mapped types and reduced 40% of the time in the Material-UI compilation. Also, they’ve worked on file renaming functionalities regarding editors like Visual Studio Code.


CommonJS Auto-Imports in JavaScript

Previously, TypeScript always expected ECMAScript-style imports regardless of your file type. But most developers are using the CommonJS-style require(); import instead of the ECMAScript-style modules when writing JavaScript files.

ECMAScript style: import * as fs from "fs";

CommonJS style: const fs = require("fs");

With the latest release, TypeScript now automatically detects the types of imports you’re using to keep your file’s style clean.


Improvements in Inference and Promise.all

In version 3.7, TypeScript came up with an update to the declarations of functions like Promise.all and Promise.race. But there were a few complications with this update since it caused regressions when mixing in values with null or undefined. An example is given below.

interface Bird{ 
fly(): void
}
interface Fish{
singKissFromARose(): void
}
async function animalBehaviours(birdBehaviour: Promise<Bird>, fishBehaviour: Promise<Fish| undefined>) {
let [bird, fish] = await Promise.all([birdBehaviour, fishBehaviour]);
bird.fly();
// ~~~~
// Object is possibly ‘undefined’.
}

Although fishBehaviour is the one containing undefined, it somehow has affected the birdBehaviour to include undefined as well. So this issue is also fixed with the 3.9 release of TypeScript.


Code Actions Preserve New Lines

Photo by Pankaj Patel on Unsplash

Many developers like to keep new lines between separate functionality code lines, but earlier TypeScript code refactoring didn’t preserve new lines. It almost removed all blank lines between code lines. With the latest release, TypeScript has worked on this issue, and now TypeScript code refactoring is preserving new lines in your code after running a refactor.


Quick Fixes for Missing Return Expressions

Sometimes we might forget to return the value from a function at the end of that function. So TypeScript is now providing a quick fix solution to add missing return statements.


Uncalled Function Checks in Conditional Expressions

After version 3.7, TypeScript checked for uncalled function checks in if conditions and reported errors. With the 3.9 release, this error-checking has further extended to ternary conditional statements as well.


Additional Minor Changes

Other than these changes, there are some minor changes like:

  • } and > are now invalid JSX text characters
  • export * is retained
  • Getters and setters are no longer enumerable
  • Type parameters which extend any are no longer acting as any
  • More libdom.d.ts refinements

Overall, these are the changes that we can see in the latest release of TypeScript. So if you’re a TypeScript lover, it’s always good to keep up to date with new updates that can make your coding life easier.

Better Programming

Advice for programmers.

Welcome to a place where words matter. On Medium, smart voices and original ideas take center stage - with no ads in sight. Watch
Follow all the topics you care about, and we’ll deliver the best stories for you to your homepage and inbox. Explore
Get unlimited access to the best stories on Medium — and support writers while you’re at it. Just $5/month. Upgrade

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store