mirror of
https://github.com/openclaw/openclaw.git
synced 2026-04-24 15:41:40 +00:00
fix: unblock cli startup metadata
This commit is contained in:
16
extensions/browser/cli-metadata.ts
Normal file
16
extensions/browser/cli-metadata.ts
Normal file
@@ -0,0 +1,16 @@
|
||||
import { definePluginEntry } from "openclaw/plugin-sdk/core";
|
||||
|
||||
export default definePluginEntry({
|
||||
id: "browser",
|
||||
name: "Browser",
|
||||
description: "Default browser tool plugin",
|
||||
register(api) {
|
||||
api.registerCli(
|
||||
async ({ program }) => {
|
||||
const { registerBrowserCli } = await import("./runtime-api.js");
|
||||
registerBrowserCli(program);
|
||||
},
|
||||
{ commands: ["browser"] },
|
||||
);
|
||||
},
|
||||
});
|
||||
10
extensions/discord/contract-surfaces.ts
Normal file
10
extensions/discord/contract-surfaces.ts
Normal file
@@ -0,0 +1,10 @@
|
||||
export { normalizeCompatibilityConfig, legacyConfigRules } from "./src/doctor-contract.js";
|
||||
export {
|
||||
collectRuntimeConfigAssignments,
|
||||
secretTargetRegistryEntries,
|
||||
} from "./src/secret-config-contract.js";
|
||||
export {
|
||||
unsupportedSecretRefSurfacePatterns,
|
||||
collectUnsupportedSecretRefConfigCandidates,
|
||||
} from "./src/security-contract.js";
|
||||
export { deriveLegacySessionChatType } from "./src/session-contract.js";
|
||||
5
extensions/feishu/contract-surfaces.ts
Normal file
5
extensions/feishu/contract-surfaces.ts
Normal file
@@ -0,0 +1,5 @@
|
||||
export {
|
||||
collectRuntimeConfigAssignments,
|
||||
secretTargetRegistryEntries,
|
||||
} from "./src/secret-contract.js";
|
||||
export { messageActionTargetAliases } from "./src/message-action-contract.js";
|
||||
4
extensions/googlechat/contract-surfaces.ts
Normal file
4
extensions/googlechat/contract-surfaces.ts
Normal file
@@ -0,0 +1,4 @@
|
||||
export {
|
||||
collectRuntimeConfigAssignments,
|
||||
secretTargetRegistryEntries,
|
||||
} from "./src/secret-contract.js";
|
||||
@@ -1,4 +1,4 @@
|
||||
import { coerceSecretRef } from "openclaw/plugin-sdk/config-runtime";
|
||||
import { coerceSecretRef } from "openclaw/plugin-sdk/provider-auth";
|
||||
import {
|
||||
getChannelSurface,
|
||||
hasOwnProperty,
|
||||
|
||||
103
extensions/imessage/contract-surfaces.ts
Normal file
103
extensions/imessage/contract-surfaces.ts
Normal file
@@ -0,0 +1,103 @@
|
||||
import path from "node:path";
|
||||
import type { OpenClawConfig } from "./runtime-api.js";
|
||||
import { resolveIMessageAccount } from "./src/accounts.js";
|
||||
|
||||
const DEFAULT_IMESSAGE_ATTACHMENT_ROOTS = ["/Users/*/Library/Messages/Attachments"] as const;
|
||||
const WILDCARD_SEGMENT = "*";
|
||||
const WINDOWS_DRIVE_ABS_RE = /^[A-Za-z]:\//;
|
||||
const WINDOWS_DRIVE_ROOT_RE = /^[A-Za-z]:$/;
|
||||
|
||||
function normalizePosixAbsolutePath(value: string): string | undefined {
|
||||
const trimmed = value.trim();
|
||||
if (!trimmed || trimmed.includes("\0")) {
|
||||
return undefined;
|
||||
}
|
||||
const normalized = path.posix.normalize(trimmed.replaceAll("\\", "/"));
|
||||
const isAbsolute = normalized.startsWith("/") || WINDOWS_DRIVE_ABS_RE.test(normalized);
|
||||
if (!isAbsolute || normalized === "/") {
|
||||
return undefined;
|
||||
}
|
||||
const withoutTrailingSlash = normalized.endsWith("/") ? normalized.slice(0, -1) : normalized;
|
||||
if (WINDOWS_DRIVE_ROOT_RE.test(withoutTrailingSlash)) {
|
||||
return undefined;
|
||||
}
|
||||
return withoutTrailingSlash;
|
||||
}
|
||||
|
||||
function splitPathSegments(value: string): string[] {
|
||||
return value.split("/").filter(Boolean);
|
||||
}
|
||||
|
||||
function isValidInboundPathRootPattern(value: string): boolean {
|
||||
const normalized = normalizePosixAbsolutePath(value);
|
||||
if (!normalized) {
|
||||
return false;
|
||||
}
|
||||
const segments = splitPathSegments(normalized);
|
||||
if (segments.length === 0) {
|
||||
return false;
|
||||
}
|
||||
return segments.every((segment) => segment === WILDCARD_SEGMENT || !segment.includes("*"));
|
||||
}
|
||||
|
||||
function normalizeInboundPathRoots(roots?: readonly string[]): string[] {
|
||||
const normalized: string[] = [];
|
||||
const seen = new Set<string>();
|
||||
for (const root of roots ?? []) {
|
||||
if (typeof root !== "string") {
|
||||
continue;
|
||||
}
|
||||
if (!isValidInboundPathRootPattern(root)) {
|
||||
continue;
|
||||
}
|
||||
const candidate = normalizePosixAbsolutePath(root);
|
||||
if (!candidate || seen.has(candidate)) {
|
||||
continue;
|
||||
}
|
||||
seen.add(candidate);
|
||||
normalized.push(candidate);
|
||||
}
|
||||
return normalized;
|
||||
}
|
||||
|
||||
function mergeInboundPathRoots(...rootsLists: Array<readonly string[] | undefined>): string[] {
|
||||
const merged: string[] = [];
|
||||
const seen = new Set<string>();
|
||||
for (const roots of rootsLists) {
|
||||
const normalized = normalizeInboundPathRoots(roots);
|
||||
for (const root of normalized) {
|
||||
if (seen.has(root)) {
|
||||
continue;
|
||||
}
|
||||
seen.add(root);
|
||||
merged.push(root);
|
||||
}
|
||||
}
|
||||
return merged;
|
||||
}
|
||||
|
||||
export function resolveInboundAttachmentRoots(params: {
|
||||
cfg: OpenClawConfig;
|
||||
accountId?: string | null;
|
||||
}): string[] {
|
||||
const account = resolveIMessageAccount(params);
|
||||
return mergeInboundPathRoots(
|
||||
account.config.attachmentRoots,
|
||||
params.cfg.channels?.imessage?.attachmentRoots,
|
||||
DEFAULT_IMESSAGE_ATTACHMENT_ROOTS,
|
||||
);
|
||||
}
|
||||
|
||||
export function resolveRemoteInboundAttachmentRoots(params: {
|
||||
cfg: OpenClawConfig;
|
||||
accountId?: string | null;
|
||||
}): string[] {
|
||||
const account = resolveIMessageAccount(params);
|
||||
return mergeInboundPathRoots(
|
||||
account.config.remoteAttachmentRoots,
|
||||
params.cfg.channels?.imessage?.remoteAttachmentRoots,
|
||||
account.config.attachmentRoots,
|
||||
params.cfg.channels?.imessage?.attachmentRoots,
|
||||
DEFAULT_IMESSAGE_ATTACHMENT_ROOTS,
|
||||
);
|
||||
}
|
||||
1
extensions/line/contract-surfaces.ts
Normal file
1
extensions/line/contract-surfaces.ts
Normal file
@@ -0,0 +1 @@
|
||||
export {};
|
||||
9
extensions/matrix/cli-metadata.ts
Normal file
9
extensions/matrix/cli-metadata.ts
Normal file
@@ -0,0 +1,9 @@
|
||||
import { definePluginEntry } from "openclaw/plugin-sdk/core";
|
||||
import { registerMatrixCliMetadata } from "./src/cli-metadata.js";
|
||||
|
||||
export default definePluginEntry({
|
||||
id: "matrix",
|
||||
name: "Matrix",
|
||||
description: "Matrix channel plugin (matrix-js-sdk)",
|
||||
register: registerMatrixCliMetadata,
|
||||
});
|
||||
9
extensions/matrix/contract-surfaces.ts
Normal file
9
extensions/matrix/contract-surfaces.ts
Normal file
@@ -0,0 +1,9 @@
|
||||
export {
|
||||
namedAccountPromotionKeys,
|
||||
resolveSingleAccountPromotionTarget,
|
||||
singleAccountKeysToMove,
|
||||
} from "./src/setup-contract.js";
|
||||
export {
|
||||
collectRuntimeConfigAssignments,
|
||||
secretTargetRegistryEntries,
|
||||
} from "./src/secret-contract.js";
|
||||
@@ -1,5 +1,6 @@
|
||||
import { defineChannelPluginEntry } from "openclaw/plugin-sdk/core";
|
||||
import { matrixPlugin } from "./src/channel.js";
|
||||
import { registerMatrixCliMetadata } from "./src/cli-metadata.js";
|
||||
import { setMatrixRuntime } from "./src/runtime.js";
|
||||
|
||||
export { matrixPlugin } from "./src/channel.js";
|
||||
@@ -11,23 +12,7 @@ export default defineChannelPluginEntry({
|
||||
description: "Matrix channel plugin (matrix-js-sdk)",
|
||||
plugin: matrixPlugin,
|
||||
setRuntime: setMatrixRuntime,
|
||||
registerCliMetadata(api) {
|
||||
api.registerCli(
|
||||
async ({ program }) => {
|
||||
const { registerMatrixCli } = await import("./src/cli.js");
|
||||
registerMatrixCli({ program });
|
||||
},
|
||||
{
|
||||
descriptors: [
|
||||
{
|
||||
name: "matrix",
|
||||
description: "Manage Matrix accounts, verification, devices, and profile state",
|
||||
hasSubcommands: true,
|
||||
},
|
||||
],
|
||||
},
|
||||
);
|
||||
},
|
||||
registerCliMetadata: registerMatrixCliMetadata,
|
||||
registerFull(api) {
|
||||
void import("./src/plugin-entry.runtime.js")
|
||||
.then(({ ensureMatrixCryptoRuntime }) =>
|
||||
|
||||
19
extensions/matrix/src/cli-metadata.ts
Normal file
19
extensions/matrix/src/cli-metadata.ts
Normal file
@@ -0,0 +1,19 @@
|
||||
import type { OpenClawPluginApi } from "openclaw/plugin-sdk/core";
|
||||
|
||||
export function registerMatrixCliMetadata(api: OpenClawPluginApi) {
|
||||
api.registerCli(
|
||||
async ({ program }) => {
|
||||
const { registerMatrixCli } = await import("./cli.js");
|
||||
registerMatrixCli({ program });
|
||||
},
|
||||
{
|
||||
descriptors: [
|
||||
{
|
||||
name: "matrix",
|
||||
description: "Manage Matrix accounts, verification, devices, and profile state",
|
||||
hasSubcommands: true,
|
||||
},
|
||||
],
|
||||
},
|
||||
);
|
||||
}
|
||||
4
extensions/mattermost/contract-surfaces.ts
Normal file
4
extensions/mattermost/contract-surfaces.ts
Normal file
@@ -0,0 +1,4 @@
|
||||
export {
|
||||
collectRuntimeConfigAssignments,
|
||||
secretTargetRegistryEntries,
|
||||
} from "./src/secret-contract.js";
|
||||
24
extensions/memory-core/cli-metadata.ts
Normal file
24
extensions/memory-core/cli-metadata.ts
Normal file
@@ -0,0 +1,24 @@
|
||||
import { definePluginEntry } from "openclaw/plugin-sdk/core";
|
||||
|
||||
export default definePluginEntry({
|
||||
id: "memory-core",
|
||||
name: "Memory (Core)",
|
||||
description: "File-backed memory search tools and CLI",
|
||||
register(api) {
|
||||
api.registerCli(
|
||||
async ({ program }) => {
|
||||
const { registerMemoryCli } = await import("./src/cli.js");
|
||||
registerMemoryCli(program);
|
||||
},
|
||||
{
|
||||
descriptors: [
|
||||
{
|
||||
name: "memory",
|
||||
description: "Search, inspect, and reindex memory files",
|
||||
hasSubcommands: true,
|
||||
},
|
||||
],
|
||||
},
|
||||
);
|
||||
},
|
||||
});
|
||||
10
extensions/memory-lancedb/cli-metadata.ts
Normal file
10
extensions/memory-lancedb/cli-metadata.ts
Normal file
@@ -0,0 +1,10 @@
|
||||
import { definePluginEntry } from "openclaw/plugin-sdk/core";
|
||||
|
||||
export default definePluginEntry({
|
||||
id: "memory-lancedb",
|
||||
name: "Memory LanceDB",
|
||||
description: "LanceDB-backed memory provider",
|
||||
register(api) {
|
||||
api.registerCli(() => {}, { commands: ["ltm"] });
|
||||
},
|
||||
});
|
||||
1
extensions/signal/contract-surfaces.ts
Normal file
1
extensions/signal/contract-surfaces.ts
Normal file
@@ -0,0 +1 @@
|
||||
export {};
|
||||
5
extensions/slack/contract-surfaces.ts
Normal file
5
extensions/slack/contract-surfaces.ts
Normal file
@@ -0,0 +1,5 @@
|
||||
export { normalizeCompatibilityConfig, legacyConfigRules } from "./src/doctor-contract.js";
|
||||
export {
|
||||
collectRuntimeConfigAssignments,
|
||||
secretTargetRegistryEntries,
|
||||
} from "./src/secret-contract.js";
|
||||
1
extensions/synology-chat/contract-surfaces.ts
Normal file
1
extensions/synology-chat/contract-surfaces.ts
Normal file
@@ -0,0 +1 @@
|
||||
export {};
|
||||
6
extensions/telegram/contract-surfaces.ts
Normal file
6
extensions/telegram/contract-surfaces.ts
Normal file
@@ -0,0 +1,6 @@
|
||||
export { normalizeCompatibilityConfig, legacyConfigRules } from "./src/doctor-contract.js";
|
||||
export {
|
||||
collectRuntimeConfigAssignments,
|
||||
secretTargetRegistryEntries,
|
||||
} from "./src/secret-contract.js";
|
||||
export { singleAccountKeysToMove } from "./src/setup-contract.js";
|
||||
10
extensions/voice-call/cli-metadata.ts
Normal file
10
extensions/voice-call/cli-metadata.ts
Normal file
@@ -0,0 +1,10 @@
|
||||
import { definePluginEntry } from "openclaw/plugin-sdk/core";
|
||||
|
||||
export default definePluginEntry({
|
||||
id: "voice-call",
|
||||
name: "Voice Call",
|
||||
description: "Voice call channel plugin",
|
||||
register(api) {
|
||||
api.registerCli(() => {}, { commands: ["voicecall"] });
|
||||
},
|
||||
});
|
||||
49
extensions/whatsapp/contract-surfaces.ts
Normal file
49
extensions/whatsapp/contract-surfaces.ts
Normal file
@@ -0,0 +1,49 @@
|
||||
type UnsupportedSecretRefConfigCandidate = {
|
||||
path: string;
|
||||
value: unknown;
|
||||
};
|
||||
|
||||
function isRecord(value: unknown): value is Record<string, unknown> {
|
||||
return typeof value === "object" && value !== null;
|
||||
}
|
||||
|
||||
export const unsupportedSecretRefSurfacePatterns = [
|
||||
"channels.whatsapp.creds.json",
|
||||
"channels.whatsapp.accounts.*.creds.json",
|
||||
] as const;
|
||||
|
||||
export function collectUnsupportedSecretRefConfigCandidates(
|
||||
raw: unknown,
|
||||
): UnsupportedSecretRefConfigCandidate[] {
|
||||
if (!isRecord(raw)) {
|
||||
return [];
|
||||
}
|
||||
if (!isRecord(raw.channels) || !isRecord(raw.channels.whatsapp)) {
|
||||
return [];
|
||||
}
|
||||
|
||||
const candidates: UnsupportedSecretRefConfigCandidate[] = [];
|
||||
const whatsapp = raw.channels.whatsapp;
|
||||
const creds = isRecord(whatsapp.creds) ? whatsapp.creds : null;
|
||||
if (creds) {
|
||||
candidates.push({
|
||||
path: "channels.whatsapp.creds.json",
|
||||
value: creds.json,
|
||||
});
|
||||
}
|
||||
|
||||
const accounts = isRecord(whatsapp.accounts) ? whatsapp.accounts : null;
|
||||
if (!accounts) {
|
||||
return candidates;
|
||||
}
|
||||
for (const [accountId, account] of Object.entries(accounts)) {
|
||||
if (!isRecord(account) || !isRecord(account.creds)) {
|
||||
continue;
|
||||
}
|
||||
candidates.push({
|
||||
path: `channels.whatsapp.accounts.${accountId}.creds.json`,
|
||||
value: account.creds.json,
|
||||
});
|
||||
}
|
||||
return candidates;
|
||||
}
|
||||
4
extensions/zalo/contract-surfaces.ts
Normal file
4
extensions/zalo/contract-surfaces.ts
Normal file
@@ -0,0 +1,4 @@
|
||||
export {
|
||||
collectRuntimeConfigAssignments,
|
||||
secretTargetRegistryEntries,
|
||||
} from "./src/secret-contract.js";
|
||||
1
extensions/zalouser/contract-surfaces.ts
Normal file
1
extensions/zalouser/contract-surfaces.ts
Normal file
@@ -0,0 +1 @@
|
||||
export {};
|
||||
Reference in New Issue
Block a user