_.findWhere
_.findWhere and its properties shorthand
- list_or_dict
- properties
- *
_.find asks "first element where this predicate is true." _.findWhere is the same idea with training wheels: instead of writing a truth test, you hand it a properties object and it returns the first element whose fields match all of those key-value pairs. One object of criteria, no function required.
It's one of the _.* nodes in sfinktah/comfy-ovum, the auto-generated wrappers around underscore3 (a Python port of Underscore.js). Family design is uniform: a primary collection input, the method's arguments, one output.
The match-the-whole-record trick
The killer feature here is that matching is all-fields. Give it {"on": true, "mode": "fast"} and it only matches elements where both are true - that's object-shorthand matching with the AND semantics, no lambda needed. That's a big deal in a graph where you can't type Python functions into a widget. Instead you drop a JSON object into the properties input and let it do the work.
The inputs that matter
- list_or_dict - the collection to search (loose
*; also accepts a_.CHAIN). - properties - the match criteria. An
ANYinput that takes a JSON object of key-value pairs, e.g.{"enabled": true}. This one has no separate_jsonstring fallback - the input is the JSON-able object, so wire in a dict or type the JSON directly if your frontend lets you.
Output is a loose *: the first element that matches every property, or None if nothing (or an empty list) does.
Where it shines
Lists of dicts are everywhere once you start treating ComfyUI as a data-processing graph - tag objects, config records, per-item metadata. _.findWhere is the least-fiddly way to pull "the first config with active: true" out of that pile. When your criteria are values, not computations, prefer this over _.find; you skip the predicate entirely.
Install
Same pack, same steps. ComfyUI Manager, search "comfy-ovum", or:
cd ComfyUI/custom_nodes
git clone https://github.com/sfinktah/comfy-ovum
Restart, find it under ovum/underscore. No models, no downloads.
Honest warnings
Family-wide README disclaimer: work in progress, not for production. A practical gotcha: the properties object must actually be parseable as JSON - an object with a key whose value is None won't match a Python None in your data the way you might hope. And feeding a _.CHAIN in returns a chain out; remember _.value to unwrap. If you need "match on any field" rather than all, _.find with an iteratee is the escape hatch.
Inputs (2)
| Name | Type | Default | Description |
|---|---|---|---|
| list_or_dictopt | * | Primary input object (expected collection). You can still pass any JSON-serializable value. Also accepts _.CHAIN to continue chaining. | |
| propertiesopt | * | properties: JSON allowed for arrays/objects where applicable. |
Outputs (1)
| Name | Type | Description |
|---|---|---|
| * | * | — |