Block trigger
Fire a workflow every N blocks on a network — keeper duties, per-block checks, periodic onchain maintenance that should track chain time rather than wall time.
workflows:
keeper:
trigger:
block:
every: 10 # every 10th block
network: ethereum
steps:
- id: upkeep
read:
contract: Keeper
network: ethereum
function: "checkUpkeep()"
assert: "${{ output }}"
- id: perform
send_transaction:
network: ethereum
relayer: keeper
contract: Keeper
function: "performUpkeep()"| Field | Required | Description |
|---|---|---|
every | ✅ | Fire every N blocks (>= 1, validated). 1 fires every block |
network | ✅ | A declared network |
The trigger context
| Path | Description |
|---|---|
trigger.args.block_number | The block that fired |
trigger.args.network | The network name |
Semantics
- One poll per network — workflows sharing a network share the head poll
(~2s interval); every newly observed block number
bwithb % every == 0fires. - Exactly-once — the claim key is derived from the block number
(
block:{network}:{number}), so poll overlap and restarts are duplicates, never double fires. - Catch-up is capped — the first poll after boot only anchors the head (no historical firing). After an RPC outage, every block in the observed gap is considered, capped at the newest 100 blocks with a warning — a long outage on a fast chain does not replay thousands of runs.
For "every block, act on the events in it", prefer an event trigger — it decodes and filters for you. For "poll a value until it crosses a line", prefer a read trigger — it is edge-triggered.