Skip to content

useService

Wraps a ROS service client. Unlike useTopic, calls are imperative: invoke callService whenever you need to, and loading / result / error reflect the most recent call.

tsx
import { useService } from "roshooks";

interface AddTwoIntsRequest {
  a: number;
  b: number;
}

interface AddTwoIntsResponse {
  sum: number;
}

const { callService, loading, result, error } = useService<AddTwoIntsRequest, AddTwoIntsResponse>({
  name: "/add_two_ints",
  serviceType: "rospy_tutorials/AddTwoInts",
});

Options

OptionTypeDescription
namestringThe service name, e.g. "/add_two_ints".
serviceTypestringThe service type, e.g. "rospy_tutorials/AddTwoInts".

Returns

FieldTypeDescription
callService(request: TRequest, timeout?: number) => Promise<TResponse>Calls the service. Resolves with the response, or rejects with an Error wrapping rosbridge's failure message.
loadingbooleantrue while a call is in flight.
resultTResponse | nullThe response from the most recent successful call.
errorstring | nullThe failure message from the most recent failed call.
serviceService<TRequest, TResponse> | nullThe underlying roslib.js Service instance, or null before it's created.

Example

tsx
function AddTwoInts() {
  const { callService, loading, result, error } = useService<AddTwoIntsRequest, AddTwoIntsResponse>({
    name: "/add_two_ints",
    serviceType: "rospy_tutorials/AddTwoInts",
  });

  return (
    <div>
      <button disabled={loading} onClick={() => callService({ a: 2, b: 3 }).catch(() => {})}>
        2 + 3
      </button>
      {result && <p>sum: {result.sum}</p>}
      {error && <p role="alert">{error}</p>}
    </div>
  );
}

TIP

callService returns a promise, so an unhandled rejection is possible if a call fails and nothing awaits or catches it. Either await it in a try/catch, or attach a no-op .catch() if you're only interested in the error field.

See Testing for how to simulate service responses without a real rosbridge server.

Released under the BSD-3 License.