Skip to main content

What changed

The Rust SDK’s function registration is collapsed into a single entry point that mirrors Node and Python: RegisterFunction carries the handler plus all optional metadata. There are three constructors:
Value implements JsonSchema (via schemars), so untyped handlers go through new / new_async and emit a permissive AnyValue schema. No separate untyped constructor is needed. Builder methods (chainable, all consume self): RegisterFunction::http does no schema introspection, so the format setters are the only way to attach a schema for HTTP-invoked functions.

Handler error type fixed to IIIError

Previously, sync/async handler bounds were F: Fn(T) -> Result<R, E> where E: Display — the error type was generic. To enable clean type inference for Fn(Value) -> ... closures (where Ok(...) alone left E unbound), the bound is now F: Fn(T) -> Result<R, IIIError>. To smooth migration, IIIError now implements From<String> and From<&str>. Existing handlers returning Result<R, String> need to:
  1. Update the return type to Result<R, IIIError>.
  2. Either return IIIError::Handler(s) directly, or use ?-propagation: Err::<_, IIIError>("oops".into()) works, as does Err("oops".to_string())? once the function returns Result<_, IIIError>.

Removed

RegisterFunctionMessage::with_id / with_description remain on the wire-protocol type but are not used in the public registration API.

Why

Two BREAKING reshapes shipped together:
  1. The previous changelog entry already moved register_function_with to (id, handler, options) to match Node and Python. While doing the consumer migration, the redundancy between register_function, register_function_with, and the tuple form became evident: three call shapes, one trait machinery, two helper structs (IIIFn / IIIAsyncFn), and two traits (IntoFunctionHandler, IntoFunctionRegistration) — all serving roughly the same purpose with different ergonomics.
  2. With a single entry point, a single registration type, and three constructors (new, new_async, http), the surface area becomes one method and one builder. Schemars’ JsonSchema for Value impl lets new / new_async cover both typed and Value handlers without a separate untyped escape hatch.
The cost: every existing call site changes shape and Result<R, String> handlers migrate to Result<R, IIIError>. The benefit: documentation, IDE completion, and cross-SDK familiarity all converge on a single pattern.

Migration

Replace each registration call with the matching RegisterFunction::* constructor. RegisterFunction is exported from the crate root: use iii_sdk::RegisterFunction;. RegisterFunctionOptions is no longer exported — drop the import.