Files
openclaw/docs/plugins/sdk-overview.md
Vincent Koc 28838802d4 docs(plugins): add SDK reference and how-to guide pages (#52366)
* docs(plugins): add SDK reference and how-to guide pages

Create 7 new plugin SDK documentation pages:
- sdk-overview: import map, registration API reference
- sdk-entrypoints: definePluginEntry/defineChannelPluginEntry reference
- sdk-runtime: api.runtime namespace reference
- sdk-setup: packaging, manifests, config schemas reference
- sdk-channel-plugins: step-by-step channel plugin how-to
- sdk-provider-plugins: step-by-step provider plugin how-to
- sdk-testing: test utilities and patterns reference

Restructure plugin docs navigation with nested groups:
- Top-level: user-facing pages (Install, Community, Bundles)
- Building Plugins: Getting Started, Channel, Provider
- SDK Reference: Overview, Entry Points, Runtime, Setup, Testing, Migration, Manifest, Internals

Revise existing pages for new IA:
- building-plugins.md: tightened as quick-start, routes to detailed guides
- architecture.md: updated info box with links to new guides
- sdk-migration.md: expanded Related section

* docs(plugins): add Mintlify components (Steps, CodeGroup, Tabs, Accordion, CardGroup)

- Channel plugin guide: wrap walkthrough in Steps, use CodeGroup for
  package.json/manifest, Accordion for createChatChannelPlugin details,
  CardGroup for advanced topics
- Provider plugin guide: wrap walkthrough in Steps, use CodeGroup for
  package files, Tabs for hook examples, Accordion for all-hooks reference
- Getting started: use CardGroup for plugin-type picker and next steps,
  CodeGroup for package/manifest
- SDK Overview: wrap subpath tables in AccordionGroup for scannability

* fix(docs): address PR review feedback on plugin SDK pages

- Remove nonexistent api.runtime.channel.handleInboundMessage call,
  replace with realistic webhook pattern and note about channel-specific
  inbound handling (issue a)
- Fix registrationMode values: 'setup' -> 'setup-only' and 'setup-runtime'
  matching actual PluginRegistrationMode type (issue b)
- Fix createOptionalChannelSetupSurface params: channelId -> channel,
  add required label field (issue c)
- Fix broken anchor links: #multi-capability-providers ->
  #step-5-add-extra-capabilities, #plugin-kinds -> #registration-api (issue d)
- Add missing acmeChatApi import in channel plugin example (issue e)
- Fix undefined provider variable in provider test example (issue f)

* fix(docs): use correct createProviderApiKeyAuthMethod options

Replace incorrect params (provider, validate) with actual required fields
(providerId, methodId, optionKey, flagName, promptMessage) matching
src/plugins/provider-api-key-auth.ts.

* fix(docs): address second round of PR review feedback

- Add required model fields (reasoning, input, cost, contextWindow,
  maxTokens) to catalog example (issue b)
- Fix buildChannelConfigSchema to take a Zod schema argument (issue c)
- Replace fabricated setupWizard steps/run with real ChannelSetupWizard
  contract (channel, status, credentials) (issue d)
- Add required sessionFile/workspaceDir to runEmbeddedPiAgent (issue e)
- Fix wrapStreamFn to return StreamFn from ctx.streamFn (issue f)
2026-03-22 11:35:53 -07:00

9.6 KiB

title, sidebarTitle, summary, read_when
title sidebarTitle summary read_when
Plugin SDK Overview SDK Overview Import map, registration API reference, and SDK architecture
You need to know which SDK subpath to import from
You want a reference for all registration methods on OpenClawPluginApi
You are looking up a specific SDK export

Plugin SDK Overview

The plugin SDK is the typed contract between plugins and core. This page is the reference for what to import and what you can register.

**Looking for a how-to guide?** - First plugin? Start with [Getting Started](/plugins/building-plugins) - Channel plugin? See [Channel Plugins](/plugins/sdk-channel-plugins) - Provider plugin? See [Provider Plugins](/plugins/sdk-provider-plugins)

Import convention

Always import from a specific subpath:

import { definePluginEntry } from "openclaw/plugin-sdk/plugin-entry";
import { defineChannelPluginEntry } from "openclaw/plugin-sdk/core";

// Deprecated — will be removed in the next major release
import { definePluginEntry } from "openclaw/plugin-sdk";

Each subpath is a small, self-contained module. This keeps startup fast and prevents circular dependency issues.

Subpath reference

The most commonly used subpaths, grouped by purpose. The full list of 100+ subpaths is in scripts/lib/plugin-sdk-entrypoints.json.

Plugin entry

Subpath Key exports
plugin-sdk/plugin-entry definePluginEntry
plugin-sdk/core defineChannelPluginEntry, createChatChannelPlugin, createChannelPluginBase, defineSetupPluginEntry, buildChannelConfigSchema
| Subpath | Key exports | | --- | --- | | `plugin-sdk/channel-setup` | `createOptionalChannelSetupSurface` | | `plugin-sdk/channel-pairing` | `createChannelPairingController` | | `plugin-sdk/channel-reply-pipeline` | `createChannelReplyPipeline` | | `plugin-sdk/channel-config-helpers` | `createHybridChannelConfigAdapter` | | `plugin-sdk/channel-config-schema` | Channel config schema types | | `plugin-sdk/channel-policy` | `resolveChannelGroupRequireMention` | | `plugin-sdk/channel-lifecycle` | `createAccountStatusSink` | | `plugin-sdk/channel-inbound` | Debounce, mention matching, envelope helpers | | `plugin-sdk/channel-send-result` | Reply result types | | `plugin-sdk/channel-actions` | `createMessageToolButtonsSchema`, `createMessageToolCardSchema` | | `plugin-sdk/channel-targets` | Target parsing/matching helpers | | `plugin-sdk/channel-contract` | Channel contract types | | `plugin-sdk/channel-feedback` | Feedback/reaction wiring | | Subpath | Key exports | | --- | --- | | `plugin-sdk/provider-auth` | `createProviderApiKeyAuthMethod`, `ensureApiKeyFromOptionEnvOrPrompt`, `upsertAuthProfile` | | `plugin-sdk/provider-models` | `normalizeModelCompat` | | `plugin-sdk/provider-catalog` | Catalog type re-exports | | `plugin-sdk/provider-usage` | `fetchClaudeUsage` and similar | | `plugin-sdk/provider-stream` | Stream wrapper types | | `plugin-sdk/provider-onboard` | Onboarding config patch helpers | | Subpath | Key exports | | --- | --- | | `plugin-sdk/command-auth` | `resolveControlCommandGate` | | `plugin-sdk/allow-from` | `formatAllowFromLowercase` | | `plugin-sdk/secret-input` | Secret input parsing helpers | | `plugin-sdk/webhook-ingress` | Webhook request/target helpers | | Subpath | Key exports | | --- | --- | | `plugin-sdk/runtime-store` | `createPluginRuntimeStore` | | `plugin-sdk/config-runtime` | Config load/write helpers | | `plugin-sdk/infra-runtime` | System event/heartbeat helpers | | `plugin-sdk/agent-runtime` | Agent dir/identity/workspace helpers | | `plugin-sdk/directory-runtime` | Config-backed directory query/dedup | | `plugin-sdk/keyed-async-queue` | `KeyedAsyncQueue` | | Subpath | Key exports | | --- | --- | | `plugin-sdk/image-generation` | Image generation provider types | | `plugin-sdk/media-understanding` | Media understanding provider types | | `plugin-sdk/speech` | Speech provider types | | `plugin-sdk/testing` | `installCommonResolveTargetErrorCases`, `shouldAckReaction` |

Registration API

The register(api) callback receives an OpenClawPluginApi object with these methods:

Capability registration

Method What it registers
api.registerProvider(...) Text inference (LLM)
api.registerChannel(...) Messaging channel
api.registerSpeechProvider(...) Text-to-speech / STT synthesis
api.registerMediaUnderstandingProvider(...) Image/audio/video analysis
api.registerImageGenerationProvider(...) Image generation
api.registerWebSearchProvider(...) Web search

Tools and commands

Method What it registers
api.registerTool(tool, opts?) Agent tool (required or { optional: true })
api.registerCommand(def) Custom command (bypasses the LLM)

Infrastructure

Method What it registers
api.registerHook(events, handler, opts?) Event hook
api.registerHttpRoute(params) Gateway HTTP endpoint
api.registerGatewayMethod(name, handler) Gateway RPC method
api.registerCli(registrar, opts?) CLI subcommand
api.registerService(service) Background service
api.registerInteractiveHandler(registration) Interactive handler

Exclusive slots

Method What it registers
api.registerContextEngine(id, factory) Context engine (one active at a time)
api.registerMemoryPromptSection(builder) Memory prompt section builder

Events and lifecycle

Method What it does
api.on(hookName, handler, opts?) Typed lifecycle hook
api.onConversationBindingResolved(handler) Conversation binding callback

API object fields

Field Type Description
api.id string Plugin id
api.name string Display name
api.config OpenClawConfig Current config snapshot
api.pluginConfig Record<string, unknown> Plugin-specific config from plugins.entries.<id>.config
api.runtime PluginRuntime Runtime helpers
api.logger PluginLogger Scoped logger (debug, info, warn, error)
api.registrationMode PluginRegistrationMode "full", "setup-only", or "setup-runtime"
api.resolvePath(input) (string) => string Resolve path relative to plugin root

Internal module convention

Within your plugin, use local barrel files for internal imports:

my-plugin/
  api.ts            # Public exports for external consumers
  runtime-api.ts    # Internal-only runtime exports
  index.ts          # Plugin entry point
  setup-entry.ts    # Lightweight setup-only entry (optional)
Never import your own plugin through `openclaw/plugin-sdk/` from production code. Route internal imports through `./api.ts` or `./runtime-api.ts`. The SDK path is the external contract only.