docs/how-to/trigger-functions-from-cli.mdx
Invoke a registered function on a running iii engine directly from the terminal, without writing application code or connecting an SDK.
iii trigger \
--function-id='<function_id>' \
--payload='<json>'
| Flag | Required | Default | Description |
|---|---|---|---|
--function-id | Yes | — | The ID of the function to invoke (e.g. iii::queue::redrive, orders::process) |
--payload | Yes | — | A JSON string passed as the function's input |
--address | No | localhost | The hostname or IP of the engine |
--port | No | 49134 | The engine's WebSocket port |
Examples of function IDs:
- `iii::queue::redrive` — builtin DLQ redrive
- `orders::process-payment` — a user-defined function
- `enqueue` — the builtin topic-based enqueue function
```bash
# Simple object
--payload='{"queue": "payment"}'
# Nested payload
--payload='{"orderId": "ord_789", "amount": 149.99, "currency": "USD"}'
# Empty payload (for functions that don't require input)
--payload='{}'
```
The CLI validates that the payload is valid JSON before connecting to the engine. Invalid JSON produces an immediate error.
The CLI connects to the engine over WebSocket, sends the invocation, and waits for the result. On success, the function's return value is printed to stdout as pretty-printed JSON:
```json
{
"queue": "payment",
"redriven": 12
}
```
If the function returns an error, it is printed to stderr and the process exits with code 1.
By default, iii trigger connects to localhost:49134. Use --address and --port to target a different engine instance:
iii trigger \
--function-id='iii::queue::redrive' \
--payload='{"queue": "payment"}' \
--address='10.0.1.5' \
--port=49134
The iii trigger command operates as a lightweight WebSocket client:
sequenceDiagram
participant CLI as iii trigger
participant Engine as iii engine
CLI->>Engine: WebSocket connect
Engine-->>CLI: WorkerRegistered
CLI->>Engine: InvokeFunction { function_id, data }
Engine->>Engine: Route to handler
Engine-->>CLI: InvocationResult { result }
CLI->>CLI: Print result to stdout
The CLI connects to the engine's WebSocket endpoint (the same protocol SDKs use), waits for the WorkerRegistered handshake, sends an InvokeFunction message with the function ID and payload, and prints the InvocationResult when it arrives.
Move all failed messages from the payment queue's DLQ back to the main queue:
iii trigger \
--function-id='iii::queue::redrive' \
--payload='{"queue": "payment"}'
{
"queue": "payment",
"redriven": 12
}
Trigger any function registered by your workers:
iii trigger \
--function-id='orders::process-payment' \
--payload='{"orderId": "ord_789", "amount": 149.99, "currency": "USD"}'
Use the builtin enqueue function to publish a message to a topic:
iii trigger \
--function-id='enqueue' \
--payload='{"topic": "order.created", "data": {"orderId": "ord_789"}}'
#!/bin/bash
QUEUES=("payment" "email" "notifications")
for queue in "${QUEUES[@]}"; do
echo "Redriving $queue..."
iii trigger \
--function-id='iii::queue::redrive' \
--payload="{\"queue\": \"$queue\"}"
done
| Scenario | Behavior |
|---|---|
Invalid JSON in --payload | Error printed immediately, no connection attempted |
| Engine not running (connection refused) | Error with the target address and port |
| Function not found | Engine returns a function_not_found error, printed to stderr |
| Function returns an error | Error body printed to stderr, exit code 1 |
| Connection drops before result | Error indicating the connection closed unexpectedly |