Skip Main Navigation

ECMAScript pattern matching proposal

Analyzing a potential future feature of JavaScript that could make testing object contents much easier

29 May 2020 · 4 min read

Over 4 years ago, I wrapped up the Learning ES6 series where I explained the majority of the features in ES2015 in great detail. It was a lot of fun and reignited my passion for JavaScript.

Instead of continuing with big huge releases as they did with ES2015, the TC39 committee decided to switch to a proposal process. A feature that has reached Stage 4 will be in the next year’s release of ECMAScript. Some proposals advance quickly, others move slowly, and some even stall and get abandoned.

I gave a talk at Node Summit 2018 entitled ES.next features that’ll make ya 💃🕺🏾 where I explained the proposal process while showcasing some features in various stages of the process. The majority of those proposals are now official features in ECMAScript, but there are always more proposals getting added. The one I just learned about from a coworker is the pattern matching proposal.

The proposal is currently sitting at Stage 1, meaning that the proposal has been formally introduced to the committee, it has a champion, and the committee will devote discussion time to it in future committee meetings. Here it is at a glance implementing a redux reducer:

const todos = (state = initialState, action) => {
  return case (action) {
    when {type: 'set-visibility-filter', filter: visFilter} ->
      ({...state, visFilter}),
    when {type: 'add-todo', text} ->
      ({...state, todos: [...state.todos, {text}]}),
    when {type: 'toggle-todo', index} -> (
      {
        ...state,
        todos: state.todos.map((todo, idx) => idx === index
          ? {...todo, done: !todo.done}
          : todo
        )
      }
    )
    when _ -> state
  }
}

There are several things to digest here.

First, the syntax (as it stands today) replaces switch with case:

return case (action) {

In addition, there’s also the return keyword before the case. This means that the entire case statement is an expression. It’s basically a multi-case, better-organized ternary statement.

The most interesting part and the crux of the whole proposal is the when clause:

when {type: 'set-visibility-filter', filter: visFilter} ->
  ({...state, visFilter}),

The when clause is much like _.isMatch from lodash which returns true if the object partially matches the specified match object. This is super powerful because it allows us to use a switch-like syntax for cases that require more complex matching. In this case (pun intended), we’re matching if the action has a type property that equals 'set-visibility-filter' and a filter property that equals visFilter.

What’s also different in this code fragment is the -> operator. It’s an arrow (->) instead of the fat arrow (=>) we use for arrow functions. Likely a different operator is needed in order for the parser to understand what exactly is happening. This isn’t a function. None of the examples in the proposal show it, but I’m assuming we’ll be able to wrap multiple statements in curly braces ({}) so that we can have multiple lines of logic before a return statement.

The last bit of unique syntax is here:

when _ -> state

This is basically the default case in a switch statement. It still uses the same when keyword, but uses an underscore (_) as the unknown or catch-all matcher. I’d be surprised if that sticks. 😄

This proposal draws heavily from corresponding features in Rust, F#, Scala, and Elixir/Erlang. Given that the proposal is only in Stage 1, it’s highly likely that the syntax will change as it moves through the proposal process. It’s also been sitting in Stage 1 since it was formally introduced in the May 2018 TC39 meeting. That’s over 2 years! Still, I’m holding out hope for it (or some version of it) to be approved and make it into the spec!

If you’re interested in knowing what other features are coming down the pike, peruse the TC39’s Active Proposals list.

Keep learning my friends. 🤓


Hi, I'm Ben Ilegbodu. 👋🏾

I'm a Christian, husband, and father of 3, with 15+ years of professional experience developing user interfaces for the Web. I'm a Principal Frontend Engineer at Stitch Fix, frontend development teacher, Google Developer Expert, and Microsoft MVP. I love helping developers level up their frontend skills.

Discuss on Twitter // Edit on Github


Attend upcoming minishops

Minishops by Ben Ilegbodu are fully-remote workshops that last about 3 hours. They’re highly-focused, covering only the concepts you want to learn so that you can level up your skills and get on with the rest of your day.