KB LabsDocs

Adapter System

Last updated April 7, 2026


What adapters are and why the platform uses them.

Adapters implement the concrete backends that the KB Labs platform depends on: LLM providers, caches, vector stores, databases, loggers, and more. You choose which adapters to use in kb.config.json. Plugins never reference adapters directly — they call useLLM(), useCache(), useStorage(), and the platform injects whatever is configured.

This page explains the design. For hands-on usage see Guides → Writing Your First Adapter.

Interface-first design

Every platform capability has a TypeScript interface that defines the contract:

  • ILLMchat(), chatWithTools(), embed(), countTokens()
  • ICacheget(), set(), delete(), clear()
  • IVectorStoreupsert(), search(), delete(), createCollection()
  • IStorageread(), write(), delete(), list(), exists()
  • ILoggerdebug(), info(), warn(), error(), child()
  • IAnalyticstrack(), identify(), flush()
  • IEnvironmentAdapter — provision, start, attach, release sandbox environments

These interfaces live in @kb-labs/core-platform. Adapters live in separate packages and implement one or more interfaces. The platform runtime holds references to the interface type, not the adapter class — which is how you can swap OpenAI for Anthropic without touching any plugin code.

Shipped adapters

The platform ships adapters for common backends out of the box:

InterfaceAdapterPackage
ILLMOpenAI (GPT-4o, o1, ...)@kb-labs/adapter-llm-openai
ILLMAnthropic (Claude 3.x, 4.x)@kb-labs/adapter-llm-anthropic
ICacheIn-memory@kb-labs/adapter-cache-memory
ICacheRedis@kb-labs/adapter-cache-redis
IVectorStoreQdrant@kb-labs/adapter-vector-qdrant
IVectorStoreIn-memory@kb-labs/adapter-vector-memory
IStorageLocal filesystem@kb-labs/adapter-storage-fs
ILoggerConsole (structured JSON)@kb-labs/adapter-logger-console
IEnvironmentAdapterDocker@kb-labs/adapter-environment-docker

In-memory adapters (adapter-cache-memory, adapter-vector-memory) are the default in dev — no external services required. For production you swap to Redis and Qdrant by changing two lines in kb.config.json.

How adapters are loaded

The platform reads .kb/kb.config.json at startup. The adapters section maps each interface to a package reference and optional configuration:

JSON
{
  "adapters": {
    "llm": {
      "package": "@kb-labs/adapter-llm-openai",
      "options": {
        "model": "gpt-4o",
        "temperature": 0.2
      }
    },
    "cache": {
      "package": "@kb-labs/adapter-cache-redis",
      "options": {
        "url": "redis://localhost:6379"
      }
    },
    "vectorStore": {
      "package": "@kb-labs/adapter-vector-qdrant",
      "options": {
        "url": "http://localhost:6333"
      }
    }
  }
}

At startup loadPlatformConfig() reads this, dynamically imports each adapter package, instantiates the adapter with its options, and registers it in the platform singleton. From that point on, useLLM() returns the OpenAI adapter, useCache() returns Redis, and so on — regardless of which plugin or service is calling.

Adapters vs plugins

This distinction trips people up at first:

AdapterPlugin
What it isConcrete backend for a platform interfaceFeature contributed to the platform
ExamplesOpenAI LLM, Redis cache, Qdrant vector storeCommit assistant, QA runner, AI review
How it's configuredkb.config.jsonadapters.*kb marketplace install
Who uses itThe platform runtime, other adaptersEnd users, CI pipelines
SandboxNo — adapters run with host-level accessYes — always runs in the plugin sandbox

If you want to change what LLM provider the platform uses, that's an adapter. If you want to add a new AI-powered command, that's a plugin. A plugin calls useLLM() and is blissfully unaware of whether it ends up talking to OpenAI or Anthropic.

Writing a custom adapter

Implement the relevant interface, export a factory function, and reference your package in kb.config.json:

TYPESCRIPT
// my-custom-cache/src/index.ts
import type { ICache } from '@kb-labs/core-platform';
 
export function createAdapter(options: { url: string }): ICache {
  return {
    async get(key) { /* ... */ },
    async set(key, value, ttlMs) { /* ... */ },
    async delete(key) { /* ... */ },
    async clear() { /* ... */ },
  };
}
JSON
{
  "adapters": {
    "cache": {
      "package": "./my-custom-cache",
      "options": { "url": "..." }
    }
  }
}

The platform calls createAdapter(options) and uses the returned object for all cache operations. Your adapter doesn't need to register anywhere or extend a base class — the interface contract is the only requirement.

See Guides → Writing Your First Adapter for a step-by-step walkthrough.

Adapter System — KB Labs Docs