diff --git a/src/plugins/bundled-package-channel-metadata.ts b/src/plugins/bundled-package-channel-metadata.ts index 5decfc3e8e9..37e5138868a 100644 --- a/src/plugins/bundled-package-channel-metadata.ts +++ b/src/plugins/bundled-package-channel-metadata.ts @@ -1,10 +1,12 @@ import { listChannelCatalogEntries } from "./channel-catalog-registry.js"; import type { PluginPackageChannel } from "./manifest.js"; +/** Lists channel metadata contributed by bundled package manifests. */ export function listBundledPackageChannelMetadata(): readonly PluginPackageChannel[] { return listChannelCatalogEntries({ origin: "bundled" }).map((entry) => entry.channel); } +/** Finds bundled package channel metadata by id or alias. */ export function findBundledPackageChannelMetadata( channelId: string, ): PluginPackageChannel | undefined { diff --git a/src/plugins/bundled-plugin-metadata.ts b/src/plugins/bundled-plugin-metadata.ts index 00e0712e266..04b1add975c 100644 --- a/src/plugins/bundled-plugin-metadata.ts +++ b/src/plugins/bundled-plugin-metadata.ts @@ -37,6 +37,7 @@ type BundledPluginPathPair = { built: string; }; +/** Metadata collected from a bundled plugin package and manifest. */ export type BundledPluginMetadata = { dirName: string; idHint: string; @@ -168,6 +169,7 @@ function collectBundledPluginMetadata( return entries; } +/** Lists bundled plugin metadata from source or built package layouts. */ export function listBundledPluginMetadata(params?: { rootDir?: string; scanDir?: string; @@ -190,6 +192,7 @@ export function listBundledPluginMetadata(params?: { return metadata; } +/** Finds bundled plugin metadata by manifest id. */ export function findBundledPluginMetadataById( pluginId: string, params?: { @@ -202,6 +205,7 @@ export function findBundledPluginMetadataById( return listBundledPluginMetadata(params).find((entry) => entry.manifest.id === pluginId); } +/** Resolves the source directory for a bundled plugin in the current workspace. */ export function resolveBundledPluginWorkspaceSourcePath(params: { rootDir: string; scanDir?: string; @@ -296,6 +300,7 @@ function listBundledPluginEntrySearchPaths( return uniqueStrings(paths); } +/** Resolves a generated runtime path for a bundled plugin entry. */ export function resolveBundledPluginGeneratedPath( rootDir: string, entry: BundledPluginPathPair | undefined, @@ -345,6 +350,7 @@ function resolveBundledPluginEntryCandidate(baseDir: string, entryPath: string): return candidate; } +/** Resolves the repo entry path for a bundled plugin, preferring source unless requested. */ export function resolveBundledPluginRepoEntryPath(params: { rootDir: string; pluginId: string; diff --git a/src/plugins/channel-presence-policy.ts b/src/plugins/channel-presence-policy.ts index 93c290b272c..7e592bd767f 100644 --- a/src/plugins/channel-presence-policy.ts +++ b/src/plugins/channel-presence-policy.ts @@ -28,11 +28,13 @@ import { loadPluginManifestRegistryForPluginRegistry } from "./plugin-registry-c const IGNORED_CHANNEL_CONFIG_KEYS = new Set(["defaults", "modelByChannel"]); +/** Source classes that can make a channel appear configured for read-only scopes. */ export type ConfiguredChannelPresenceSource = | "explicit-config" | Exclude | "manifest-env"; +/** Reasons a configured channel signal is not effective. */ export type ConfiguredChannelBlockedReason = | "plugins-disabled" | "blocked-by-denylist" @@ -44,6 +46,7 @@ export type ConfiguredChannelBlockedReason = | "no-channel-owner" | "not-activated"; +/** Policy evaluation row for one configured channel signal. */ export type ConfiguredChannelPresencePolicyEntry = { channelId: string; sources: ConfiguredChannelPresenceSource[]; @@ -70,6 +73,7 @@ function hasNonEmptyEnvValue(env: NodeJS.ProcessEnv, key: string): boolean { return typeof value === "string" && value.trim().length > 0; } +/** True when config contains meaningful enabled channel settings. */ export function hasExplicitChannelConfig(params: { config: OpenClawConfig; channelId: string; @@ -89,6 +93,7 @@ export function hasExplicitChannelConfig(params: { return enabled === true || hasMeaningfulChannelConfig(entry); } +/** Lists explicitly configured channel ids, excluding global channel config keys. */ export function listExplicitConfiguredChannelIdsForConfig(config: OpenClawConfig): string[] { const channels = config.channels; if (!channels || typeof channels !== "object" || Array.isArray(channels)) { @@ -182,6 +187,7 @@ function isChannelPluginEligibleForScopedOwnership(params: { rootConfig: OpenClawConfig; channelId?: string; }): boolean { + // Explicit config can activate bundled channel owners even under restrictive allowlists. const allowRestrictiveAllowlistBypass = params.channelId !== undefined && isBundledManifestOwner(params.plugin) && @@ -221,6 +227,7 @@ function evaluateEffectiveChannelPlugin(params: { config: OpenClawConfig; activationSource: ReturnType; }): { effective: boolean; pluginId: string; blockedReason?: ConfiguredChannelBlockedReason } { + // Bundled channels with explicit config are effective before default enablement checks. const explicitBundledChannelConfig = isBundledManifestOwner(params.plugin) && hasExplicitChannelConfig({ @@ -319,6 +326,7 @@ function loadInstalledChannelManifestRecords(params: { }).plugins; } +/** Resolves effective configured-channel policy rows from config, auth state, env, and manifests. */ export function resolveConfiguredChannelPresencePolicy(params: { config: OpenClawConfig; activationSourceConfig?: OpenClawConfig; @@ -406,6 +414,7 @@ export function resolveConfiguredChannelPresencePolicy(params: { return entries; } +/** Lists effective channel ids available to read-only scoped discovery. */ export function listConfiguredChannelIdsForReadOnlyScope( params: Parameters[0], ): string[] { @@ -414,12 +423,14 @@ export function listConfiguredChannelIdsForReadOnlyScope( .map((entry) => entry.channelId); } +/** True when read-only scoped discovery has any effective configured channel. */ export function hasConfiguredChannelsForReadOnlyScope( params: Parameters[0], ): boolean { return listConfiguredChannelIdsForReadOnlyScope(params).length > 0; } +/** Lists channel ids that should be announced as configured for operators. */ export function listConfiguredAnnounceChannelIdsForConfig(params: { config: OpenClawConfig; activationSourceConfig?: OpenClawConfig; @@ -498,6 +509,7 @@ function resolveScopedChannelOwnerPluginIds(params: { .toSorted((left, right) => left.localeCompare(right)); } +/** Resolves plugin ids discoverable for scoped channel activation. */ export function resolveDiscoverableScopedChannelPluginIds(params: { config: OpenClawConfig; activationSourceConfig?: OpenClawConfig; @@ -509,6 +521,7 @@ export function resolveDiscoverableScopedChannelPluginIds(params: { return resolveScopedChannelOwnerPluginIds(params); } +/** Resolves plugin ids that own currently configured channels. */ export function resolveConfiguredChannelPluginIds(params: { config: OpenClawConfig; activationSourceConfig?: OpenClawConfig; diff --git a/src/plugins/channel-validation.ts b/src/plugins/channel-validation.ts index 3ffa3a71116..3445ef490ab 100644 --- a/src/plugins/channel-validation.ts +++ b/src/plugins/channel-validation.ts @@ -50,6 +50,7 @@ function collectMissingChannelMetaFields(meta?: Partial | null): st return missing; } +/** Validates and normalizes a channel plugin registration before runtime catalog insertion. */ export function normalizeRegisteredChannelPlugin(params: { pluginId: string; source: string; diff --git a/src/plugins/codex-app-server-extension-types.ts b/src/plugins/codex-app-server-extension-types.ts index 492094e4ba5..a714ed2f733 100644 --- a/src/plugins/codex-app-server-extension-types.ts +++ b/src/plugins/codex-app-server-extension-types.ts @@ -1,5 +1,6 @@ import type { AgentToolResult } from "../agents/runtime/index.js"; +/** Tool-result event emitted to Codex app-server plugin extensions. */ export type CodexAppServerToolResultEvent = { threadId: string; turnId: string; @@ -9,6 +10,7 @@ export type CodexAppServerToolResultEvent = { result: AgentToolResult; }; +/** Session context passed with Codex app-server extension events. */ export type CodexAppServerExtensionContext = { agentId?: string; sessionId?: string; @@ -16,10 +18,12 @@ export type CodexAppServerExtensionContext = { runId?: string; }; +/** Optional replacement result returned by a Codex app-server extension handler. */ export type CodexAppServerToolResultHandlerResult = { result: AgentToolResult; }; +/** Runtime event surface exposed to Codex app-server extension factories. */ export type CodexAppServerExtensionRuntime = { on: ( event: "tool_result", @@ -33,6 +37,7 @@ export type CodexAppServerExtensionRuntime = { ) => void; }; +/** Factory signature for Codex app-server plugin extensions. */ export type CodexAppServerExtensionFactory = ( runtime: CodexAppServerExtensionRuntime, ) => Promise | void; diff --git a/src/plugins/http-path.ts b/src/plugins/http-path.ts index 1dfef3967ee..b7b54a96080 100644 --- a/src/plugins/http-path.ts +++ b/src/plugins/http-path.ts @@ -1,5 +1,6 @@ import { normalizeOptionalString } from "@openclaw/normalization-core/string-coerce"; +/** Normalizes plugin HTTP paths to leading-slash form with optional fallback. */ export function normalizePluginHttpPath( path?: string | null, fallback?: string | null, diff --git a/src/plugins/install-security-scan.ts b/src/plugins/install-security-scan.ts index 2993f1af517..264658edd76 100644 --- a/src/plugins/install-security-scan.ts +++ b/src/plugins/install-security-scan.ts @@ -11,6 +11,7 @@ type InstallScanLogger = { warn?: (message: string) => void; }; +/** Result returned by plugin/skill install security policy checks. */ export type InstallSecurityScanResult = { blocked?: { code?: "security_scan_blocked" | "security_scan_failed"; @@ -18,8 +19,10 @@ export type InstallSecurityScanResult = { }; }; +/** Plugin install request kinds that share install policy without skill install semantics. */ export type PluginInstallRequestKind = Exclude; +/** Skill install metadata shape passed into shared install policy evaluation. */ export type SkillInstallSpecMetadata = { id?: string; kind: "brew" | "node" | "go" | "uv" | "download"; @@ -36,16 +39,19 @@ export type SkillInstallSpecMetadata = { targetDir?: string; }; +/** Package executable metadata used to scope dependency and entrypoint scans. */ export type PackageExecutableScanMetadata = { runtimeExtensions?: readonly string[]; runtimeSetupEntry?: string; setupEntry?: string; }; +/** Lazily loads install scanning so normal plugin startup avoids policy/runtime imports. */ async function loadInstallSecurityScanRuntime() { return await import("./install-security-scan.runtime.js"); } +/** Scans an unpacked bundle source before plugin install/update. */ export async function scanBundleInstallSource( params: InstallSafetyOverrides & { config?: OpenClawConfig; @@ -63,6 +69,7 @@ export async function scanBundleInstallSource( return await scanBundleInstallSourceRuntime(params); } +/** Scans a package source directory and executable metadata before install/update. */ export async function scanPackageInstallSource( params: InstallSafetyOverrides & { config?: OpenClawConfig; @@ -84,6 +91,7 @@ export async function scanPackageInstallSource( return await scanPackageInstallSourceRuntime(params); } +/** Scans the installed package dependency tree after npm resolution. */ export async function scanInstalledPackageDependencyTree(params: { additionalPackageDirs?: string[]; allowManagedNpmRootPackagePeerSymlinks?: boolean; @@ -103,6 +111,7 @@ export async function scanInstalledPackageDependencyTree(params: { return await scanInstalledPackageDependencyTreeRuntime(params); } +/** Scans one file-based plugin install source. */ export async function scanFileInstallSource( params: InstallSafetyOverrides & { config?: OpenClawConfig; @@ -118,6 +127,7 @@ export async function scanFileInstallSource( return await scanFileInstallSourceRuntime(params); } +/** Runs npm install policy checks before package install side effects. */ export async function preflightPluginNpmInstallPolicy(params: { config?: OpenClawConfig; logger: InstallScanLogger; @@ -133,6 +143,7 @@ export async function preflightPluginNpmInstallPolicy(params: { return await preflightPluginNpmInstallPolicyRuntime(params); } +/** Runs git install policy checks before plugin install side effects. */ export async function preflightPluginGitInstallPolicy(params: { config?: OpenClawConfig; logger: InstallScanLogger; @@ -146,6 +157,7 @@ export async function preflightPluginGitInstallPolicy(params: { return await preflightPluginGitInstallPolicyRuntime(params); } +/** Evaluates shared install policy for skill-managed dependency installs. */ export async function evaluateSkillInstallPolicy(params: { config?: OpenClawConfig; installId: string; diff --git a/src/plugins/interactive-registry.ts b/src/plugins/interactive-registry.ts index 33352fdb614..5df32caa622 100644 --- a/src/plugins/interactive-registry.ts +++ b/src/plugins/interactive-registry.ts @@ -13,11 +13,13 @@ import { } from "./interactive-state.js"; import type { PluginInteractiveHandlerRegistration } from "./types.js"; +/** Registration result for plugin interactive namespace handlers. */ export type InteractiveRegistrationResult = { ok: boolean; error?: string; }; +/** Resolves a channel payload to a registered plugin interactive namespace handler. */ export function resolvePluginInteractiveNamespaceMatch( channel: string, data: string, @@ -29,6 +31,7 @@ export function resolvePluginInteractiveNamespaceMatch( }); } +/** Registers one plugin interactive namespace for a channel. */ export function registerPluginInteractiveHandler( pluginId: string, registration: PluginInteractiveHandlerRegistration, @@ -59,14 +62,17 @@ export function registerPluginInteractiveHandler( return { ok: true }; } +/** Clears all active plugin interactive handlers. */ export function clearPluginInteractiveHandlers(): void { clearPluginInteractiveHandlersState(); } +/** Clears stored plugin interactive handler registrations. */ export function clearPluginInteractiveHandlerRegistrations(): void { clearPluginInteractiveHandlerRegistrationsState(); } +/** Clears active interactive handlers owned by one plugin. */ export function clearPluginInteractiveHandlersForPlugin(pluginId: string): void { const interactiveHandlers = getPluginInteractiveHandlersState(); for (const [key, value] of interactiveHandlers.entries()) { @@ -76,10 +82,12 @@ export function clearPluginInteractiveHandlersForPlugin(pluginId: string): void } } +/** Lists active plugin interactive handlers. */ export function listPluginInteractiveHandlers(): RegisteredInteractiveHandler[] { return Array.from(getPluginInteractiveHandlersState().values()); } +/** Restores active plugin interactive handlers from a saved registry snapshot. */ export function restorePluginInteractiveHandlers( registrations: readonly RegisteredInteractiveHandler[], ): void { diff --git a/src/plugins/path-safety.ts b/src/plugins/path-safety.ts index bfa2c2202f5..bbaad09bc83 100644 --- a/src/plugins/path-safety.ts +++ b/src/plugins/path-safety.ts @@ -1,3 +1,4 @@ +/** Plugin-local re-export of shared path safety helpers for plugin install/runtime code. */ export { isNotFoundPathError, hasNodeErrorCode, diff --git a/src/plugins/provider-auth-choice.runtime.ts b/src/plugins/provider-auth-choice.runtime.ts index 1faf872efbe..925a2e78a72 100644 --- a/src/plugins/provider-auth-choice.runtime.ts +++ b/src/plugins/provider-auth-choice.runtime.ts @@ -12,24 +12,28 @@ type RunProviderModelSelectedHook = type ResolvePluginProviders = typeof import("./providers.runtime.js").resolvePluginProviders; type ResolvePluginSetupProvider = typeof import("./setup-registry.js").resolvePluginSetupProvider; +/** Runtime wrapper for provider plugin wizard choice resolution. */ export function resolveProviderPluginChoice( ...args: Parameters ): ReturnType { return resolveProviderPluginChoiceImpl(...args); } +/** Runtime wrapper for provider model-selected hook dispatch. */ export function runProviderModelSelectedHook( ...args: Parameters ): ReturnType { return runProviderModelSelectedHookImpl(...args); } +/** Runtime wrapper for registered model provider discovery. */ export function resolvePluginProviders( ...args: Parameters ): ReturnType { return resolvePluginProvidersImpl(...args); } +/** Runtime wrapper for plugin setup-provider discovery. */ export function resolvePluginSetupProvider( ...args: Parameters ): ReturnType { diff --git a/src/plugins/provider-auth-mode.ts b/src/plugins/provider-auth-mode.ts index 183e2b36257..bc2ab0abef6 100644 --- a/src/plugins/provider-auth-mode.ts +++ b/src/plugins/provider-auth-mode.ts @@ -1,6 +1,7 @@ import type { WizardPrompter } from "../wizard/prompts.js"; import type { SecretInputMode } from "./provider-auth-types.js"; +/** Prompt copy overrides for provider secret input mode selection. */ export type SecretInputModePromptCopy = { modeMessage?: string; plaintextLabel?: string; @@ -9,6 +10,7 @@ export type SecretInputModePromptCopy = { refHint?: string; }; +/** Resolves provider secret input mode from explicit option or wizard selection. */ export async function resolveSecretInputModeForEnvSelection(params: { prompter: Pick; explicitMode?: SecretInputMode; diff --git a/src/plugins/provider-auth-types.ts b/src/plugins/provider-auth-types.ts index c26ba4778d8..c33ac3d9dd5 100644 --- a/src/plugins/provider-auth-types.ts +++ b/src/plugins/provider-auth-types.ts @@ -1 +1,2 @@ +/** Provider secret input modes: inline plaintext or external secret reference. */ export type SecretInputMode = "plaintext" | "ref"; // pragma: allowlist secret diff --git a/src/plugins/provider-config-owner.ts b/src/plugins/provider-config-owner.ts index ea9b97f4a72..83b6f4074b3 100644 --- a/src/plugins/provider-config-owner.ts +++ b/src/plugins/provider-config-owner.ts @@ -12,6 +12,7 @@ const CORE_BUILT_IN_MODEL_APIS = new Set([ "openai-responses", ]); +/** Returns the plugin API id that owns a provider config when it is not core built-in. */ export function resolveProviderConfigApiOwnerHint(params: { provider: string; config?: OpenClawConfig; diff --git a/src/plugins/public-surface-runtime.ts b/src/plugins/public-surface-runtime.ts index 00524b9c4f0..11668b3d8f8 100644 --- a/src/plugins/public-surface-runtime.ts +++ b/src/plugins/public-surface-runtime.ts @@ -12,6 +12,7 @@ export const PUBLIC_SURFACE_SOURCE_EXTENSIONS = [ ".cjs", ] as const; +/** Normalizes a bundled public artifact subpath and rejects traversal/absolute paths. */ export function normalizeBundledPluginArtifactSubpath(artifactBasename: string): string { if ( path.posix.isAbsolute(artifactBasename) || @@ -39,6 +40,7 @@ export function normalizeBundledPluginArtifactSubpath(artifactBasename: string): return normalized; } +/** Normalizes a bundled plugin directory name and rejects path-like values. */ export function normalizeBundledPluginDirName(dirName: string): string { const normalized = dirName.trim(); if ( @@ -54,6 +56,7 @@ export function normalizeBundledPluginDirName(dirName: string): string { return normalized; } +/** Resolves a source-tree public surface artifact path for bundled plugin development. */ export function resolveBundledPluginSourcePublicSurfacePath(params: { sourceRoot: string; dirName: string; @@ -153,6 +156,7 @@ function resolvePublicSurfaceFromBundledDir(params: { ); } +/** Resolves a bundled plugin public surface artifact across source, dist, and package layouts. */ export function resolveBundledPluginPublicSurfacePath(params: { rootDir: string; dirName: string;