Skip to content

Instantly share code, notes, and snippets.

@clmrb
Last active December 20, 2025 19:28
Show Gist options
  • Select an option

  • Save clmrb/98f99fa873a2ff5a25bbc059a2c0dc6c to your computer and use it in GitHub Desktop.

Select an option

Save clmrb/98f99fa873a2ff5a25bbc059a2c0dc6c to your computer and use it in GitHub Desktop.
JavaScript enum function with working JSDoc autocompletion
/**
* @description
* Creates a frozen enumeration object where each key maps to its own string value.
* This is useful for defining a set of constant string values that can be referenced by name.
* This also avoids defining an object with duplicated string values manually.
* @template {string} T
* @param {...T} values
* @returns {{ [K in T]: K }}
* @example
* const Colors = Enum('Red', 'Green', 'Blue');
* console.log(Colors.Red); // "Red"
*/
function Enum(...values) {
// remove prototype's base functions/variables (credit @bayorm)
const result = Object.create(null);
for (const key of values) {
result[key] = key;
}
return Object.freeze(result);
}
// Usage
const Colors = Enum('Red', 'Green', 'Blue');
console.log(Colors.Red); // "Red"
@bayorm
Copy link

bayorm commented Dec 19, 2025

const result = Object.create(null) removes protos

@clmrb
Copy link
Author

clmrb commented Dec 19, 2025

const result = Object.create(null) removes protos

@bayorm Didn't know that, thanks, fixed !

@snnsnn
Copy link

snnsnn commented Dec 19, 2025

Here is typescript version with type-level immutability, if you think freeze is expensive:

export function Enum<const T extends readonly string[]>(
  ...values: T
): Readonly<{ [K in T[number]]: K }> {
  const result = Object.create(null) as { [K in T[number]]: K };

  values.forEach((key: T[number]) => {
    result[key] = key;
  });

  return result;
}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment