RPC result serialization
When QA runs a service step, the web app sends rpc:call with args and expects a JSON RPC_RESPONSE (result, label, …). Your handler might return a Date, bigint, a class instance, or a very large object. rpcSerialization (type RpcSerializationOptions) tells the SDK how to prepare that traffic: optional checks on inputs, normalize outputs, cap size, and optionally enforce JSON Schema you attached at registration.
Default: everything is off. The handler return value is passed through (the transport still JSON-encodes what it can). Turning options on is opt-in and only affects the RPC path—not real HTTP responses from Express or Postman.
What you get when you enable it
| Benefit | Which flag |
|---|---|
QA never receives values that break JSON (e.g. bigint, Date, ORM entities) | enabled: true |
| Huge results are rejected before they hit the browser | enabled: true + maxUtf8Bytes |
| Bad test inputs are rejected before your handler runs | validateParamsJsonSchema: true + paramsJsonSchema on the entry |
| Handler return shape is checked after invoke (contract tests on the server) | enabled: true + validateReturnJsonSchema: true + returnJsonSchema on the entry |
Schemas come from cat / catModule options or registerParamsJsonSchema / registerReturnJsonSchema—serialization config only turns enforcement on.
How executeRPC uses rpcSerialization
On each rpc:call, after the function is found and arg count matches the catalog:
- Params schema (optional) — if
validateParamsJsonSchemais on and the entry hasparamsJsonSchema, validateargsfirst. On failure →INPUT_SCHEMA_INVALID(handler not run). - Invoke — run the handler and get the return value.
- Serialization (optional) — if
enabled, normalize the result to JSON-safe data and enforcemaxUtf8Bytes. On failure →RESULT_NOT_SERIALIZABLE. - Return schema (optional) — if
enabledandvalidateReturnJsonSchemaand the entry hasreturnJsonSchema, validateresult. On failure →RETURN_SCHEMA_INVALID(handler already ran). - Success — build
RPC_RESPONSEwithstatus: 'ok'.
Other errors (FN_NOT_FOUND, WRONG_ARG_COUNT, INVOKE_TIMEOUT, etc.) are unchanged; see RPC error codes.
RpcSerializationOptions
| Field | Default | What it does |
|---|---|---|
enabled | false | When true, serializeRpcResult deep-clones the handler result into JSON-safe plain data before building RPC_RESPONSE. |
maxUtf8Bytes | 4 * 1024 * 1024 when enabled | After normalization, JSON.stringify(result) must fit in this UTF-8 budget or RPC returns RESULT_NOT_SERIALIZABLE. |
validateParamsJsonSchema | false | Before invoke, validate args against paramsJsonSchema if present. Does not require enabled. |
validateReturnJsonSchema | false | After serialization, validate result against returnJsonSchema if present. Requires enabled: true. |
Turn it on
On the host (attachCatRPC)
Recommended for cat-demo–style servers:
import { attachCatRPC } from '@gloocan/cat-inspector/socket-io'
attachCatRPC(io, {
scanRoots: [/* … */],
rpcSerialization: {
enabled: true,
maxUtf8Bytes: 64_000,
validateParamsJsonSchema: true,
validateReturnJsonSchema: true,
},
})Same object can live under bootstrap: { rpcSerialization: { … } } when you pass nested bootstrap options (attachCatRPC merges them).
Global config (tests or custom gateways)
import { setRpcSerializationConfig } from '@gloocan/cat-inspector'
setRpcSerializationConfig({
enabled: true,
maxUtf8Bytes: 64_000,
validateParamsJsonSchema: true,
validateReturnJsonSchema: true,
})resetRpcSerializationConfig clears all flags (used in tests).
Enabled vs disabled (plain examples)
enabled: false (default)
- Handler returns
Return('OK', { at: new Date() })→ client may get a non-ISO date shape or encoding quirks depending on the transport. returnJsonSchemaon the registry entry is ignored even ifvalidateReturnJsonSchema: true.
enabled: true
- Same handler →
result.atis an ISO string inRPC_RESPONSE. - Class instances,
Map, functions in the return tree →RESULT_NOT_SERIALIZABLE(handler ran; RPC response is an error).
validateParamsJsonSchema: true
- QA sends
args: ['']but schema requires non-empty string →INPUT_SCHEMA_INVALIDbefore invoke.
validateReturnJsonSchema: true (with enabled: true)
- Handler returns
Return('OK', { n: 'text' })but schema expects{ n: number }→RETURN_SCHEMA_INVALIDafter invoke.
Serialization rules (serializeRpcResult)
When enabled is true, the SDK:
- Allows:
null, boolean, number, string, arrays, plain objects (Objectornullprototype) - Converts:
bigint→ decimal string,Date→ ISO string, nestedundefinedin objects omitted; rootundefined→null - Rejects: functions, symbols, class instances,
Map/Set, circular references
Use maybeSerializeRpcResult if you need { ok, value | message } without throwing. Inside executeRPC, failures map to RESULT_NOT_SERIALIZABLE.
API reference
| Function | Description |
|---|---|
setRpcSerializationConfig(partial) | Merge into global options; sets default maxUtf8Bytes when enabling. |
getRpcSerializationConfig() | Read-only snapshot. |
resetRpcSerializationConfig() | Sets enabled: false and turns off both schema flags. |
serializeRpcResult(raw) | Normalize one value; throws SerializeRpcResultError (code: RESULT_NOT_SERIALIZABLE). |
maybeSerializeRpcResult(raw) | Same as above but returns { ok: true, value } or { ok: false, message }. |
See also
- Params JSON Schema — tuple schema on
args - Return JSON Schema — object schema on
result - RPC error codes —
INPUT_SCHEMA_INVALID,RETURN_SCHEMA_INVALID,RESULT_NOT_SERIALIZABLE - Bootstrap /
attachCatRPC—rpcSerializationon host setup