Contracts
import { z } from "zod";
export const contracts = {
user: {
getUser: {
transport: "grpc",
service: "user.v1.UserService",
rpc: "GetUser",
request: z.object({ id: z.string() }),
response: z.object({ id: z.string(), name: z.string() }),
deadlineMs: 5_000,
},
},
};transport: "grpc" does not compile until this package is installed — the
module augmentation is what adds it to typefetch's registry. Once it is, a gRPC
route is fully checked, including that it may not carry path, method,
bodyType or responseType. None of those mean anything for a unary RPC.
Fields
| Field | Required | Meaning |
|---|---|---|
service | yes | Fully-qualified service, "user.v1.UserService" |
rpc | yes | Method name, "GetUser" |
deadlineMs | no | Server-side deadline (Connect-Timeout-Ms / grpc-timeout) |
codec | no | Switches this RPC to binary protobuf — see below |
deadlineMs is not RequestOptions.timeout. The timeout aborts locally; a
deadline asks the server to stop working, which is what stops an abandoned
query from holding a database connection. Setting both is normal — make the
local timeout the more generous one.