Creating workflows
A workflow (sometimes called a "rule") watches your devices and does something when a reading crosses a line you set: raise an alert, email a group, or set a device's status. Your provider can build these for you, but if your plan includes workflow editing you can also build your own.
Do you have this? Workflow editing is a plan feature. If you don't see Operations -> Workflows in the sidebar, your provider hasn't enabled it for your workspace. Ask them if you'd like it turned on. Creating and editing workflows needs Operator or Workspace Admin access.
What you can build
When workflow editing is on, you can create workflows scoped to:
- A single device: just that one device.
- Your whole account (shown as "Whole account" in the scope picker, and part of some plans): one workflow that watches every device on your account, so a new device is covered the moment it arrives, with no per-device setup. Because it spans different device types, its field conditions use the universal fields: Signal Quality, RSSI, SNR, Battery, and the semantic fields (readings marked as the same kind across device profiles, such as Temperature (°F) or Humidity (%)). A semantic condition applies to the devices whose profile carries that reading; alert on other device-specific readings with a single-device workflow instead.
- A customized device profile (shown as "Device profile" in the scope picker, and part of some plans): if your plan lets you customize device profiles, one workflow can watch every device on one of your customized profiles - with that profile's full field catalog available in conditions. New devices on that profile are covered automatically. The picker lists only profiles you own; if you haven't customized one yet, do that first under Device profiles. If your plan doesn't include this, the option still appears but is locked, with a note about upgrading.
- A single gateway, or all your gateways: workflows that watch the gateways your devices report through rather than the devices themselves - a gateway going offline, or switching to battery power. The all-gateways scope covers gateways assigned to you later automatically. These behave a little differently from device workflows; see Gateway workflows below.
Profile-level workflows (ones that apply across a whole product line) stay with your provider. Everything you build lives in your workspace and only ever touches your own devices and gateways.
The builder
Open Operations -> Workflows -> New Workflow. You'll land on a canvas where you connect nodes into a small flow:
Trigger -> Condition(s) -> Action(s)
- The palette on the left lists every node you can add.
- Drag a node onto the canvas, or click it to drop it in.
- Connect nodes by dragging from the right edge of one to the left edge of the next.
- Click a node to set it up in the panel on the right.
- Delete a node with its X button or Backspace; delete a connection by clicking it and pressing Backspace.
- A node outlined in red has a problem; hover it to see what. You can save a draft with problems, but you can't switch it on until it's clean.
Triggers: what starts it
Every workflow starts with one Trigger. It's a pure starting point; the checking happens in the conditions you wire after it. There are two kinds:
| Trigger | When it starts |
|---|---|
| On uplink | Each time the device sends a fresh reading. This is the usual one. |
| Periodic | A regular sweep that checks for things that don't happen, like a device going quiet (for example "hasn't reported in 24 hours"). May not be available on every plan. |
| Certification | A daily sweep that fires when a tracked device's certification is within your chosen number of days of expiry (or already expired). Its Fire mode sets the cadence: Once fires a single time when the window is first crossed; Once per day per device keeps firing daily until the certification is renewed. May not be available on every plan. |
Older versions had triggers like "low battery" or "device offline" built in. Those are now expressed as a plain trigger plus a condition, for example On uplink plus a condition of battery < 20.
Conditions: what must be true
A Condition checks a reading against a value you choose and decides whether the nodes wired after it run.
To add one: drop a Condition node after your trigger, open its panel, pick the Field to test (for example temperature), choose an Operator, and type the Value. The field picker offers the fields that exist on the device, plus the built-in Signal fields (Signal Quality, RSSI, and SNR) that every device reports, and the built-in Battery field. For example, Signal Quality is less than 30 alerts you when a device's connection turns weak, and Battery is less than 30 warns you before a battery dies. Battery conditions use the device's latest known level and are also checked the moment a fresh battery reading arrives, so a sudden drop alerts you without waiting for the device's next regular reading. See Battery readings for how battery levels work.
Conditions available for a field value:
| Condition | Meaning |
|---|---|
| is / is not | Matches (or doesn't match) exactly the value you enter |
| contains | The reading contains the text you enter |
| is greater than / is at least | Above a number (or at/above it) |
| is less than / is at most | Below a number (or at/below it) |
| is between / is not between | Inside (or outside) a range you set with a lower and upper value |
For is / is not / contains, type the value the sensor reports for the state you care about. This is how you alert on a leak, whichever way the sensor reports it:
- A yes/no sensor sends
true- enter true. - A flag sensor sends
1- enter 1. - A status sensor sends text like
LEAKorWATER_DETECTED- enter that word.
Capitalization is ignored (so LEAK, Leak, and leak all match), and a number matches whether the sensor sends 1 or "1". If you're not sure what your sensor sends, open a recent reading on the device's Events tab and copy the value.
The greater/less/between conditions are for number readings (for example temperature is greater than 25).
is is an exact match. temperature is 25 runs only when the reading is exactly 25; a reading of 26 or 30 does nothing. To act when a reading goes above or below a number, pick is greater than, is at least, is less than, or is at most (temperature is greater than 25 runs on 25.5, 26, 30, and so on). The Condition panel shows this reminder when you set a number field to is.
A periodic workflow on a device uses a single time-based condition instead: how long the device has been silent. To watch a gateway going quiet, use a gateway workflow; a device workflow can't watch the gateway.
A few things to know about how conditions are checked:
- Workflows compare the adjusted reading, after any calibration set for the device, the same value you see in the app.
- If a reading is missing (the device didn't send that field), the condition counts as not met and the workflow doesn't run for that reading.
- Conditions work on simple values only: numbers, text, and yes/no.
Combining conditions
You don't type expressions like > 90 or < 30 into the value box; the value is a single number. Instead, how you wire the Condition nodes decides how they combine:
- Above one number or below another (outside a range): one Condition with is not between, a lower value and an upper value. For example,
temperature is not between 30 and 90passes when the reading is below 30 or above 90. is between is the opposite: it passes only inside the range. - Both must be true (and): wire the Conditions one after another (Trigger, then Condition A, then Condition B, then the action). The action runs only when every Condition on that chain passes.
- Either can be true (or): wire each Condition directly off the Trigger and connect both to the same action. The action runs when either branch passes, and it runs once per reading even if both pass. This does the same job as is not between when the two Conditions test the same field; use it when they test different fields (for example
temperature is greater than 90orhumidity is greater than 80). - Different actions for different cases: wire each Condition to its own action, as in the branching example below.
Branching: send different conditions to different actions
You can wire more than one Condition straight off the same Trigger, each leading to its own action. Every branch is checked on each reading, and only the branches that pass run their actions. This is how one workflow can react differently at different levels.
For a tank level sensor:
┌─ Condition: tank level below 30 ─→ Set status: Alert
Trigger (uplink) ┤
└─ Condition: tank level between 30 and 50 ─→ Set status: Warning
- A reading of 25 sets the device to Alert.
- A reading of 40 sets it to Warning.
- A reading of 60 matches neither branch, so nothing happens.
Because a device's status follows the workflow that set it, the level tracks the current band: a device at Alert that recovers into the 30 to 50 range is moved to Warning on its next reading.
To build it, drop the Trigger, drag a separate Condition off it for each band, and connect each Condition to its own action. Use is between (with an upper value) for a middle band, and is less than or is greater than for the open ends.
Two things to keep in mind:
- Leaving every band does not clear the status on its own. When a reading matches no branch (the tank at 60 above), nothing runs, so the last status stays until its Auto-clear timer expires or someone acknowledges the alert. Set Auto-clear on a status action if you want it to lapse by itself. See Responding to alerts.
- A Throttle node paces only what flows through it. If you place one before your Conditions, readings inside its window are dropped before the bands are even checked, so the device won't switch bands until the next reading passes. For status that should follow every reading, leave Throttle off this chain. Use Sustain instead if you only want to react after a reading stays bad for a while.
How a workflow runs: every matching reading acts
A workflow is simple on purpose: a reading arrives, the conditions are checked, and if they pass, every action on the passing branch runs - every time. A leak sensor reading "wet" on every update sends a text on every update. The platform never decides a notification is one too many; how often a workflow acts is entirely in your hands, with three levers:
- Throttle node: pace the flow where you place it (details below).
- Acknowledging the alarm: tell the platform you have it - notifications for that alarm pause until it actually recovers. See Responding to alerts.
- Max fires / hr: the safety cap for workflows that turn out noisier than expected.
Modulators: schedule, sustain, and throttle
These optional controls change when or how often a workflow acts.
- Schedule (node): only allow the workflow during certain days, hours, or months. Pick a timezone and tick the allowed periods. Outside the window the workflow stays quiet. A Schedule gates only the branch it sits on.
- Throttle (node): lets a reading through at most once per time window, measured from the last reading it let through; everything arriving inside the window is dropped unseen. Where you place it decides what gets paced: before a Condition, it limits how often the workflow even looks at readings (a reading that would have alarmed can wait until the next pass, up to one full window); after a Condition, every reading is still checked, but that branch's actions run at most once per window. Each Throttle paces only its own branch, and each device keeps its own clock.
- Sustain (hold before acting) (a setting on the Throttle node): the condition has to stay true for a set time before the alarm opens, which smooths out noisy sensors. For example "temperature above 25 for 10 minutes" rather than alarming on the first spike. If the reading drops back during the hold, the timer resets. It applies to the whole workflow, so only one Throttle node may set it.
- Recovery delay (in the settings bar, not a node): how long the conditions must stay clear before the alarm recovers. It's the mirror of Sustain: Sustain stops a brief spike from alarming, Recovery delay stops a brief dip from clearing the alarm. Use a few minutes on any reading that hovers around its limit. At 0, the alarm recovers on the first clear reading.
- Recovery email (in the settings bar, not a node) (plan feature): sends a follow-up email to the workflow's email recipients when the alarm recovers, so the all-clear reaches the same people as the alert. Needs at least one Email action on the workflow; certification workflows don't send recovery emails. If the switch is locked, it isn't part of your plan.
- Max fires / hr (in the settings bar, not a node): a safety cap on notifications per device per hour, for workflows that turn out noisier than expected. It never blocks the first notification when an alarm opens, and it doesn't schedule anything on its own - pacing on purpose is the Throttle node's job.
Example: uplinks every 5 minutes, condition "temperature above 25", no throttle: an over-limit sensor notifies every 5 minutes. Add a Throttle (30 min) between the Condition and the actions: readings are still checked every 5 minutes, but the actions run at most twice an hour. Move the Throttle before the Condition instead: the workflow only looks at one reading per 30 minutes.
Offline alerts: "no readings for N hours"
Workflows built on the time since last reading condition (under a periodic trigger) are checked every few minutes by the platform rather than waiting for a reading that isn't coming. While a device stays silent past your threshold, the workflow fires on every check - same rules as everything else: pace it with a Throttle, acknowledge the alarm to quiet it, and the moment the device reports again the alarm recovers (recovery email included if enabled). For gateways going quiet, see Gateway workflows below.
Gateway workflows: offline and power
A gateway workflow watches a gateway instead of a device. Pick Single gateway or All gateways in the scope picker when you create the workflow; the all-gateways scope covers every gateway on your account, including ones assigned to you later. Gateway workflows always run on the Periodic trigger (there are no readings to trigger on), and they offer exactly two conditions:
- Gateway offline (no reports for N hours): the gateway hasn't reported for longer than your threshold, checked every few minutes. This threshold is yours to set and is independent of the red/green status chip on gateway pages, which uses a fixed 30 minutes - so a gateway can show offline in the app before your workflow's threshold is reached.
- Gateway on battery power: the gateway has lost line power and is running on its backup battery. Power changes are picked up the moment the gateway reports them, so the alert doesn't wait for the next periodic check. An optional Only after this long on battery hold (in minutes) rides out brief power blips; at 0, the first battery report fires the alert. Not every gateway model reports its power source - the condition panel warns you when the gateway you picked has never reported one, because the workflow can't fire until it does.
Gateway workflows behave differently from device workflows in one important way: they notify once per incident. When the condition starts holding (the gateway goes quiet, or switches to battery), your email, SMS, and webhook actions run once, and then the workflow stays quiet until the gateway recovers - it reports again, or line power returns. On recovery the alarm closes (recovery email included, if enabled on the workflow), and the next incident notifies in full. There is nothing to acknowledge: gateway alerts arrive through the actions you wire and the workflow's fire log, and don't appear in the notification bell or set a status anywhere.
Because there are no readings or device statuses involved, gateway workflows offer the Send email, Send SMS, and Webhook actions only. Message fields offer gateway variables instead of device ones; see Message variables.
Actions: what happens
Drop an Action node at the end of a branch. You can add more than one on the same branch and they all run together. The actions available to you depend on your plan; commonly:
- Send email: sends an email to notification groups, individual email addresses, or both. Pick one or more of your workspace's notification groups (a Workspace Admin creates and maintains these), or type up to 5 individual addresses directly on the node; any address works, including people outside your workspace. Choose a severity (Info, Warning, or Critical) that sets the email's tone. When the workflow runs, every recipient is emailed once (someone in a group and also typed individually only gets one email), with automatic retries if delivery is briefly unavailable. Need more than 5 individual recipients? That's what notification groups are for.
- Send SMS (plan feature): sends a text to the SMS members of one or more notification groups, to up to 5 phone numbers typed directly on the node, or both. Numbers must be US, Canada, or Puerto Rico, and you confirm that the people you type in have agreed to receive alert texts. Choose a severity for the in-app entry, and optionally override the message body (message variables work here); the text always starts with your workspace name and ends with an opt-out footer, and the node shows a live estimate of how many message segments (and so how many SMS credits) each text will use. Every text uses credits, so pace a workflow that can fire repeatedly with a Throttle. If SMS isn't in your palette, your plan doesn't include it; ask your provider.
- Set device status: flags the device Info, Warning, or Alert, with an optional Auto-clear after (minutes) timer. This is what colors the pill on the device list, the device page, and Status widgets. Without Auto-clear, the status stays until someone acknowledges the alert. See Responding to alerts.
- Webhook (plan feature): POSTs a signed message to a URL you choose, so another system (a ticketing tool, an on-call service, your own software) hears about the alert the moment it fires. See The webhook action below.
Other actions (such as sending a downlink or firing a multi-cast group) depend on your plan; if one isn't in your palette or shows locked, ask your provider about enabling it.
Every time a workflow acts, it also adds an entry to your notification bell so there's always a record of what happened, even for non-email actions. The entry's severity is the highest one wired on the run: a Set device status of Alert shows as Critical, Warning as Warning, and an email action's severity counts too. See Responding to alerts.
The webhook action
The Webhook action tells another system about the alert by POSTing a small JSON message to a URL you choose. It's a notification, exactly like the email and SMS actions but aimed at software instead of an inbox: it goes quiet while an alarm is acknowledged, and it counts against Max fires / hr. It is not a live data feed; it sends one message per workflow fire, nothing more.
Setting it up on the node:
- URL: where to POST. Only
https://addresses are accepted. - Message (optional): the human-readable text inside the payload. Leave it blank for the default ("Workflow name fired for device name"), or write your own and use Insert variable to drop in live values; see Message variables.
- Signing secret: generated the first time you save the workflow and shown on the node with a copy button. Give it to whoever runs the receiving endpoint: every delivery carries an
X-Pulse-Signatureheader (an HMAC-SHA256 of the request body) they should verify before trusting the payload, plusX-Pulse-EventandX-Pulse-Deliveryheaders for routing and duplicate detection. Each webhook node has its own secret; to rotate it, delete the node and add it again. - Send test: POSTs a sample delivery to your URL right away, signed with the real secret, and shows the result on the node. The test uses the node as last saved, so save first; device readings are blank in a test, since no real reading triggered it.
What the receiver gets, as JSON:
{
"event": "workflow.fired",
"occurredAt": "2026-09-01T14:02:11Z",
"message": "Freezer temp high on Cold Room 2: 12.4",
"severity": "alert",
"rule": { "id": "...", "name": "Freezer temp high" },
"device": { "id": "...", "name": "Cold Room 2", "devEui": "..." }
}
On a gateway workflow, the payload carries a gateway object (id, name, gatewayEui) in place of device, and the default message names the gateway instead. Receivers can key off which object is present.
Deliveries are queued and retried automatically: if your endpoint is down, the platform tries again on a backoff schedule for about half an hour before giving up. The Fire log shows the outcome per fire ("1 webhook queued", or the reason nothing was sent). If the Webhook tile is locked or missing from your palette, it isn't part of your plan; ask your provider.
Message variables
Wherever a workflow text field shows Insert variable (the email subject and message overrides, the SMS message, and the webhook message), you can mix {{ }} tokens into your text and they're replaced with live values when the workflow fires:
| Variable | Inserts |
|---|---|
{{ rule.name }} | The workflow's name |
{{ triggering_device.name }} | The device that fired it |
{{ triggering_device.devEui }} | That device's DevEUI |
{{ firedAt }} | When it fired (ISO datetime) |
On top of these, every field on the device is offered as {{ triggering_device.<field> }} (for example {{ triggering_device.temperature }}), so a message can carry the reading that tripped the alarm: Freezer high on {{ triggering_device.name }}: {{ triggering_device.temperature }}. A variable whose value is missing on that reading renders as empty text.
On a gateway workflow, the menu offers gateway variables instead:
| Variable | Inserts |
|---|---|
{{ triggering_gateway.name }} | The gateway that fired it |
{{ triggering_gateway.gatewayEui }} | That gateway's EUI |
{{ triggering_gateway.serialNumber }} | Its serial number, when set |
{{ triggering_gateway.hours_since_stats }} | Whole hours since it last reported (offline alerts) |
{{ triggering_gateway.power_status }} | line or battery at fire time |
{{ triggering_gateway.battery_pct }} | Backup battery percentage, when reported |
{{ rule.name }} and {{ firedAt }} work the same on both.
Saving, switching on, and pausing
A workflow has three states:
| State | What it means |
|---|---|
| Draft | Editable, doesn't run. Use while you build. |
| Enabled | Live. Runs on matching readings. |
| Disabled | Saved but paused, without losing the configuration. |
Use the Enabled / Disabled switch at the top right. A workflow has to be problem-free before you can enable it.
Disabling withdraws everything the workflow asserted: any active alerts it set on devices are cleared for everyone, and its paused notifications reset. The confirmation dialog tells you exactly what will be cleared ("This workflow has 3 active alarms on 2 devices...") and offers Snooze 24h instead for the common case where you just want it quiet for a while. If an alert's condition is still true when you re-enable the workflow, the alert comes back on the device's next reading, with notifications.
Some workflows in your list may be marked Managed by your provider's workspace. Those watch your devices but were set up by your provider: you can open them to see how they work and view their history, but only your provider can change, pause, or delete them. Their alerts show up in your notifications and on your dashboards like any other. If one is too noisy for your team, use the switch next to its Managed by tag to mute it for your account: your notifications and dashboards go quiet for that workflow, while the workflow itself keeps running and your provider still sees everything. Ask your provider if one of them needs adjusting rather than just muting.
To pause a live workflow for a set time (a site visit, expected maintenance), use Snooze: the clock button next to the Enabled switch, in the workflow list and in the builder, with preset durations from 1 hour to 7 days. The workflow goes fully quiet for the window (notifications, device commands, status changes) and wakes on its own, without changing its Enabled state; active alerts stay exactly as they are. Resume now in the same menu ends a snooze early.
Monitoring: fire log and email deliveries
- Fire log (a tab on any workflow): every recent run where the workflow engaged, either fired or was held back by a Throttle, Sustain, or Snooze, with the device, the reading it saw, and the result. Readings that simply didn't meet a condition aren't logged; at fleet scale they would bury the real fires. Entries are kept for about 90 days.
- Email deliveries (a tab on any workflow with an email action): per-recipient outcomes, queued, sent, retrying, or failed with a reason. Useful when someone reports a missing alert email.
Testing a workflow
The most reliable test is a real reading. In order of convenience:
- Use Set Value on the device's Fields tab to feed in a test reading (if your role allows it). It runs through the workflow engine just like a real one.
- Send a downlink that makes the device report, if it supports a "request status" command.
- Wait for a natural reading, often the only option for sleeping sensors.
Frequently asked
Why didn't my workflow run? The condition looks right. Check the Fire log tab first: if you see throttled, sustained, or snoozed entries, the workflow engaged but a rate control held it back. If there's no entry at all, the condition didn't pass on that reading; the usual causes are a Schedule blocking it (wrong day or hour), the reading being missing, or the value not quite crossing your threshold. Compare the device's Fields tab against the condition.
Why is a workflow tagged "Unavailable"? The device or gateway it watches is no longer active in your workspace, so the workflow can't fire. The tag shows in the Workflows list and at the top of the workflow. A Send downlink action that targets a device that is no longer active is skipped the same way. The workflow runs again if the hardware is made active again; otherwise delete it or build a new one for the replacement.
How do I quiet a workflow that's too noisy? Switch it to Disabled to pause it indefinitely, or use Snooze for a short, self-clearing pause. You can also add a Throttle or a Sustain to calm it without turning it off.
Can one workflow start another? Not directly. For a chain, have one workflow set a device status and another react to that status.
Where do alert emails come from? From your workspace's branded sender, set up by your provider. If email isn't configured for your workspace yet, the workflow still runs but the email is skipped. Ask your provider if you expect emails and aren't getting them.