Diving Into ES2019 && ES2020

Each year ECMA International releases another version of the ECMAScript standardization with additional features and updates designed to make our lives as engineers easier. With the twelfth edition (ES2021) on the horizon, I wanted to take the time to break down the most exciting and useful additions, many of which you can use now, as well as discuss some changes under the hood that you may not be aware of. Before we get started, lets take a brief look at the history of JavaScript, as well as some information about the naming standardization associated with the language. Let's dive in!

NAMING THE STANDARD

If you’re a software engineer (or are currently on your journey to becoming one), you have likely heard of JavaScript’s many names and version numbers, including ES5, ES6, and ES2018, to name a few. So you may be thinking, why aren’t they called JS5 and JS2018 - where does the ES come from?

Though we’re all familiar with our beloved scripting language’s “street name,” JavaScript’s formal name is ECMAScript (European Computer Manufacturers Association Script). Since many companies have their own browsers (ex: Google Chrome and Mozilla Firefox) and therefore different codebases, the JavaScript standardization helps companies maintain consistency across platforms by providing a schematic (or roadmap) of features. So while each browser's JavaScript engine may be different, they all display similar information to the user.

ANOTHER YEAR => ANOTHER VERSION

Though ECMA International now releases a new version every year, this wasn’t always the case. With the first version of the ECMA standard being adopted by the ECMA General Assembly in June of 1997, we had sporadic (albeit necessary) updates to the language up until ES6 (ES2015), which provided a whole slew of additions that have become synonymous with the language, including fan favorites: Arrow Functions, Template Literals (my favorite), and the variable declarations const and let, to name a few.

Before getting to the new features of ES2019 and ES2020, I must preface that not every browser is compatible with the brand new additions laid out below (especially the ES2020 ones), as it’s up to the individual companies to update their own engines. Remember to check the browser compatibility on our favorite resource, MDN web docs for any conflicts.

Alright, now let's focus on the real reason why you’re here, to learn cool new tips and tricks that will take your engineering to the next level! We’ll start with the ES2019 additions:

ECMASCRIPT 2019

Array.prototype.flat()
The flat method creates a new array with all sub-array elements concatenated into it, up to the depth which you specify as an optional argument. When no argument is passed, the depth defaults to 1. Before this addition, you could go about flattening an array a variety of ways. However, most were complicated, clunky, and verbose, here’s an example:

arrayFlatVerbose

Now we have a built-in method that takes a recursive approach under the hood. Let’s see it in action:

arrayFlat

Ahh yes, much better. Clean, concise, and beautiful! Let’s move on.

Array.prototype.flatMap()
As you may have guessed, .flatMap() is a combination of the native .map() method with the new .flat() method, which first maps each element, then flattens to the depth of 1 and returns a new array. While this is identical to using .map() followed by .flat(), combining the two becomes slightly more performant, and of course, easier to read:

arrayFlatMap

Object.fromEntries()
I personally love this one. Object.fromEntries() will change the list of key-value pairs of an iterable, such as an Array or Map (or other objects implementing the iterable protocol) into an Object:

objectFromEntries

Object.fromEntries() is also the inverse of the Object.entries() method:

objectEntries

Ta-da!

String.prototype.trimStart() and String.prototype.trimEnd()
Now, you may be saying, “…but Matt, there are already methods to do this called .trimRight() and .trimLeft(),” and that’s absolutely correct, but ES2019 added .trimStart() and .trimEnd() so the method names can be more in line with their purposes (.trimRight() and .trimLeft() will remain aliases for .trimStart() and .trimEnd() respectively for web browser compatibility):

trimStart

trimEnd

ES2019 - UPDATED SYNTAX

Optional Catch Binding
Before ES2019, we were required to make an argument in a catch block, without one we get a ‘Syntax Error.’ However, there were times when this binding wouldn't be used, especially when you want your catch statement to do something that doesn’t care about the value that’s thrown:

catchBinding

Now, you can simply leave off the parentheses and it’s smooth sailing:

tryCatchNoBind

ES2019 - UNDER-THE-HOOD IMPROVEMENTS

Array.prototype.sort() is now a stable sort
Prior to Chrome 70 (which uses the V8 v7.0 JavaScript engine), Array.prototype.sort() used the unstable Quick Sort for arrays with more than 10 elements (and who are we kidding… that’s basically all of them!). It now uses one of the fastest sorting algorithms you probably have never heard of: Tim Sort! Which is a hybrid sorting algorithm derived from merge and insertion sort, which first sorts small pieces using Insertion Sort, then merges the pieces using Merge Sort.

arraySortStable

Fun fact, TimSort was created by Tim Peters (no relation…) in 2002 for use in Python, and was designed to perform well with many kinds of real-world data (Pythons claim to fame). With a best-case time complexity of O(n), an average and worst-case time complexity of O(n log n), it slightly edges out MergeSort who’s best, average, and worst-case complexities are a consistent O(n log n). Very cool!

ECMASCRIPT 2020

Now it’s time for the brand new ECMAScript 2020 (11th edition) features. While the 2019 features are certainly nice, the 2020 additions listed below are really exciting! Bear in mind, these are bleeding-edge and have not fully reached cross-browser stability. An example being Nullish Coalescing mentioned below, which is supported in the latest version of Chrome and only for Node.js 14.0.0+. It does not work for Internet Explorer (big surprise there...) or the mobile versions of Firefox, Opera, and Samsung Internet as of this writing. However, that’s not going to stop us from checking them out.

String.prototype.matchAll()
Who loves regular expressions? **cricket cricket**

Well… we now have a method that matches a string against a regular expression, and returns an iterator of all the resulting matches:

regexMatchAll

You’ll notice I included the global (‘/g’) flag in my RegEx example. This is actually required for the regular expression you’re testing against (which makes sense, as you’re searching for ALL occurrences!), otherwise, a TypeError will be thrown. So be vigilant!

BigInt
BigInt is a new built-in object that can represent whole numbers larger than the largest number reliably represented by JavaScript’s Number primitive (2^53 - 1 or the MAX_SAFE_INTEGER constant, which evaluates to 90,071,99,254,740,991). Before, Javascript was limited to this topmost number, check this out:

NumbersMax

Hmm, looks like we’ve hit our max. Until now!

With the normal Numbers object, we are unable to go above 90,071,99,254,740,992. Now with the BingInt data type, we can work with very large integers above this cap:

BigInt

You may have noticed I put an ‘n’ at the end of the number exceeding the MAX_SAFE_INTEGER constant. This is actually required by the JavaScript engine so that it understands this is a BigInt, so don’t forget!

Nullish Coalescing
Now we have the option to check for values that are just nullish (undefined or null) instead of outright falsey (undefined, null, false, NaN, 0, ‘’), using the new nullish coalescing operator (‘??’) syntax:

NullishCoalescing

Compare this to using the or (||) operator:

orOperator

Now the and (&&) operator:

andOperator

As you can see, when we only want to deal with logic involving null (**caugh BST’s and Linked Lists **caugh **caugh) or undefined, we now have a more explicit option for doing so.

Optional Chaining
The new optional chaining operator (‘?.’) allows us to read values nested within objects without having to validate each reference in the chain. Normally a reference error is thrown if your code has an erroneous path through object properties, as the reference would be nullish (meaning null or undefined). When that happens, it’s game over and your code won't run. Now, with the optional chaining operator, the thrown error is short-circuited and will simply return undefined. Let’s see it in action:

optionalChaining

Dynamic Import
This one’s fantastic. Dynamic Import allows code splitting, or the ability to import JavaScript files on-demand as modules into your application:

dynamicImport

Code splitting as the hallmark of Webpack and other module bundlers, but with a native Dynamic Import option with Javascript, you may no longer need to worry about taking the time setting up these additional compilers.

globalThis
This one’s a, “Wow, this should have been implemented long ago,” addition. globalThis is a universal way to access the global 'this' value, no matter what platform you’re coding for. Now, no matter if you’re working in Node, the browser, or a web-worker, which all have different namespaces (‘global’, ‘window’ or ‘self’ respectfully), you’ll be able to access the global object with one universal property:

globalThis

You’ll notice this example returns the Window object, as it was invoked within the console of my browser. If this were invoked within Node, you’d get Node’s respective global object!

IN CONCLUSION

You may have noticed a pattern by now. Though some of the additions to each year's update include brand new methods and under the hood improvements, many are simply syntactic updates that either rename or change syntax to be more streamlined with already existing options. Not all updates need to be as drastic as ES6, but having minor and ‘quality of life’ updates does make our lives as engineers more enjoyable, while also giving us the assurance that JavaScript is alive and well, and will not be going anywhere anytime soon.

Thanks again for joining me, and I hope you learned about some cool additions to our every updated language. The last thing to bear in mind, check browser compatibility prior to using these in production code and/or confirm your compilers (like Babel) are configured to handle the latest and greatest JavaScript has to offer.

Happy coding and thanks again!

Back to Blog

Related Articles

Finding My Confidence at Codesmith

My brother is a mechanical engineer. Outside of his profession, he is an inventor. I have watched...

2019 In Review - New Online Resources, Curriculum Updates, New Partnerships, Diversity and More!

Happy New Year! As 2020 kicks off, we want to take some time to reflect on Codesmith’s biggest...

React Router and Client-Side Routing

If you’ve been programming using React or have thought about using React, there is a high...