_.defaults
Fill in missing keys, keep the ones you have
- py_dict
- defaults
- DICT
_.defaults is the "give me the user's values, but fill the gaps with sane fallbacks" node. It takes a dict and one or more defaults dicts, and returns a dict where every key the input was missing gets filled in from the defaults - without ever overwriting a key the input actually has. The author's description: "Returns object after filling in its undefined properties with the first value present in the following list of defaults objects."
This is the config-merge pattern. You have a settings dict that may only set width and seed, you have a defaults dict that defines every other parameter, and you want a complete dict where explicit values win and everything else falls back. _.defaults is that merge, and it's the exact inverse of _.extend in this family: extend overwrites, defaults preserves.
How it works
Generated wrapper around underscore3, the bundled Python port of Underscore.js. Semantics:
- Only keys that are absent (undefined) in the destination get filled.
- Defaults are consulted in order - the first defaults object that has the missing key supplies it.
- Existing values - including an explicitly-set
None? - no: "undefined" means the key isn't set at all. If the input has a key with a value, that value wins, period.
So _.defaults({"a": 1}, {"a": 99, "b": 2}) → {"a": 1, "b": 2}. Explicit beats default, every time.
Inputs and output
py_dict(any type) - the destination dict whose missing keys get filled.defaults(any type) - one or more defaults objects; the tooltip notes JSON is allowed for arrays/objects, so you can wire in a JSON array of defaults dicts or a single one.- Output:
DICT- the merged result.
Installing it
Part of sfinktah/comfy-ovum ("comfy-ovum"):
- ComfyUI Manager: search "comfy-ovum", install, restart.
- Manual:
cd ComfyUI/custom_nodes && git clone https://github.com/sfinktah/comfy-ovum, restart.
No model downloads; light dependencies; underscore3 bundled in the repo.
Real-world shape
The classic Comfy use is a "settings" dict built from widgets upstream, merged over a full defaults dict so every consumer downstream can assume the complete set of keys exists. That's the pattern that saves you a dozen "if this key is missing" checks. Two caveats worth carrying: it's a shallow merge, so nested dicts are not recursively defaulted - that's what _.extendDeep is for - and the pack's README flags the whole underscore family as work-in-progress. For a flat config merge, though, this node does exactly one thing and does it predictably.
Inputs (2)
| Name | Type | Default | Description |
|---|---|---|---|
| py_dictopt | * | Primary input object (expected object). You can still pass any JSON-serializable value. Also accepts _.CHAIN to continue chaining. | |
| defaultsopt | * | defaults: JSON allowed for arrays/objects where applicable. |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| DICT | DICT | — |