JavaScript enumerator, or enums in plain JS

ImageImage
Rufat.jpg
written byChief Software Engineer I, EPAM Anywhere

I'm a Software Engineer with 10 years of commercial experience. Starting from the very first work day, I'm really into simplifying the complex, effective troubleshooting, failing fast, and learning from each small task. Therefore, I've played various roles as a system back-end engineer, system administrator, penetration tester, and finally a full-stack JS engineer. At the same time, I'm really keen on product and people management, I'm an engineering manager and technical product manager as well.

I'm a Software Engineer with 10 years of commercial experience. Starting from the very first work day, I'm really into simplifying the complex, effective troubleshooting, failing fast, and learning from each small task. Therefore, I've played various roles as a system back-end engineer, system administrator, penetration tester, and finally a full-stack JS engineer. At the same time, I'm really keen on product and people management, I'm an engineering manager and technical product manager as well.

Even though Enums are not supported in JavaScript natively, our Chief Software Engineer I, Rufat Khaslarov, offers a workaround for creating the enumeration type in JavaScript.

Let’s start with a question: Can numbers refer not to the amount but types of something?

The short answer is they can. A number can mean anything that we want, starting from types of cars (say, 1 is for truck) or even the status of a calculation (for instance, 1 is for started).

We might think that just having a variable is enough to understand it. Let’s have a quick look at the code below:

Wow! We can figure out the type of car! But what if we need to add more car types?

We can do this infinitely, and it will still work. These types won’t, however, be logically connected. They’ll be just separate constants that can be moved anywhere in your code. Handling variables this way is a little bit messy.

What are Enums?

With that as our background, let me introduce Enums (the enumeration type). With Enums, a developer can define a set of named constants. This makes it easier to document or create a set of distinct cases.

Using Enums might also mitigate spelling errors, as Enums are unchangeable. And it can make your code safer and cleaner (that is, searchable by name, with the ability to remove the magic values, and so on). Think of Enums as a kind of closed class, the instances of which are predefined statically.

There’s one small problem, though — Enums are not supported in JavaScript natively. However, since Enum is a pattern, it can be replicated via some techniques and features of native JavaScript.

Let’s take a look at two options of applying enumerator in JavaScript.

JavaScript enumerator: a basic representation

Step 1. Define a plain object literal (POJO)

As we mentioned before, Enums are name constants or, in other words, key-value pairs, so we can simply create an object.

The naming convention here is a matter of taste. The most widespread one is PascalCase for name, and UPPER_CASE for keys. But again, it’s up to you to decide how you want it to look.

Note that this still won’t replicate real Enums, because the values can be changed easily.

Step 2. Make sure that values are constant

In native JS, it’s possible to keep properties of the object unchanged. The first option is to use the defineProperty method, but in ES6 we’ve got the freeze method for doing so:

That’s it for basic scenarios. For more complex scenarios, where values should be objects or another logic should be included, we can develop our own Enum implementation.

JavaScript enumerator: an advanced representation

As we know, Enum is a class with predefined instances. So, let’s have a look at our implementation closely. We’ll use ES6, since older versions are not really relevant here:

In this case, we’re literally predefining the instances of the class that can be used in our business logic, and adding the toString method as an example of a custom logic for our enumeration.

We can make this example iterable, add more useful methods, and use the Proxy class for restricting the direct change of the properties, but I’ll leave that for your self-study since it goes beyond the scope of this article.

Other enumeration options

You can also use npm packages like enumify, which help implement the enum pattern itself, or an enum package that provides complete implementation with more features, like namespaces.

Finally, if you use TypeScript in your project, Enums are available right out of the box.

Rufat.jpg
written byChief Software Engineer I, EPAM Anywhere

I'm a Software Engineer with 10 years of commercial experience. Starting from the very first work day, I'm really into simplifying the complex, effective troubleshooting, failing fast, and learning from each small task. Therefore, I've played various roles as a system back-end engineer, system administrator, penetration tester, and finally a full-stack JS engineer. At the same time, I'm really keen on product and people management, I'm an engineering manager and technical product manager as well.

I'm a Software Engineer with 10 years of commercial experience. Starting from the very first work day, I'm really into simplifying the complex, effective troubleshooting, failing fast, and learning from each small task. Therefore, I've played various roles as a system back-end engineer, system administrator, penetration tester, and finally a full-stack JS engineer. At the same time, I'm really keen on product and people management, I'm an engineering manager and technical product manager as well.

our editorial policy

Explore our Editorial Policy to learn more about our standards for content creation.

read more