How to turn key–value pairs into objects, invert maps, filter entries, and unlock elegant patterns in modern JavaScript.

Introduction
You’ve probably used Object.entries
to turn an object into an array of [key, value]
pairs. But what about the reverse?
That’s where Object.fromEntries
comes in. Introduced in ES2019, it does the opposite of Object.entries
:
const entries = [["id", 1], ["name", "Ali"]];
const obj = Object.fromEntries(entries);
console.log(obj);
// { id: 1, name: "Ali" }
This tiny method unlocks powerful transformations: filtering objects, flipping keys and values, converting Maps into plain objects, and more — all in a few lines of clean, functional-style code.
Let’s dive into how to use it for fun and profit.
1. The Basics
const pairs = [["a", 1], ["b", 2]];
const obj = Object.fromEntries(pairs);
console.log(obj); // { a: 1, b: 2 }
- Input: iterable of
[key, value]
pairs (like arrays, Maps). - Output: a new object with those pairs as properties.
- Keys are converted to strings (unless
Symbol
).
2. Converting a Map
to an Object
const map = new Map([
["id", 42],
["name", "Umar"]
]);
const obj = Object.fromEntries(map);
console.log(obj); // { id: 42, name: "Umar" }
👉 Useful when you need a plain object for JSON serialization or React props.
3. Filtering Objects Elegantly
Combine with Object.entries
to filter out properties.
const env = { NODE_ENV: "production", DEBUG: false, SECRET: null };
const filtered = Object.fromEntries(
Object.entries(env).filter(([k, v]) => v != null)
);
console.log(filtered);
// { NODE_ENV: 'production', DEBUG: false }
👉 Much cleaner than mutating or manually deleting keys.
4. Transforming Values
Use map
on entries to transform values.
const prices = { apple: 1, banana: 2 };
const withTax = Object.fromEntries(
Object.entries(prices).map(([k, v]) => [k, v * 1.1])
);
console.log(withTax);
// { apple: 1.1, banana: 2.2 }
👉 Great for computed fields, scaling values, or sanitizing data.
5. Renaming Keys
You can even change keys during transformation.
const user = { fname: "Rahmat", lname: "Ali" };
const renamed = Object.fromEntries(
Object.entries(user).map(([k, v]) => [
k === "fname" ? "firstName" : k === "lname" ? "lastName" : k,
v
])
);
console.log(renamed);
// { firstName: 'Rahmat', lastName: 'Ali' }
👉 Useful when adapting API responses to frontend conventions.
6. Flipping Keys and Values
const obj = { a: 1, b: 2, c: 3 };
const flipped = Object.fromEntries(
Object.entries(obj).map(([k, v]) => [v, k])
);
console.log(flipped);
// { '1': 'a', '2': 'b', '3': 'c' }
👉 Handy for lookup tables.
7. Removing Sensitive Data
const user = { id: 1, name: "Ali", password: "secret" };
const safe = Object.fromEntries(
Object.entries(user).filter(([k]) => k !== "password")
);
console.log(safe);
// { id: 1, name: 'Ali' }
👉 Safer than manual delete
—and works well in functional pipelines.
8. Combining with Array Methods
Transform arrays of objects into a single lookup.
const users = [
{ id: 1, name: "Ali" },
{ id: 2, name: "Umar" }
];
const byId = Object.fromEntries(users.map(u => [u.id, u]));
console.log(byId);
// { '1': { id:1, name:'Ali' }, '2': { id:2, name:'Umar' } }
👉 Perfect for building dictionaries for fast lookups in React or Redux.
9. Real-World Use Cases
- API responses: Normalize data into lookup objects.
- Filtering configs: Drop
null
/undefined
safely. - Form handling: Map field arrays into objects for submission.
- Localization: Build key → translation objects from CSV rows.
- Testing: Quickly mock objects from arrays of values.
10. TypeScript Patterns
A) Strongly typed transforms
function mapValues<T extends object, U>(
obj: T,
fn: (value: T[keyof T], key: keyof T) => U
): { [K in keyof T]: U } {
return Object.fromEntries(
Object.entries(obj).map(([k, v]) => [k, fn(v as T[keyof T], k as keyof T)])
) as { [K in keyof T]: U };
}
const scores = { a: 1, b: 2 };
const doubled = mapValues(scores, v => v * 2);
// { a: 2, b: 4 }
B) Partial filtering
function filterKeys<T extends object>(
obj: T,
predicate: (key: keyof T, value: T[keyof T]) => boolean
): Partial<T> {
return Object.fromEntries(
Object.entries(obj).filter(([k, v]) =>
predicate(k as keyof T, v as T[keyof T])
)
) as Partial<T>;
}
11. Edge Cases & Gotchas
- Keys become strings: Numeric keys (
1
) →"1"
. - Symbols not supported in
Object.fromEntries
. - Order: Keys preserve the array order but not guaranteed for object access.
- Prototype pollution risk: Guard when working with untrusted keys (
__proto__
,constructor
).
Safe guard:
const blocked = new Set(["__proto__", "constructor", "prototype"]);
const safeObj = Object.fromEntries(
entries.filter(([k]) => !blocked.has(k))
);
Conclusion
Object.fromEntries
is the perfect complement to Object.entries
—turning arrays (or Maps) of pairs back into objects. With it, you can:
- Filter and transform objects declaratively.
- Convert between Maps and objects.
- Build fast lookup tables.
- Cleanly strip or rename keys.
Pro Tip: Use Object.entries
+ array methods + Object.fromEntries
as a pipeline for object transformations. It’s functional, expressive, and avoids messy loops.
Call to Action (CTA)
What’s your favorite trick with Object.fromEntries
—filtering configs, renaming keys, or building lookups?
Drop your use case in the comments, and share this with a teammate who still mutates objects manually.
Leave a Reply