Skip to main content

Remote Procedure Call (RPC)

Receive RPC calls from the App SDK and return a response. Your app sends a request, your device processes it and replies.

Overview​

RPC uses a request/reply pattern — your app sends a request, your device processes it and sends a response. Unlike commands, the caller waits for a response.

API​

listen()​

Register a handler for incoming RPC calls matching a given name.

await device.rpc.listen(name, callback)
ParameterTypeDescription
namestringThe RPC name to listen for
callbackfunctionCalled when an RPC request arrives. Receives an RpcRequest object

Throws DuplicateListenerError if a listener with the same name is already registered

Throws ValidationError if name contains invalid characters

Naming rules

Names can only contain letters, numbers, hyphens, and underscores (A-Z, a-z, 0-9, -, _). This applies to RPC names, command names, and event names.

off()​

Unregister a previously registered RPC listener.

await device.rpc.off(name)

Returns true if the listener was removed, false if no listener existed for that name

The RpcRequest Object​

When an RPC call arrives, your callback receives a request object.

Property/MethodDescription
request.payloadThe data sent by the caller
request.respond(data)Send a success response back
request.error(data)Send an error response back

Every RPC handler should call either respond() or error() — the caller is waiting for a reply.

Listen for RPC Calls​

await device.rpc.listen("get_status", (request) => {
const status = {
uptime: process.uptime(),
temperature: readSensor(),
firmware: "1.2.0",
};

request.respond(status);
});

Responding with an Error​

If the request can't be fulfilled, use request.error() instead of request.respond().

await device.rpc.listen("restart_service", (request) => {
const { service } = request.payload;

if (!isValidService(service)) {
request.error({ message: `Unknown service: ${service}` });
return;
}

restartService(service);
request.respond({ restarted: service });
});

Remove a Listener​

await device.rpc.off("get_status");

Safe to call even if no listener exists for that name.

Error Handling​

// registering the same name twice throws DuplicateListenerError
await device.rpc.listen("get_status", handler);

try {
await device.rpc.listen("get_status", anotherHandler);
} catch (err) {
// DuplicateListenerError: "get_status" is already registered
console.error(err.message);
}

To replace a listener, call off() first, then listen() again with the new handler.