map.set() belongs to the built-in sass:map module. It returns a new map with one key written (added or updated). This page covers nested path updates, missing path segments, immutability, vs map.merge, and five compiled examples.
01
Concept
Write one key
02
Module
@use "sass:map"
03
Add / update
Same call
04
Nested path
Dart Sass 1.27+
05
vs merge
One key vs many
06
Practice
5 examples
Concept
What Is map.set()?
Sass maps are immutable. You cannot assign into a map like $map["primary"] = #fff. Instead, map.set() builds a new map with one key written:
If the key is new, it is added
If the key already exists, its value is replaced
All other keys are copied as they were
With Dart Sass 1.27+, you can pass a path of keys to update a nested value without rebuilding the whole tree by hand.
💡
Beginner tip
Think of rewriting one line on a sticky note and getting a fresh copy. The old note stays the same until you reassign: $map: map.set($map, $key, $value);
Source map. Never mutated—you always get a new map back.
$keys...
Keys
No
Optional path into nested maps (Dart Sass 1.27+). Omitted for a top-level set.
$key
Any
Yes
The key to write in the targeted map (last key before the value).
$value
Any
Yes
The value stored at $key.
⚠️
Argument naming note
Official docs describe nested calls as map.set($map, $keys..., $key, $value) for clarity. In practice Sass receives them as map.set($map, $args...)—the last argument is the value, and the one before it is the key being set.
Return value
Type
Situation
Result
Map
No path keys
Copy of $map with top-level $key set to $value
Map
With path keys
Copy of $map where the nested target has $key set to $value
Modules
📦 Loading sass:map
map.set lives in the map module. There is no legacy global map-set()—always load sass:map.
styles.scss
// Recommended — namespaced
@use "sass:map";
$tokens: map.set($tokens, "primary", #1d4ed8);
// Optional — bring members into the current namespace
@use "sass:map" as *;
$tokens: set($tokens, "primary", #1d4ed8);
// Optional — custom namespace
@use "sass:map" as m;
$tokens: m.set($tokens, "primary", #1d4ed8);
⚠️
Put @use first
@use rules must appear before most other rules. Keep @use "sass:map"; near the top of the file.
Details
🔢 Add vs Update
The same call handles both cases. Sass does not care whether the key already existed.
With Dart Sass 1.27+, pass keys before the final key/value to update a nested map. If a key along the path is missing or not a map, Sass stores an empty map there so the path can continue.
Nested map.set writes one leaf. Nested map.merge overlays a whole map onto a nested target. Pick set for a single token; pick merge for many keys at that location.
Compare
📋 map.set vs map.merge
map.set
map.merge
Writes
One key (or one nested leaf)
All keys from an overlay map
Best for
Single token updates
Layering defaults + overrides
Nested form
Path + final key/value
Path + overlay map
Legacy global
None
map-merge
Support
🛠 Compatibility
This is about Sass compilers, not browsers. Compiled CSS only contains the finished values you read from the updated map (for example with map.get).
Implementation
map.set() (2–3 args)
Nested path set
Dart Sass (1.23+)
Yes — preferred
1.27+ only
LibSass
No modern sass:map API
No
Ruby Sass
No modern sass:map API
No
Prefer Dart Sass for new work. Use current Dart Sass (1.27+) for nested path updates.
Cheat Sheet
⚡ Quick Reference
Goal
Code
Import map
@use "sass:map";
Set top-level key
map.set($map, "primary", #1d4ed8)
Set nested leaf
map.set($map, "a", "b", "c", $value)
Keep result
$map: map.set($map, $key, $value);
Read after set
map.get($map, $key)
Many keys at once
map.merge($map, $overlay)
Hands-On
Examples Gallery
Each example uses @use "sass:map". Open View Compiled CSS to see what Dart Sass emits (maps inspected via meta.inspect where needed).
📚 Getting Started
Official docs sample plus adding a brand-new key.
Example 1 — Update a Top-Level Key (Official Docs)
"theme" and "colors" did not exist, so Sass created nested maps for them, then stored "primary". Existing "meta" is preserved.
Applications
🚀 Real-World Use Cases
Single token patches — change one color, radius, or weight without rebuilding the map.
Nested design systems — update brand → colors → primary with a path set.
Mixin APIs — accept a user key/value and write it onto defaults.
Incremental builders — grow a config map step by step during compilation.
Safe path creation — let missing segments become empty maps when scaffolding tokens.
🧠 How Compilation Works
1
Write SCSS
Call map.set($map, $key, $value) after @use "sass:map".
Source
2
Copy & write
Dart Sass copies the map (and nested targets) and stores the new value.
Compile
3
New map returned
Reassign if needed, then read with map.get.
Result
4
✓
CSS sees values
Browsers never see map.set—only the finished CSS you emit.
Watch Out
⚠️ Common Pitfalls
Forgetting to reassign — map.set returns a copy; originals stay unless you assign the result.
Wrong argument order — the last argument is always the value; the one before it is the key being set.
Expecting a global map-set — there is none; load sass:map.
Nested path on old Sass — more than three arguments needs Dart Sass 1.27+.
Using set for many keys — prefer map.merge when overlaying a whole map of updates.
Pro Tips
💡 Best Practices
✅ Do
Use @use "sass:map" and map.set() in new SCSS
Reassign when updating a stored config variable
Use nested paths for leaf tokens in design-system maps
Prefer map.merge when writing many keys at once
Prefer Dart Sass 1.27+ for nested path set
❌ Don’t
Expect the browser to evaluate map.set
Assume originals mutate without reassignment
Look for a legacy global map-set()
Chain many single sets when one merge would be clearer
Rely on LibSass for the modern map module API
Summary
Key Takeaways
Knowledge Unlocked
Five things to remember about map.set()
Write one key—returns a new map; nested paths need Dart Sass 1.27+.
5
Core concepts
📝01
Call
map.set($map, $key, $value)
API
📦02
Module
sass:map only
@use
✎03
Effect
add or update
Rule
🔗04
Nested
path + leaf value
Safe
✓05
Immutable
reassign to keep
Tooling
❓ Frequently Asked Questions
map.set($map, $key, $value) returns a new map with $key set to $value. If the key already exists, its value is replaced. Extra keys before the final key/value (Dart Sass 1.27+) update a nested map along that path.
No. It returns a copy. Reassign if you need to keep the result: $tokens: map.set($tokens, "primary", #1d4ed8).
Yes on Dart Sass 1.27+: map.set($map, "a", "b", "c", $value) walks a → b and sets c to $value. Missing keys along the path become empty maps.
map.set updates one key (or one nested leaf). map.merge combines two whole maps. Use set for a single write; use merge when overlaying many keys at once.
No. Unlike map-get or map-remove, map.set is module-only. Load it with @use "sass:map" (or @use "sass:map" as * and call set()).
Official docs: if any key in the path is missing or points to a non-map, Sass sets that key to an empty map so the path can continue, then applies the final set.
Did you know?
Official Sass docs use the same Helvetica nested weights sample for map.get, map.set, map.merge, and the deep helpers—so you can compare read, write, and merge patterns on one familiar map shape.
map.set() is the everyday write helper for Sass maps: one key, one value, a new map returned. Use nested paths on Dart Sass 1.27+ for design-system leaves, reassign to keep results, and reach for map.merge when many keys change together.