Plugin setup and config
기준일: 2026-07-26
공식 기준: Plugin setup and config
Plugin setup and config 문서는 OpenClaw 공식 문서(plugins/sdk-setup)를 한국어로 정리한 가이드입니다. Setup wizards, setup-entry.ts, config schemas, and package.json metadata 명령·설정 키·코드 예시는 공식 문서를 그대로 보존하며, 해석과 절차 안내는 한국어로 제공합니다. 최종 동작은 설치된 CLI 버전과 공식 원문을 확인하세요.
핵심 요약
Setup wizards, setup-entry.ts, config schemas, and package.json metadata
한국어 가이드 범위: plugins/sdk-setup 경로의 설정·명령·제약·예시를 학습용으로 재구성합니다.
문서 구성
공식 문서의 주요 섹션은 다음과 같습니다.
- Package metadata
- Channel-owned setup fields
- Deferred full load
- Plugin manifest
- ClawHub publishing
- Setup entry
- Narrow setup helper imports
- Channel-owned setup input fields
- Channel-owned single-account promotion
- Config schema
- Building channel config schemas
- Setup wizards
- Publishing and installing
- 관련 문서
상세 내용
본문
Reference for plugin packaging (package.json metadata), manifests (openclaw.plugin.json), setup entries, and config schemas.
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
Package metadata
Your package.json needs an openclaw field that tells the plugin system what your plugin provides:
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
{
"name": "@myorg/openclaw-my-channel",
"version": "1.0.0",
"type": "module",
"openclaw": {
"extensions": ["./index.ts"],
"setupEntry": "./setup-entry.ts",
"channel": {
"id": "my-channel",
"label": "My Channel",
"blurb": "Short description of the channel."
}
}
}
openclaw fields
Entry point files (relative to package root). Valid source entries for workspace and git checkout development.
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
openclaw.channel
openclaw.channel is cheap package metadata for channel discovery and setup surfaces before runtime loads.
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
Channel-owned setup fields
Channel plugins should define setup fields once in runtime code with defineChannelSetupContract(...) and publish the matching serializable projection under openclaw.channel.setup.fields. The runtime definition infers the plugin-local input type, parses both guided and non-interactive values, and keeps channel-specific keys out of core types. Package metadata lets openclaw channels add --help and openclaw channels add --channel --help discover only the selected channel's options without loading the plugin.
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
주요 항목:
configured: include the channel in configured/status-style listing surfacessetup: include the channel in interactive setup/configure pickersdocs: mark the channel as public-facing in docs/navigation surfaces
| Field | Type | What it means |
|---|---|---|
id |
string |
Canonical channel id. |
label |
string |
Primary channel label. |
selectionLabel |
string |
Picker/setup label when it should differ from label. |
detailLabel |
string |
Secondary detail label for richer channel catalogs and status surfaces. |
docsPath |
string |
Docs path for setup and selection links. |
docsLabel |
string |
Override label used for docs links when it should differ from the channel id. |
blurb |
string |
Short onboarding/catalog description. |
order |
number |
Sort order in channel catalogs. |
aliases |
string[] |
Extra lookup aliases for channel selection. |
preferOver |
string[] |
Lower-priority plugin/channel ids this channel should outrank. |
systemImage |
string |
Optional icon/system-image name for channel UI catalogs. |
selectionDocsPrefix |
string |
Prefix text before docs links in selection surfaces. |
selectionDocsOmitLabel |
boolean |
Show the docs path directly instead of a labeled docs link in selection copy. |
selectionExtras |
string[] |
Extra short strings appended in selection copy. |
markdownCapable |
boolean |
Marks the channel as markdown-capable for outbound formatting decisions. |
exposure |
object |
Channel visibility controls for setup, configured lists, and docs surfaces. |
quickstartAllowFrom |
boolean |
Opt this channel into the standard quickstart allowFrom setup flow. |
forceAccountBinding |
boolean |
Require explicit account binding even when only one account exists. |
preferSessionLookupForAnnounceTarget |
boolean |
Prefer session lookup when resolving announce targets for this channel. |
setup |
object |
Serializable channel-owned setup fields used for lazy CLI option discovery. |
fields: {
endpoint: {
kind: "string",
cli: { flags: "--endpoint <url>", description: "Service endpoint" },
},
transport: {
kind: "choice",
choices: ["native", "container"],
cli: { flags: "--transport <kind>", description: "Transport owner" },
},
},
adapter: {
applyAccountConfig: ({ cfg, input }) => ({
...cfg,
channels: { ...cfg.channels, example: input },
}),
},
});
{
"openclaw": {
"channel": {
"id": "example",
"setup": {
"fields": [
{
"key": "endpoint",
"kind": "string",
"cli": { "flags": "--endpoint <url>", "description": "Service endpoint" }
},
{
"key": "transport",
"kind": "choice",
"choices": ["native", "container"],
"cli": { "flags": "--transport <kind>", "description": "Transport owner" }
}
]
}
}
}
}
{
"openclaw": {
"channel": {
"id": "my-channel",
"label": "My Channel",
"selectionLabel": "My Channel (self-hosted)",
"detailLabel": "My Channel Bot",
"docsPath": "/channels/my-channel",
"docsLabel": "my-channel",
"blurb": "Webhook-based self-hosted chat integration.",
"order": 80,
"aliases": ["mc"],
"preferOver": ["my-channel-legacy"],
"selectionDocsPrefix": "Guide:",
"selectionExtras": ["Markdown"],
"markdownCapable": true,
"exposure": {
"configured": true,
"setup": true,
"docs": true
},
"quickstartAllowFrom": true
}
}
}
openclaw.install
openclaw.install is package metadata, not manifest metadata.
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
| Field | Type | What it means |
|---|---|---|
clawhubSpec |
string |
Canonical ClawHub spec for install/update and onboarding install-on-demand flows. |
npmSpec |
string |
Canonical npm spec for install/update fallback flows. |
localPath |
string |
Local development or bundled install path. |
defaultChoice |
"clawhub" | "npm" | "local" |
Preferred install source when multiple sources are available. |
minHostVersion |
string |
Minimum supported OpenClaw version, >=x.y.z or >=x.y.z-prerelease. |
expectedIntegrity |
string |
Expected npm dist integrity string, usually sha512-..., for pinned installs. |
allowInvalidConfigRecovery |
boolean |
Lets bundled-plugin reinstall flows recover from specific stale-config failures. |
requiredPlatformPackages |
string[] |
Required platform-specific npm aliases verified during npm install. |
{
"openclaw": {
"install": {
"npmSpec": "@wecom/wecom-openclaw-plugin@1.2.3",
"expectedIntegrity": "sha512-REPLACE_WITH_NPM_DIST_INTEGRITY",
"defaultChoice": "npm"
}
}
}
Deferred full load
Channel plugins can opt into deferred loading with:
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
{
"openclaw": {
"extensions": ["./index.ts"],
"setupEntry": "./setup-entry.ts",
"startup": {
"deferConfiguredChannelFullLoadUntilAfterListen": true
}
}
}
Plugin manifest
Every native plugin must ship an openclaw.plugin.json in the package root. OpenClaw uses this to validate config without executing plugin code.
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
{
"id": "my-plugin",
"name": "My Plugin",
"description": "Adds My Plugin capabilities to OpenClaw",
"configSchema": {
"type": "object",
"additionalProperties": false,
"properties": {
"webhookSecret": {
"type": "string",
"description": "Webhook verification secret"
}
}
}
}
{
"id": "my-channel",
"channels": ["my-channel"],
"configSchema": {
"type": "object",
"additionalProperties": false,
"properties": {}
}
}
{
"id": "my-plugin",
"configSchema": {
"type": "object",
"additionalProperties": false
}
}
ClawHub publishing
Skills and plugin packages use separate ClawHub publish commands. For plugin packages, use the package-specific command:
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
clawhub package publish your-org/your-plugin --dry-run
clawhub package publish your-org/your-plugin
Setup entry
setup-entry.ts is a lightweight alternative to index.ts that OpenClaw loads when it only needs setup surfaces (onboarding, config repair, disabled channel inspection):
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
주요 항목:
- The channel is disabled but needs setup/onboarding surfaces.
- The channel is enabled but unconfigured.
- Deferred loading is enabled (
deferConfiguredChannelFullLoadUntilAfterListen). - The channel plugin object (via
defineSetupPluginEntry). - Any HTTP routes required before gateway listen.
- Any gateway methods needed during startup.
- CLI registrations.
- Background services.
- Heavy runtime imports (crypto, SDKs).
- Gateway methods only needed after startup.
// setup-entry.ts
Narrow setup helper imports
For hot setup-only paths, prefer the narrow setup helper seams over the broader plugin-sdk/setup umbrella when you only need part of the setup surface:
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
| Import path | Use it for | Key exports |
|---|---|---|
plugin-sdk/setup-runtime |
setup-time runtime helpers that stay available in setupEntry / deferred channel startup |
createSetupTranslator, createPatchedAccountSetupAdapter, createEnvPatchedAccountSetupAdapter, createSetupInputPresenceValidator, noteChannelLookupFailure, noteChannelLookupSummary, promptResolvedAllowFrom, splitSetupEntries, createAllowlistSetupWizardProxy, createDelegatedSetupWizardProxy |
plugin-sdk/setup-tools |
setup/install CLI/archive/docs helpers | formatCliCommand, detectBinary, extractArchive, resolveBrewExecutable, formatDocsLink, CONFIG_DIR |
Channel-owned setup input fields
ChannelSetupInput is a generic envelope shared by setup callers and channel plugins. Its permanently typed fields are name, token, tokenFile, useEnv, allowFrom, and defaultTo. Additional plugin-owned keys can still be present on the runtime input object, but the shared type does not declare an index signature. Each plugin must declare and narrow its own setup fields or validate them with a plugin-owned schema at the adapter boundary:
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
type AcmeSetupInput = ChannelSetupInput & {
workspaceId?: string;
webhookUrl?: string;
};
applyAccountConfig: ({ cfg, input }) => {
const setupInput = input as AcmeSetupInput;
return {
...cfg,
channels: {
...cfg.channels,
acme: {
token: setupInput.token,
workspaceId: setupInput.workspaceId,
webhookUrl: setupInput.webhookUrl,
},
},
};
},
};
Channel-owned single-account promotion
When a channel upgrades from a single-account top-level config to channels..accounts.*, the default shared behavior moves promoted account-scoped values into accounts.default.
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
주요 항목:
singleAccountKeysToMove: extra top-level keys that should move into the promoted accountnamedAccountPromotionKeys: when named accounts already exist, only these keys move into the promoted account; shared policy/delivery keys stay at the channel rootresolveSingleAccountPromotionTarget(...): choose which existing account receives promoted values
Config schema
Plugin config is validated against the JSON Schema in your manifest. Users configure plugins via:
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
{
plugins: {
entries: {
"my-plugin": {
config: {
webhookSecret: "abc123",
},
},
},
},
}
{
channels: {
"my-channel": {
token: "bot-token",
allowFrom: ["user1", "user2"],
},
},
}
Building channel config schemas
Use buildChannelConfigSchema to convert a Zod schema into the ChannelConfigSchema wrapper used by plugin-owned config artifacts:
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
const accountSchema = z.object({
token: z.string().optional(),
allowFrom: z.array(z.string()).optional(),
accounts: z.object({}).catchall(z.any()).optional(),
defaultAccount: z.string().optional(),
});
const configSchema = buildChannelConfigSchema(accountSchema);
const configSchema = buildJsonChannelConfigSchema(
Type.Object({
token: Type.Optional(Type.String()),
allowFrom: Type.Optional(Type.Array(Type.String())),
}),
);
Setup wizards
Channel plugins can provide interactive setup wizards for openclaw onboard. The wizard is a ChannelSetupWizard object on the ChannelPlugin:
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
주요 항목:
createDetectedBinaryStatus(...)for status blocks that vary only by labels, hints, scores, and binary detectioncreateCliPathTextInput(...)for path-backed text inputscreateDelegatedSetupWizardProxy(...)whensetupEntryneeds to forward status, prepare, or finalize behavior to a heavier full wizard lazilycreateDelegatedTextInputShouldPrompt(...)whensetupEntryonly needs to delegate atextInputs[*].shouldPromptdecision
const setupWizard: ChannelSetupWizard = {
channel: "my-channel",
status: {
configuredLabel: "Connected",
unconfiguredLabel: "Not configured",
resolveConfigured: ({ cfg }) => Boolean((cfg.channels as any)?.["my-channel"]?.token),
},
credentials: [
{
inputKey: "token",
providerHint: "my-channel",
credentialLabel: "Bot token",
preferredEnvVar: "MY_CHANNEL_BOT_TOKEN",
envPrompt: "Use MY_CHANNEL_BOT_TOKEN from environment?",
keepPrompt: "Keep current token?",
inputPrompt: "Enter your bot token:",
inspect: ({ cfg, accountId }) => {
const token = (cfg.channels as any)?.["my-channel"]?.token;
return {
accountConfigured: Boolean(token),
hasConfiguredValue: Boolean(token),
};
},
},
],
};
import { createOptionalChannelSetupSurface } from "openclaw/plugin-sdk/channel-setup";
const setupSurface = createOptionalChannelSetupSurface({
channel: "my-channel",
label: "My Channel",
npmSpec: "@myorg/openclaw-my-channel",
docsPath: "/channels/my-channel",
});
// Returns { setupAdapter, setupWizard }
Publishing and installing
Bare package specs install from npm during the launch cutover, unless the name matches a bundled or official plugin id, in which case OpenClaw uses that local/official copy instead. Use clawhub:, npm:, git:, or npm-pack: for deterministic source selection — see Manage plugins.
위 내용은 공식 문서의 해당 섹션 요지입니다. 세부 플래그·기본값은 원문과
--help를 확인하세요.
openclaw plugins install @myorg/openclaw-my-plugin
openclaw plugins install clawhub:@myorg/openclaw-my-plugin
openclaw plugins install npm:@myorg/openclaw-my-plugin
관련 문서
주요 항목:
- Building plugins — step-by-step getting started guide
- Plugin manifest — full manifest schema reference
- SDK entry points —
definePluginEntryanddefineChannelPluginEntry
실습 체크리스트
- 공식 문서와 로컬 버전을 대조합니다:
https://docs.openclaw.ai/plugins/sdk-setup - 관련 CLI는
openclaw --help및 하위 명령--help로 옵션을 확인합니다. - 설정 변경 시
openclaw config/openclaw doctor로 유효성을 검사합니다. - Gateway·채널·플러그인 변경 후에는 필요 시 Gateway를 재시작합니다.
자주 쓰는 명령·설정 예시
{
"name": "@myorg/openclaw-my-channel",
"version": "1.0.0",
"type": "module",
"openclaw": {
"extensions": ["./index.ts"],
"setupEntry": "./setup-entry.ts",
"channel": {
"id": "my-channel",
"label": "My Channel",
"blurb": "Short description of the channel."
}
}
}
Publishing externally on ClawHub requires `compat` and `build`. Canonical publish snippets live in `docs/snippets/plugin-publish/`.
### `openclaw` fields
Entry point files (relative to package root). Valid source entries for workspace and git checkout development.
Built JavaScript peers for `extensions`, preferred when OpenClaw loads an installed npm package. See [SDK entry points](/plugins/sdk-entrypoints) for the source/built resolution order.
Lightweight setup-only entry (optional).
Built JavaScript peer for `setupEntry`. Requires `setupEntry` to also be set.
`{ id, label }` fallback plugin identity, used when a plugin has no channel/provider metadata to derive an id or label from.
Channel catalog metadata for setup, picker, quickstart, and status surfaces.
Install hints: `npmSpec`, `localPath`, `defaultChoice`, `minHostVersion`, `expectedIntegrity`, `allowInvalidConfigRecovery`, `requiredPlatformPackages`.
Startup behavior flags.
`pluginApi` version range this plugin supports. Required for external ClawHub publishes.
Provider ids (`providers: string[]`) are manifest metadata, not package metadata. Declare them in `openclaw.plugin.json`, not here — see [Plugin manifest](/plugins/manifest).
### `openclaw.channel`
`openclaw.channel` is cheap package metadata for channel discovery and setup surfaces before runtime loads.
### Channel-owned setup fields
Channel plugins should define setup fields once in runtime code with `defineChannelSetupContract(...)` and publish the matching serializable projection under `openclaw.channel.setup.fields`. The runtime definition infers the plugin-local input type, parses both guided and non-interactive values, and keeps channel-specific keys out of core types. Package metadata lets `openclaw channels add <channel-id> --help` and `openclaw channels add --channel <channel-id> --help` discover only the selected channel's options without loading the plugin.
Supported field kinds are `string`, `boolean`, `integer`, `string-list`, and `choice`. Use `sensitive: true` for credentials. Each field key must equal the camelCased attribute name of its long CLI flag, including any negated form, such as `apiToken` for `--api-token`. Boolean fields may add `cli.negatedFlags` when both positive and `--no-*` forms are needed. `channel`, `account`, and the account display `name` remain the shared control envelope.
The released `setup`/`ChannelSetupInput` adapter stays available for existing external plugins. New plugins should expose `setupContract`; OpenClaw always prefers it when both are present.
| Field | Type | What it means |
| -------------------------------------- | ---------- | ----------------------------------------------------------------------------- |
| `id` | `string` | Canonical channel id. |
| `label` | `string` | Primary channel label. |
| `selectionLabel` | `string` | Picker/setup label when it should differ from `label`. |
| `detailLabel` | `string` | Secondary detail label for richer channel catalogs and status surfaces. |
| `docsPath` | `string` | Docs path for setup and selection links. |
| `docsLabel` | `string` | Override label used for docs links when it should differ from the channel id. |
| `blurb` | `string` | Short onboarding/catalog description. |
| `order` | `number` | Sort order in channel catalogs. |
| `aliases` | `string[]` | Extra lookup aliases for channel selection. |
| `preferOver` | `string[]` | Lower-priority plugin/channel ids this channel should outrank. |
| `systemImage` | `string` | Optional icon/system-image name for channel UI catalogs. |
| `selectionDocsPrefix` | `string` | Prefix text before docs links in selection surfaces. |
| `selectionDocsOmitLabel` | `boolean` | Show the docs path directly instead of a labeled docs link in selection copy. |
| `selectionExtras` | `string[]` | Extra short strings appended in selection copy. |
| `markdownCapable` | `boolean` | Marks the channel as markdown-capable for outbound formatting decisions. |
| `exposure` | `object` | Channel visibility controls for setup, configured lists, and docs surfaces. |
| `quickstartAllowFrom` | `boolean` | Opt this channel into the standard quickstart `allowFrom` setup flow. |
| `forceAccountBinding` | `boolean` | Require explicit account binding even when only one account exists. |
| `preferSessionLookupForAnnounceTarget` | `boolean` | Prefer session lookup when resolving announce targets for this channel. |
| `setup` | `object` | Serializable channel-owned setup fields used for lazy CLI option discovery. |
Example:
`exposure` supports:
- `configured`: include the channel in configured/status-style listing surfaces
- `setup`: include the channel in interactive setup/configure pickers
- `docs`: mark the channel as public-facing in docs/navigation surfaces
### `openclaw.install`
`openclaw.install` is package metadata, not manifest metadata.
| Field | Type | What it means |
| ---------------------------- | ----------------------------------- | --------------------------------------------------------------------------------- |
| `clawhubSpec` | `string` | Canonical ClawHub spec for install/update and onboarding install-on-demand flows. |
| `npmSpec` | `string` | Canonical npm spec for install/update fallback flows. |
| `localPath` | `string` | Local development or bundled install path. |
| `defaultChoice` | `"clawhub"` \| `"npm"` \| `"local"` | Preferred install source when multiple sources are available. |
| `minHostVersion` | `string` | Minimum supported OpenClaw version, `>=x.y.z` or `>=x.y.z-prerelease`. |
| `expectedIntegrity` | `string` | Expected npm dist integrity string, usually `sha512-...`, for pinned installs. |
| `allowInvalidConfigRecovery` | `boolean` | Lets bundled-plugin reinstall flows recover from specific stale-config failures. |
| `requiredPlatformPackages` | `string[]` | Required platform-specific npm aliases verified during npm install. |
Interactive onboarding uses `openclaw.install` for install-on-demand surfaces: if your plugin exposes provider auth choices or channel setup/catalog metadata before runtime loads, onboarding can prompt for ClawHub, npm, or local install, install or enable the plugin, then continue the selected flow. ClawHub choices use `clawhubSpec` and are preferred when present; npm choices require trusted catalog metadata with a registry `npmSpec` (exact versions and `expectedIntegrity` are optional pins, enforced on install/update when set). Keep "what to show" in `openclaw.plugin.json` and "how to install it" in `package.json`.
If `minHostVersion` is set, install and non-bundled manifest-registry loading both enforce it. Older hosts skip external plugins; invalid version strings are rejected. Bundled source plugins are assumed to be co-versioned with the host checkout.
For pinned npm installs, keep the exact version in `npmSpec` and add the expected artifact integrity:
`allowInvalidConfigRecovery` is not a general bypass for broken configs. It is narrow bundled-plugin recovery only, letting reinstall/setup repair known upgrade leftovers like a missing bundled plugin path or a stale `channels.<id>` entry for that same plugin. If config is broken for unrelated reasons, install still fails closed and tells the operator to run `openclaw doctor --fix`.
### Deferred full load
Channel plugins can opt into deferred loading with:
관련 링크
- 공식 원문: plugins/sdk-setup
- OpenClaw 문서 홈
이 가이드는 공식 문서를 한국어 학습용으로 재구성한 것입니다. 옵션 기본값·플래그 이름은 설치 버전에 따라 달라질 수 있습니다.