The Complete node is a quiet utility in Node-RED that pays off once your flow grows beyond a handful of nodes. It watches a target node, catches its final payload, and hands that value to whatever you wire next. For anyone running Node-RED on a Raspberry Pi or home server, that single hook can clean up messy flows fast.
The Complete node triggers once its monitored counterpart finishes, then passes the resulting payload downstream. It is a tidy way to start follow-up logic without polling or guessing when a job is done.
Quick take
- The Complete node fires after a target node finishes execution and forwards that node's payload.
- A typical setup uses an Inject node to start, a Function node to count and time out, and a Debug node for output.
- The Count and Trigger function increments once per second and fires after a five-second timeout.
- A second Function node formats the payload before it reaches the Debug pane.
- Useful for anyone running local automation stacks that need a clear "finished" signal.
How the flow fits together
Drop in an Inject node to kick things off, then a Function node that acts as both counter and timer. That node starts a one-second interval, updates the node status text on the editor canvas as it ticks, and uses a five-second setTimeout to stop the count, change the status colour to green, send the final count as msg.payload, and call node.done().
Attach a Debug node to see the live count in the sidebar. The Complete node sits between the count function and your downstream logic. Wire the second Function node to the Complete node's output, and you get a string that reads "Count completed: X seconds". The Inject button starts it all, and the Debug pane shows the final formatted message.
Why it matters
Without the Complete node, you see two ugly patterns. Either a flow keeps firing the next step on every tick, which wastes CPU and floods downstream logic with intermediate values, or you rig up a separate delay node and hope the timing lines up. The Complete node skips both problems because it reacts to a real "I am done" signal, not a guess.
It also lines up with how Node-RED developers reason about long-running operations: start a job, do work, signal completion, branch off the result. Once you internalise that shape, debugging gets quicker and flows stay readable.
Our analysis
The upside is real for builders using Node-RED as a local automation backend. You can time-bound a sensor read, push a snapshot downstream, and only trigger follow-up actions once data is final, instead of on every intermediate tick.
The trade-off is that the Complete node is not universal. It only fires for nodes that explicitly call node.done(), and not every community node does that. If you lean on third-party nodes, check the readme before assuming the hook is available. For built-in core nodes, coverage is solid.
Another consideration: this approach runs locally with no cloud round-trip, which is the right call for a home network full of IoT devices. It also means your downstream app needs to read from a local broker or reverse-proxied endpoint, which adds a small setup cost. Worth it for privacy; less convenient if you need off-site access.
Who should care
Automation hobbyists** — If you run Node-RED on a Pi or mini-PC feeding Home Assistant or MQTT dashboards, the Complete node is the cleanest way to signal "job finished" without guessing at delays.
Flow designers** — If your current workaround involves chained Delay nodes or polling loops, this replaces guesswork with a real completion signal.
Third-party node users** — If you rely on community nodes, verify they call node.done() before wiring them to a Complete node. A small wrapper function can mimic the pattern if they do not.
A worked example
Say you have a soil moisture sensor wired to a Pi running Node-RED, and you want a clean alert only after a 30-second sampling window ends, not every time the reading shifts. Set up an Inject node that triggers every hour. A Function node collects readings once a second, averages them, and calls node.done() after the 30th sample. A Complete node hands that average to a second Function node, which builds a JSON message for an MQTT broker. Your MQTT client pushes that final reading as a single notification. One alert per hour, one clean payload, no noise.
What to watch next
Keep an eye on whether popular community nodes you rely on have been updated to call node.done() in their long-running paths. If not, a small wrapper function is usually enough to mimic the pattern. Also worth tracking: official Node-RED releases that tighten the Complete node's behaviour or expose more completion events. For now, treat it as a precision tool for flows where the difference between "still running" and "finished" matters.
Key takeaways
- The Complete node reacts to a real completion signal, not a timer guess, which keeps downstream steps from firing early.
- It only works with nodes that call node.done(), so check custom or community nodes before relying on it.
- It is a clean way to batch sensor data and push a single final update downstream instead of every intermediate tick.
- Local execution suits home automation stacks but requires a local broker or reverse proxy for remote access.
Frequently asked questions
What does the Complete node actually do in Node-RED?
It waits for a monitored node to finish its work, then passes that node's final msg.payload to whatever you connect next.
Do all Node-RED nodes work with the Complete node?
No. A node has to call node.done() when finished. Built-in core nodes often do, but third-party nodes vary, so check the documentation.
Can I use the Complete node for home automation projects?
Yes. It is handy when you want a single clean payload sent to an MQTT broker, Home Assistant, or a dashboard after a sampling or timing job wraps up.
What is the role of node.done() in the example flow?
It marks the counting function as finished after the five-second timeout, which is the signal the Complete node is waiting for.
Is the Count and Trigger pattern reusable beyond the example?
Yes. Swap the counting logic for sensor reads, API polls, or file scans and the same shape works for any bounded job.
Source: creatifwerks.com