Reliable LLM calls,
by default.
A lightweight resilience layer for LLM chat completions. Retries, timeouts, caching, and circuit breaking, dependency-light and typed from the start.
$ npm install vern-llmbuilt around the clients you already use
import OpenAI from 'openai';
import { z } from 'zod';
import { InMemoryCacheAdapter, VernLLM } from 'vern-llm';
export const llm = new VernLLM({
client: new OpenAI({ apiKey: process.env.OPENAI_API_KEY }),
model: 'gpt-4o',
maxRetries: 3,
timeoutMs: 10_000,
circuitBreaker: true,
cache: new InMemoryCacheAdapter(),
onUsage: u => console.log(`${u.requestId}: ${u.totalTokens} tokens`)
});
export const summary = await llm.cachedLLMCall({
cacheKey: 'resume:candidate-123',
ttl: 3600,
call: {
requestId: 'resume-analysis-123',
temperature: 0.2,
maxTokens: 1000,
systemPrompt: 'Analyze this resume and return structured hiring insights.',
userContent: 'Software engineer with 5 years of experience',
schema: z.object({
strengths: z.array(z.string()),
concerns: z.array(z.string()),
recommendation: z.string()
})
}
});What this call actually does.
maxRetries: 3→ Retries transient failures with backoff and jittertimeoutMs: 10_000→ Prevents attempts from hanging indefinitelycircuitBreaker: true→ Stops repeated failures from cascadingcache: new InMemoryCacheAdapter()→ Adds caching with a swappable adapteronUsage→ Tracks tokens and request metadatacachedLLMCall→ Returns cached results without another API callcacheKey→ Identifies repeatable cached requeststtl: 3600→ Controls cache lifetimeschema→ Returns validated, typed output with Zod
Every project calling an LLM API ends up writing the same defensive code: retry logic, timeouts, a circuit breaker, a cache layer, usually copied between projects and slightly wrong each time. VernLLM gives you those primitives with sensible defaults out of the box, so you keep your existing client and just wrap it.
No. VernLLM wraps the client you already have, OpenAI, Anthropic, Gemini, Bedrock, or anything OpenAI-compatible, so you keep your existing setup and just route calls through it.
Yes. cachedLLMCall works with any adapter implementing get/set/delete, so you can plug in Redis, a database, or your own store instead of the built-in in-memory cache.
Yes, written in TypeScript from the ground up. Structured output schemas, call params, and errors are all typed, so mistakes surface at compile time instead of at runtime.
Zero runtime dependencies. VernLLM does not bundle Zod or provider SDKs; it relies on compatible interfaces instead, so you bring your own provider clients and schema validators while keeping your dependency tree minimal.
17.4+ kB minified, 6.1+ kB minified and gzipped. Small enough to drop into a project without thinking twice about it.
Yes, VernLLM is MIT licensed and open source. Use it in personal or commercial projects, fork it, or contribute back on GitHub.
Stop reinventing the resilience layer.
npm install vern-llm