v0.53.4
🌟 v0.53.4 — Meet the misina link
This release adds a brand-new HTTP transport for the Silgi client, sitting side-by-side with the existing ofetch link. Nothing in your existing code changes — silgi/client/ofetch keeps working exactly as before. The new silgi/client/misina is purely additive, opt-in, and built for teams that want stricter retry and error semantics out of the box.
✨ What's new
silgi/client/misina — a second link adapter
Powered by misina, a zero-dependency, fetch-first HTTP client. Same createLink({ url, headers, retry, timeout, protocol }) shape you already know, with a few new tricks:
import { createClient } from 'silgi/client'
import { createLink } from 'silgi/client/misina'
const link = createLink({
url: 'http://localhost:3000',
retry: 2,
idempotencyKey: 'auto',
})
const client = createClient<AppRouter>(link)Why you might pick it
Retry-After&RateLimit-Resetparsing — when the server signals a delay, the link honors it instead of using your fixed backoff.- Distinct error classes —
HTTPError(server returned an error status),NetworkError(DNS, connection reset, offline), andTimeoutError(per-attempt or wall-clock budget exceeded). All still surface asSilgiErrorfor catch-by-code, so your existing error handling keeps working. Idempotency-Keyauto-generation — retriedPOST/PATCH/DELETEcalls send the sameIdempotency-Keyacross attempts so the server can deduplicate. SetidempotencyKey: 'auto'to opt in.- Wall-clock timeout —
timeoutcaps each attempt,totalTimeoutcaps the whole logical call (including retry delays). - Redirect security — sensitive headers are stripped on cross-origin redirects, and
https → httpdowngrades are refused. - Lifecycle hooks —
beforeRequest,afterResponse,beforeError, and a terminalonCompletethat fires exactly once per logical call (perfect for tracing & metrics).
Retry with backoff
const link = createLink({
url: 'http://localhost:3000',
retry: {
limit: 3,
delay: (attempt) => 0.3 * 2 ** (attempt - 1) * 1000, // 300ms, 600ms, 1200ms
backoffLimit: 30_000,
jitter: true,
statusCodes: [408, 429, 500, 502, 503, 504],
},
})Re-exports
A new silgi/misina subpath re-exports the upstream package, mirroring the existing silgi/ofetch ergonomics — so you can grab misina's typed errors and helpers directly from Silgi:
import { isHTTPError, isNetworkError, isTimeoutError } from 'silgi/misina'📚 Docs
- Full new "misina link" section in the Client docs — options table, retry-with-backoff, hooks, and trade-offs vs ofetch.
🤝 Compatibility
- Zero breaking changes. The default link is still
silgi/client/ofetch. - Both links produce the same
SilgiErrorinstances on failure — switching transports doesn't change your catch logic. - Same wire protocols (
json/messagepack/devalue), same SSE subscription support, same per-callsignal.
🙏 Which one should I use?
- Stick with ofetch if you're already happy, deploying to Nuxt/h3, or want the most battle-tested option.
- Try misina if you care about retry correctness on rate-limited APIs, want explicit
NetworkErrorvsHTTPErrordiscrimination, or need idempotency keys for retried mutations.
You can even mix both via DynamicLink if different parts of your API live behind different services.
Full Changelog: v0.53.3...v0.53.4