Typescript `enum` from JSON string Typescript `enum` from JSON string json json

Typescript `enum` from JSON string


If you are using Typescript before the 2.4 release, there is a way to achieve that with enums by casting the values of your enum to any.

An example of your first implementation

enum Type {    NEW = <any>"NEW",    OLD = <any>"OLD",}interface Thing { type: Type }let thing:Thing = JSON.parse('{"type": "NEW"}');alert(thing.type == Type.NEW); // true

Typescript 2.4 has built in support for string enums already, so the cast to any would be no longer necessary and you could achieve it without the use of String Literal Union Type, which is ok for validation and autocomplete, but not so good for readability and refactoring, depending on the usage scenario.


TS 2.9.2
My solution:

export enum Enums { VALUE1, VALUE2 }

and when I have value from API json:

 switch (response.enumValue.toString()) { //can be without toString if we have string value from JSON.    case Enums[Enums.VALUE1]:      ...    case Enums[Enums.VALUE2]:      ... }


In case someone's still looking at this question in 2021:

@Aaron wrote in the original question:

This looks nearly perfect, but there's still some heartache:

You still have to [...]

enum Color { RED = "RED", BLUE = "BLUE", GREEN = "GREEN" }type ColorMap = { [P in Color]: number; }declare const color: Color;declare const map: ColorMap;map[color] // Error: Element implicitly has an 'any' type because type 'ColorMap' has no index signature.// [...]

The equivalent code with enum Color replaced by string literal types work fine...

Yeah, I think I have OCD about this, I just want my perfect JS enums. :)

1. keyof typeof enumObj

Regarding,

The equivalent code with enum Color replaced by string literal types work fine...

use the typeof and keyof operators in chained conjunction.

type ColorKeys = keyof typeof Colortype ColorMap = { [P in ColorKeys]: number; } // will have strongly typed keys

No more implicit any when accessing map: ColorMap.
This will work with numeric enums as well (which can (and should more often than not) be const).

From Typescript Handbook - Enums at compile time:

Even though Enums are real objects that exist at runtime, the keyof keyword works differently than you might expect for typical objects. Instead, use keyof typeof to get a Type that represents all Enum keys as strings.

2. ts-enum-util

Check out ts-enum-util, which offers strongly typed interfaces to (likely) all your enum-related needs.