@nextclaw/service 0.1.17 → 0.1.18-beta.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (85) hide show
  1. package/dist/cli/commands/agent/cli-agent-runner.utils.d.ts.map +1 -1
  2. package/dist/cli/commands/agent/cli-agent-runner.utils.js +9 -5
  3. package/dist/cli/commands/agent/cli-agent-runner.utils.js.map +1 -1
  4. package/dist/cli/commands/config/services/config-commands.service.d.ts +0 -2
  5. package/dist/cli/commands/config/services/config-commands.service.d.ts.map +1 -1
  6. package/dist/cli/commands/config/services/config-commands.service.js +7 -25
  7. package/dist/cli/commands/config/services/config-commands.service.js.map +1 -1
  8. package/dist/commands/channel/channel-config-view.utils.d.ts +7 -0
  9. package/dist/commands/channel/channel-config-view.utils.d.ts.map +1 -0
  10. package/dist/commands/channel/channel-config-view.utils.js +9 -0
  11. package/dist/commands/channel/channel-config-view.utils.js.map +1 -0
  12. package/dist/commands/channel/channel-list-view.service.d.ts +0 -4
  13. package/dist/commands/channel/channel-list-view.service.d.ts.map +1 -1
  14. package/dist/commands/channel/channel-list-view.service.js +6 -19
  15. package/dist/commands/channel/channel-list-view.service.js.map +1 -1
  16. package/dist/commands/channel/index.d.ts +1 -12
  17. package/dist/commands/channel/index.d.ts.map +1 -1
  18. package/dist/commands/channel/index.js +26 -160
  19. package/dist/commands/channel/index.js.map +1 -1
  20. package/dist/service-runtime.service.d.ts +0 -2
  21. package/dist/service-runtime.service.d.ts.map +1 -1
  22. package/dist/service-runtime.service.js +10 -28
  23. package/dist/service-runtime.service.js.map +1 -1
  24. package/dist/shared/services/gateway/managers/gateway-extension.manager.d.ts +23 -0
  25. package/dist/shared/services/gateway/managers/gateway-extension.manager.d.ts.map +1 -0
  26. package/dist/shared/services/gateway/managers/gateway-extension.manager.js +77 -0
  27. package/dist/shared/services/gateway/managers/gateway-extension.manager.js.map +1 -0
  28. package/dist/shared/services/gateway/nextclaw-app.service.d.ts.map +1 -1
  29. package/dist/shared/services/gateway/nextclaw-app.service.js +2 -3
  30. package/dist/shared/services/gateway/nextclaw-app.service.js.map +1 -1
  31. package/dist/shared/services/gateway/nextclaw-gateway-runtime.service.d.ts +4 -5
  32. package/dist/shared/services/gateway/nextclaw-gateway-runtime.service.d.ts.map +1 -1
  33. package/dist/shared/services/gateway/nextclaw-gateway-runtime.service.js +13 -38
  34. package/dist/shared/services/gateway/nextclaw-gateway-runtime.service.js.map +1 -1
  35. package/dist/shared/services/gateway/service-bootstrap-status.service.d.ts +9 -9
  36. package/dist/shared/services/gateway/service-bootstrap-status.service.d.ts.map +1 -1
  37. package/dist/shared/services/gateway/service-bootstrap-status.service.js +24 -24
  38. package/dist/shared/services/gateway/service-bootstrap-status.service.js.map +1 -1
  39. package/dist/shared/services/gateway/service-startup-support.service.d.ts +1 -9
  40. package/dist/shared/services/gateway/service-startup-support.service.d.ts.map +1 -1
  41. package/dist/shared/services/gateway/service-startup-support.service.js +1 -14
  42. package/dist/shared/services/gateway/service-startup-support.service.js.map +1 -1
  43. package/dist/shared/services/gateway/utils/cron-job-handler.utils.d.ts +2 -2
  44. package/dist/shared/services/gateway/utils/cron-job-handler.utils.d.ts.map +1 -1
  45. package/dist/shared/services/gateway/utils/cron-job-handler.utils.js +7 -14
  46. package/dist/shared/services/gateway/utils/cron-job-handler.utils.js.map +1 -1
  47. package/dist/shared/services/gateway/utils/gateway-runtime-lifecycle.utils.js +1 -1
  48. package/dist/shared/services/gateway/utils/gateway-runtime-lifecycle.utils.js.map +1 -1
  49. package/dist/shared/services/marketplace/service-marketplace-installer.service.d.ts +0 -4
  50. package/dist/shared/services/marketplace/service-marketplace-installer.service.d.ts.map +1 -1
  51. package/dist/shared/services/marketplace/service-marketplace-installer.service.js +0 -27
  52. package/dist/shared/services/marketplace/service-marketplace-installer.service.js.map +1 -1
  53. package/dist/shared/services/workspace/workspace-manager.service.d.ts +0 -7
  54. package/dist/shared/services/workspace/workspace-manager.service.d.ts.map +1 -1
  55. package/dist/shared/services/workspace/workspace-manager.service.js +2 -50
  56. package/dist/shared/services/workspace/workspace-manager.service.js.map +1 -1
  57. package/package.json +33 -20
  58. package/dist/commands/channel/channel-config-view.d.ts +0 -8
  59. package/dist/commands/channel/channel-config-view.d.ts.map +0 -1
  60. package/dist/commands/channel/channel-config-view.js +0 -9
  61. package/dist/commands/channel/channel-config-view.js.map +0 -1
  62. package/dist/commands/plugin/index.d.ts +0 -29
  63. package/dist/commands/plugin/index.d.ts.map +0 -1
  64. package/dist/commands/plugin/index.js +0 -256
  65. package/dist/commands/plugin/index.js.map +0 -1
  66. package/dist/commands/plugin/plugin-command.utils.d.ts +0 -13
  67. package/dist/commands/plugin/plugin-command.utils.d.ts.map +0 -1
  68. package/dist/commands/plugin/plugin-command.utils.js +0 -37
  69. package/dist/commands/plugin/plugin-command.utils.js.map +0 -1
  70. package/dist/commands/plugin/plugin-mutation-actions.utils.d.ts +0 -16
  71. package/dist/commands/plugin/plugin-mutation-actions.utils.d.ts.map +0 -1
  72. package/dist/commands/plugin/plugin-mutation-actions.utils.js +0 -164
  73. package/dist/commands/plugin/plugin-mutation-actions.utils.js.map +0 -1
  74. package/dist/shared/services/gateway/managers/gateway-plugin.manager.d.ts +0 -32
  75. package/dist/shared/services/gateway/managers/gateway-plugin.manager.d.ts.map +0 -1
  76. package/dist/shared/services/gateway/managers/gateway-plugin.manager.js +0 -176
  77. package/dist/shared/services/gateway/managers/gateway-plugin.manager.js.map +0 -1
  78. package/dist/shared/services/plugin/utils/plugin-dev-hot-reload.utils.d.ts +0 -25
  79. package/dist/shared/services/plugin/utils/plugin-dev-hot-reload.utils.d.ts.map +0 -1
  80. package/dist/shared/services/plugin/utils/plugin-dev-hot-reload.utils.js +0 -119
  81. package/dist/shared/services/plugin/utils/plugin-dev-hot-reload.utils.js.map +0 -1
  82. package/dist/shared/services/plugin/utils/plugin-runtime-bridge.utils.d.ts +0 -7
  83. package/dist/shared/services/plugin/utils/plugin-runtime-bridge.utils.d.ts.map +0 -1
  84. package/dist/shared/services/plugin/utils/plugin-runtime-bridge.utils.js +0 -97
  85. package/dist/shared/services/plugin/utils/plugin-runtime-bridge.utils.js.map +0 -1
@@ -1 +0,0 @@
1
- {"version":3,"file":"index.js","names":[],"sources":["../../../src/commands/plugin/index.ts"],"sourcesContent":["import {\n buildPluginStatusReport,\n resolveUninstallDirectoryTargets,\n type PluginRegistry\n} from \"@nextclaw/openclaw-compat\";\nimport {\n appendPluginCapabilityLines,\n buildReservedPluginLoadOptions,\n} from \"./plugin-command.utils.js\";\nimport { ExtensionPluginRegistryService } from \"@nextclaw/kernel\";\nimport {\n loadConfig,\n type Config,\n getWorkspacePath\n} from \"@nextclaw/core\";\nimport { createInterface } from \"node:readline\";\nimport { resolve } from \"node:path\";\nimport type {\n PluginsInfoOptions,\n PluginsInstallOptions,\n PluginsListOptions,\n PluginsUninstallOptions\n} from \"../../shared/types/cli.types.js\";\nimport {\n disablePluginMutation,\n enablePluginMutation,\n installPluginMutation,\n uninstallPluginMutation,\n} from \"./plugin-mutation-actions.utils.js\";\nexport { mergePluginConfigView, toPluginConfigView } from \"@nextclaw/openclaw-compat\";\n\ntype PluginStatusReport = ReturnType<typeof buildPluginStatusReport>;\ntype PluginStatusEntry = PluginStatusReport[\"plugins\"][number];\ntype PluginInstallRecord = NonNullable<Config[\"plugins\"][\"installs\"]>[string];\n\nexport function loadPluginRegistry(config: Config, workspaceDir: string): PluginRegistry {\n return new ExtensionPluginRegistryService().load({\n config,\n workspace: workspaceDir,\n });\n}\n\nexport function logPluginDiagnostics(registry: Pick<PluginRegistry, \"diagnostics\">): void {\n for (const diag of registry.diagnostics) {\n const prefix = diag.pluginId ? `${diag.pluginId}: ` : \"\";\n const text = `${prefix}${diag.message}`;\n if (diag.level === \"error\") {\n console.error(`[plugins] ${text}`);\n } else {\n console.warn(`[plugins] ${text}`);\n }\n };\n}\n\nexport class PluginCommands {\n list = (opts: PluginsListOptions = {}): void => {\n const { report, workspaceDir } = this.loadStatusReport();\n\n const list = opts.enabled ? report.plugins.filter((plugin) => plugin.status === \"loaded\") : report.plugins;\n\n if (opts.json) {\n console.log(\n JSON.stringify(\n {\n workspaceDir,\n plugins: list,\n diagnostics: report.diagnostics\n },\n null,\n 2\n )\n );\n return;\n }\n\n if (list.length === 0) {\n console.log(\"No plugins discovered.\");\n return;\n }\n\n for (const plugin of list) {\n const status = plugin.status === \"loaded\" ? \"loaded\" : plugin.status === \"disabled\" ? \"disabled\" : \"error\";\n const title = plugin.name && plugin.name !== plugin.id ? `${plugin.name} (${plugin.id})` : plugin.id;\n if (!opts.verbose) {\n const desc = plugin.description\n ? plugin.description.length > 80\n ? `${plugin.description.slice(0, 77)}...`\n : plugin.description\n : \"(no description)\";\n console.log(`${title} ${status} - ${desc}`);\n continue;\n }\n\n console.log(`${title} ${status}`);\n console.log(` source: ${plugin.source}`);\n console.log(` origin: ${plugin.origin}`);\n if (plugin.version) {\n console.log(` version: ${plugin.version}`);\n }\n const capabilityLines: string[] = [];\n appendPluginCapabilityLines(capabilityLines, plugin);\n for (const line of capabilityLines) {\n console.log(` ${line.toLowerCase()}`);\n }\n if (plugin.error) {\n console.log(` error: ${plugin.error}`);\n }\n console.log(\"\");\n }\n };\n\n info = (id: string, opts: PluginsInfoOptions = {}): void => {\n const { config, report } = this.loadStatusReport();\n const plugin = report.plugins.find((entry) => entry.id === id || entry.name === id);\n if (!plugin) {\n console.error(`Plugin not found: ${id}`);\n process.exit(1);\n }\n\n if (opts.json) {\n console.log(JSON.stringify(plugin, null, 2));\n return;\n }\n\n console.log(this.buildPluginInfoLines(plugin, config).join(\"\\n\"));\n };\n\n enable = async (id: string): Promise<void> => {\n try {\n const result = await enablePluginMutation(id);\n console.log(result.message);\n } catch (error) {\n console.error(error instanceof Error ? error.message : String(error));\n process.exit(1);\n }\n console.log(\"If gateway is running, plugin changes are hot-applied automatically.\");\n };\n\n disable = async (id: string): Promise<void> => {\n try {\n const result = await disablePluginMutation(id);\n console.log(result.message);\n } catch (error) {\n console.error(error instanceof Error ? error.message : String(error));\n process.exit(1);\n }\n console.log(\"If gateway is running, plugin changes are hot-applied automatically.\");\n };\n\n uninstall = async (id: string, opts: PluginsUninstallOptions = {}): Promise<void> => {\n if (opts.keepConfig) {\n console.log(\"`--keep-config` is deprecated, use `--keep-files`.\");\n }\n\n const { config, report } = this.loadStatusReport();\n\n const keepFiles = Boolean(opts.keepFiles || opts.keepConfig);\n const plugin = report.plugins.find((entry) => entry.id === id || entry.name === id);\n const pluginId = plugin?.id ?? id;\n\n const hasEntry = pluginId in (config.plugins.entries ?? {});\n const hasInstall = pluginId in (config.plugins.installs ?? {});\n\n this.assertPluginCanUninstall(id, pluginId, plugin, hasEntry, hasInstall);\n\n const install = config.plugins.installs?.[pluginId];\n const preview = this.buildUninstallPreview({ config, hasEntry, hasInstall, install, keepFiles, pluginId });\n\n const pluginName = plugin?.name || pluginId;\n const pluginTitle = pluginName !== pluginId ? `${pluginName} (${pluginId})` : pluginName;\n console.log(`Plugin: ${pluginTitle}`);\n console.log(`Will remove: ${preview.length > 0 ? preview.join(\", \") : \"(nothing)\"}`);\n\n if (opts.dryRun) {\n console.log(\"Dry run, no changes made.\");\n return;\n }\n\n if (!(await this.confirmUninstall(pluginId, opts))) {\n return;\n }\n await this.runUninstallMutation(id, opts);\n console.log(\"If gateway is running, plugin changes are hot-applied automatically.\");\n };\n\n install = async (pathOrSpec: string, opts: PluginsInstallOptions = {}): Promise<void> => {\n try {\n const result = await installPluginMutation(pathOrSpec, opts);\n console.log(result.message);\n } catch (error) {\n console.error(error instanceof Error ? error.message : String(error));\n process.exit(1);\n }\n console.log(\"If gateway is running, plugin changes are hot-applied automatically.\");\n };\n\n doctor = (): void => {\n const { report } = this.loadStatusReport();\n\n const pluginErrors = report.plugins.filter((plugin) => plugin.status === \"error\");\n const diagnostics = report.diagnostics.filter((diag) => diag.level === \"error\");\n\n if (pluginErrors.length === 0 && diagnostics.length === 0) {\n console.log(\"No plugin issues detected.\");\n return;\n }\n\n if (pluginErrors.length > 0) {\n console.log(\"Plugin errors:\");\n for (const entry of pluginErrors) {\n console.log(`- ${entry.id}: ${entry.error ?? \"failed to load\"} (${entry.source})`);\n }\n }\n\n if (diagnostics.length > 0) {\n if (pluginErrors.length > 0) {\n console.log(\"\");\n }\n console.log(\"Diagnostics:\");\n for (const diag of diagnostics) {\n const prefix = diag.pluginId ? `${diag.pluginId}: ` : \"\";\n console.log(`- ${prefix}${diag.message}`);\n }\n }\n };\n\n private confirmYesNo = async (question: string): Promise<boolean> => {\n const rl = createInterface({\n input: process.stdin,\n output: process.stdout\n });\n\n const answer = await new Promise<string>((resolve) => {\n rl.question(`${question} [y/N] `, (line) => resolve(line));\n });\n\n rl.close();\n const normalized = answer.trim().toLowerCase();\n return normalized === \"y\" || normalized === \"yes\";\n };\n\n private confirmUninstall = async (pluginId: string, opts: PluginsUninstallOptions): Promise<boolean> => {\n if (opts.force) {\n return true;\n }\n const confirmed = await this.confirmYesNo(`Uninstall plugin \"${pluginId}\"?`);\n if (!confirmed) {\n console.log(\"Cancelled.\");\n }\n return confirmed;\n };\n\n private runUninstallMutation = async (id: string, opts: PluginsUninstallOptions): Promise<void> => {\n try {\n const result = await uninstallPluginMutation(id, opts);\n for (const warning of result.warnings) {\n console.warn(warning);\n }\n console.log(result.message);\n } catch (error) {\n console.error(error instanceof Error ? error.message : String(error));\n process.exit(1);\n }\n };\n\n private loadStatusReport = (): { config: Config; report: PluginStatusReport; workspaceDir: string } => {\n const config = loadConfig();\n const workspaceDir = getWorkspacePath(config.agents.defaults.workspace);\n return {\n config,\n workspaceDir,\n report: buildPluginStatusReport({\n config,\n workspaceDir,\n ...buildReservedPluginLoadOptions()\n })\n };\n };\n\n private buildPluginInfoLines = (plugin: PluginStatusEntry, config: Config): string[] => {\n const install = config.plugins.installs?.[plugin.id];\n const lines = this.buildPluginSummaryLines(plugin);\n if (install) {\n lines.push(\"\");\n lines.push(`Install: ${install.source}`);\n this.pushOptionalLine(lines, \"Spec\", install.spec);\n this.pushOptionalLine(lines, \"Source path\", install.sourcePath);\n this.pushOptionalLine(lines, \"Install path\", install.installPath);\n this.pushOptionalLine(lines, \"Recorded version\", install.version);\n this.pushOptionalLine(lines, \"Installed at\", install.installedAt);\n }\n return lines;\n };\n\n private buildPluginSummaryLines = (plugin: PluginStatusEntry): string[] => {\n const lines = [plugin.name || plugin.id];\n if (plugin.name && plugin.name !== plugin.id) {\n lines.push(`id: ${plugin.id}`);\n }\n if (plugin.description) {\n lines.push(plugin.description);\n }\n lines.push(\"\", `Status: ${plugin.status}`, `Source: ${plugin.source}`, `Origin: ${plugin.origin}`);\n this.pushOptionalLine(lines, \"Version\", plugin.version);\n appendPluginCapabilityLines(lines, plugin);\n this.pushOptionalLine(lines, \"Error\", plugin.error);\n return lines;\n };\n\n private pushOptionalLine = (lines: string[], label: string, value: string | undefined): void => {\n if (value) {\n lines.push(`${label}: ${value}`);\n }\n };\n\n private assertPluginCanUninstall = (\n requestedId: string,\n pluginId: string,\n plugin: PluginStatusEntry | undefined,\n hasEntry: boolean,\n hasInstall: boolean,\n ): void => {\n if (hasEntry || hasInstall) {\n return;\n }\n if (plugin) {\n console.error(`Plugin \"${pluginId}\" is not managed by plugins config/install records and cannot be uninstalled.`);\n } else {\n console.error(`Plugin not found: ${requestedId}`);\n }\n process.exit(1);\n };\n\n private buildUninstallPreview = (params: {\n config: Config;\n pluginId: string;\n hasEntry: boolean;\n hasInstall: boolean;\n keepFiles: boolean;\n install: PluginInstallRecord | undefined;\n }): string[] => {\n const { config, hasEntry, hasInstall, install, keepFiles, pluginId } = params;\n const preview = this.buildUninstallConfigPreview({ config, hasEntry, hasInstall, install, pluginId });\n if (!keepFiles) {\n for (const deleteTarget of resolveUninstallDirectoryTargets({ config, pluginId, hasInstall, installRecord: install })) {\n preview.push(`directory: ${deleteTarget}`);\n }\n }\n return preview;\n };\n\n private buildUninstallConfigPreview = (params: {\n config: Config;\n pluginId: string;\n hasEntry: boolean;\n hasInstall: boolean;\n install: PluginInstallRecord | undefined;\n }): string[] => {\n const { config, hasEntry, hasInstall, install, pluginId } = params;\n const preview: string[] = [];\n const isLinked =\n install?.source === \"path\" &&\n (!install.installPath || !install.sourcePath || resolve(install.installPath) === resolve(install.sourcePath));\n if (hasEntry) {\n preview.push(\"config entry\");\n }\n if (hasInstall) {\n preview.push(\"install record\");\n }\n if (config.plugins.allow?.includes(pluginId)) {\n preview.push(\"allowlist entry\");\n }\n if (isLinked && install?.sourcePath && config.plugins.load?.paths?.includes(install.sourcePath)) {\n preview.push(\"load path\");\n }\n return preview;\n };\n}\n"],"mappings":"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"}
@@ -1,13 +0,0 @@
1
- import { PluginRegistry } from "@nextclaw/openclaw-compat";
2
-
3
- //#region src/commands/plugin/plugin-command.utils.d.ts
4
- declare const RESERVED_PROVIDER_IDS: string[];
5
- declare function buildReservedPluginLoadOptions(): {
6
- reservedToolNames: ("read_file" | "write_file" | "edit_file" | "list_dir" | "exec" | "web_search" | "web_fetch" | "message" | "spawn" | "sessions_list" | "sessions_history" | "memory_search" | "memory_get" | "subagents" | "gateway" | "cron")[];
7
- reservedChannelIds: string[];
8
- reservedProviderIds: string[];
9
- };
10
- declare function appendPluginCapabilityLines(lines: string[], plugin: PluginRegistry["plugins"][number]): void;
11
- //#endregion
12
- export { RESERVED_PROVIDER_IDS, appendPluginCapabilityLines, buildReservedPluginLoadOptions };
13
- //# sourceMappingURL=plugin-command.utils.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"plugin-command.utils.d.ts","names":[],"sources":["../../../src/commands/plugin/plugin-command.utils.ts"],"mappings":";;;cAGa,qBAAA;AAAA,iBAqBG,8BAAA,CAAA;;;;;iBAQA,2BAAA,CAA4B,KAAA,YAAiB,MAAA,EAAQ,cAAA"}
@@ -1,37 +0,0 @@
1
- import { builtinProviderIds } from "@nextclaw/runtime";
2
- //#region src/commands/plugin/plugin-command.utils.ts
3
- const RESERVED_PROVIDER_IDS = builtinProviderIds();
4
- const RESERVED_TOOL_NAMES = [
5
- "read_file",
6
- "write_file",
7
- "edit_file",
8
- "list_dir",
9
- "exec",
10
- "web_search",
11
- "web_fetch",
12
- "message",
13
- "spawn",
14
- "sessions_list",
15
- "sessions_history",
16
- "memory_search",
17
- "memory_get",
18
- "subagents",
19
- "gateway",
20
- "cron"
21
- ];
22
- function buildReservedPluginLoadOptions() {
23
- return {
24
- reservedToolNames: [...RESERVED_TOOL_NAMES],
25
- reservedChannelIds: [],
26
- reservedProviderIds: RESERVED_PROVIDER_IDS
27
- };
28
- }
29
- function appendPluginCapabilityLines(lines, plugin) {
30
- if (plugin.toolNames.length > 0) lines.push(`Tools: ${plugin.toolNames.join(", ")}`);
31
- if (plugin.channelIds.length > 0) lines.push(`Channels: ${plugin.channelIds.join(", ")}`);
32
- if (plugin.providerIds.length > 0) lines.push(`Providers: ${plugin.providerIds.join(", ")}`);
33
- }
34
- //#endregion
35
- export { RESERVED_PROVIDER_IDS, appendPluginCapabilityLines, buildReservedPluginLoadOptions };
36
-
37
- //# sourceMappingURL=plugin-command.utils.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"plugin-command.utils.js","names":[],"sources":["../../../src/commands/plugin/plugin-command.utils.ts"],"sourcesContent":["import { builtinProviderIds } from \"@nextclaw/runtime\";\nimport type { PluginRegistry } from \"@nextclaw/openclaw-compat\";\n\nexport const RESERVED_PROVIDER_IDS = builtinProviderIds();\n\nconst RESERVED_TOOL_NAMES = [\n \"read_file\",\n \"write_file\",\n \"edit_file\",\n \"list_dir\",\n \"exec\",\n \"web_search\",\n \"web_fetch\",\n \"message\",\n \"spawn\",\n \"sessions_list\",\n \"sessions_history\",\n \"memory_search\",\n \"memory_get\",\n \"subagents\",\n \"gateway\",\n \"cron\",\n] as const;\n\nexport function buildReservedPluginLoadOptions() {\n return {\n reservedToolNames: [...RESERVED_TOOL_NAMES],\n reservedChannelIds: [] as string[],\n reservedProviderIds: RESERVED_PROVIDER_IDS,\n };\n}\n\nexport function appendPluginCapabilityLines(lines: string[], plugin: PluginRegistry[\"plugins\"][number]): void {\n if (plugin.toolNames.length > 0) {\n lines.push(`Tools: ${plugin.toolNames.join(\", \")}`);\n }\n if (plugin.channelIds.length > 0) {\n lines.push(`Channels: ${plugin.channelIds.join(\", \")}`);\n }\n if (plugin.providerIds.length > 0) {\n lines.push(`Providers: ${plugin.providerIds.join(\", \")}`);\n }\n}\n"],"mappings":";;AAGA,MAAa,wBAAwB,oBAAoB;AAEzD,MAAM,sBAAsB;CAC1B;CACA;CACA;CACA;CACA;CACA;CACA;CACA;CACA;CACA;CACA;CACA;CACA;CACA;CACA;CACA;CACD;AAED,SAAgB,iCAAiC;AAC/C,QAAO;EACL,mBAAmB,CAAC,GAAG,oBAAoB;EAC3C,oBAAoB,EAAE;EACtB,qBAAqB;EACtB;;AAGH,SAAgB,4BAA4B,OAAiB,QAAiD;AAC5G,KAAI,OAAO,UAAU,SAAS,EAC5B,OAAM,KAAK,UAAU,OAAO,UAAU,KAAK,KAAK,GAAG;AAErD,KAAI,OAAO,WAAW,SAAS,EAC7B,OAAM,KAAK,aAAa,OAAO,WAAW,KAAK,KAAK,GAAG;AAEzD,KAAI,OAAO,YAAY,SAAS,EAC9B,OAAM,KAAK,cAAc,OAAO,YAAY,KAAK,KAAK,GAAG"}
@@ -1,16 +0,0 @@
1
- import { PluginsInstallOptions, PluginsUninstallOptions } from "../../shared/types/cli.types.js";
2
-
3
- //#region src/commands/plugin/plugin-mutation-actions.utils.d.ts
4
- type PluginMutationResult = {
5
- message: string;
6
- };
7
- type PluginUninstallMutationResult = PluginMutationResult & {
8
- warnings: string[];
9
- };
10
- declare function enablePluginMutation(id: string): Promise<PluginMutationResult>;
11
- declare function disablePluginMutation(id: string): Promise<PluginMutationResult>;
12
- declare function uninstallPluginMutation(id: string, opts?: PluginsUninstallOptions): Promise<PluginUninstallMutationResult>;
13
- declare function installPluginMutation(pathOrSpec: string, opts?: PluginsInstallOptions): Promise<PluginMutationResult>;
14
- //#endregion
15
- export { PluginMutationResult, PluginUninstallMutationResult, disablePluginMutation, enablePluginMutation, installPluginMutation, uninstallPluginMutation };
16
- //# sourceMappingURL=plugin-mutation-actions.utils.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"plugin-mutation-actions.utils.d.ts","names":[],"sources":["../../../src/commands/plugin/plugin-mutation-actions.utils.ts"],"mappings":";;;KAgBY,oBAAA;EACV,OAAA;AAAA;AAAA,KAGU,6BAAA,GAAgC,oBAAA;EAC1C,QAAA;AAAA;AAAA,iBA+JoB,oBAAA,CAAqB,EAAA,WAAa,OAAA,CAAQ,oBAAA;AAAA,iBAS1C,qBAAA,CAAsB,EAAA,WAAa,OAAA,CAAQ,oBAAA;AAAA,iBAS3C,uBAAA,CACpB,EAAA,UACA,IAAA,GAAM,uBAAA,GACL,OAAA,CAAQ,6BAAA;AAAA,iBA4DW,qBAAA,CACpB,UAAA,UACA,IAAA,GAAM,qBAAA,GACL,OAAA,CAAQ,oBAAA"}
@@ -1,164 +0,0 @@
1
- import { buildReservedPluginLoadOptions } from "./plugin-command.utils.js";
2
- import { expandHome, getWorkspacePath, loadConfig, saveConfig } from "@nextclaw/core";
3
- import { addPluginLoadPath, buildPluginStatusReport, disablePluginInConfig, enablePluginInConfig, installPluginFromNpmSpec, installPluginFromPath, recordPluginInstall, uninstallPlugin } from "@nextclaw/openclaw-compat";
4
- import { existsSync } from "node:fs";
5
- import { resolve } from "node:path";
6
- //#region src/commands/plugin/plugin-mutation-actions.utils.ts
7
- const pluginInstallLogger = {
8
- info: (message) => console.log(message),
9
- warn: (message) => console.warn(message)
10
- };
11
- function resolveFileNpmSpecToLocalPath(raw) {
12
- const trimmed = raw.trim();
13
- if (!trimmed.toLowerCase().startsWith("file:")) return null;
14
- const rest = trimmed.slice(5);
15
- if (!rest) return {
16
- ok: false,
17
- error: "unsupported file: spec: missing path"
18
- };
19
- if (rest.startsWith("///")) return {
20
- ok: true,
21
- path: rest.slice(2)
22
- };
23
- if (rest.startsWith("//localhost/")) return {
24
- ok: true,
25
- path: rest.slice(11)
26
- };
27
- if (rest.startsWith("//")) return {
28
- ok: false,
29
- error: "unsupported file: URL host (expected \"file:<path>\" or \"file:///abs/path\")"
30
- };
31
- return {
32
- ok: true,
33
- path: rest
34
- };
35
- }
36
- function looksLikePath(raw) {
37
- return raw.startsWith(".") || raw.startsWith("~") || raw.startsWith("/") || raw.endsWith(".ts") || raw.endsWith(".js") || raw.endsWith(".mjs") || raw.endsWith(".cjs") || raw.endsWith(".tgz") || raw.endsWith(".tar.gz") || raw.endsWith(".tar") || raw.endsWith(".zip");
38
- }
39
- function isArchivePath(filePath) {
40
- const lower = filePath.toLowerCase();
41
- return lower.endsWith(".zip") || lower.endsWith(".tgz") || lower.endsWith(".tar.gz") || lower.endsWith(".tar");
42
- }
43
- function saveLinkedPluginInstall(config, params) {
44
- let next = addPluginLoadPath(config, params.resolvedPath);
45
- next = enablePluginInConfig(next, params.pluginId);
46
- next = recordPluginInstall(next, {
47
- pluginId: params.pluginId,
48
- source: "path",
49
- sourcePath: params.resolvedPath,
50
- installPath: params.resolvedPath,
51
- version: params.version ?? void 0
52
- });
53
- saveConfig(next);
54
- return { message: `Linked plugin path: ${params.resolvedPath}` };
55
- }
56
- function saveInstalledPluginResult(config, params) {
57
- let next = enablePluginInConfig(config, params.pluginId);
58
- next = recordPluginInstall(next, {
59
- pluginId: params.pluginId,
60
- source: params.source,
61
- sourcePath: params.sourcePath,
62
- spec: params.spec,
63
- installPath: params.installPath,
64
- version: params.version ?? void 0
65
- });
66
- saveConfig(next);
67
- return { message: `Installed plugin: ${params.pluginId}` };
68
- }
69
- async function installPluginFromLocalPath(config, resolvedPath, link) {
70
- if (link) {
71
- const probe = await installPluginFromPath({
72
- path: resolvedPath,
73
- dryRun: true
74
- });
75
- if (!probe.ok) throw new Error(probe.error);
76
- return saveLinkedPluginInstall(config, {
77
- resolvedPath,
78
- pluginId: probe.pluginId,
79
- version: probe.version
80
- });
81
- }
82
- const result = await installPluginFromPath({
83
- path: resolvedPath,
84
- logger: pluginInstallLogger
85
- });
86
- if (!result.ok) throw new Error(result.error);
87
- return saveInstalledPluginResult(config, {
88
- pluginId: result.pluginId,
89
- source: isArchivePath(resolvedPath) ? "archive" : "path",
90
- sourcePath: resolvedPath,
91
- installPath: result.targetDir,
92
- version: result.version
93
- });
94
- }
95
- async function installPluginFromRegistrySpec(config, spec) {
96
- const result = await installPluginFromNpmSpec({
97
- spec,
98
- logger: pluginInstallLogger
99
- });
100
- if (!result.ok) throw new Error(result.error);
101
- return saveInstalledPluginResult(config, {
102
- pluginId: result.pluginId,
103
- source: "npm",
104
- spec,
105
- installPath: result.targetDir,
106
- version: result.version
107
- });
108
- }
109
- async function enablePluginMutation(id) {
110
- saveConfig(enablePluginInConfig(loadConfig(), id));
111
- return { message: `Enabled plugin "${id}".` };
112
- }
113
- async function disablePluginMutation(id) {
114
- saveConfig(disablePluginInConfig(loadConfig(), id));
115
- return { message: `Disabled plugin "${id}".` };
116
- }
117
- async function uninstallPluginMutation(id, opts = {}) {
118
- const config = loadConfig();
119
- const report = buildPluginStatusReport({
120
- config,
121
- workspaceDir: getWorkspacePath(config.agents.defaults.workspace),
122
- ...buildReservedPluginLoadOptions()
123
- });
124
- const keepFiles = Boolean(opts.keepFiles || opts.keepConfig);
125
- const plugin = report.plugins.find((entry) => entry.id === id || entry.name === id);
126
- const pluginId = plugin?.id ?? id;
127
- const hasEntry = pluginId in (config.plugins.entries ?? {});
128
- const hasInstall = pluginId in (config.plugins.installs ?? {});
129
- if (!hasEntry && !hasInstall) {
130
- if (plugin) throw new Error(`Plugin "${pluginId}" is not managed by plugins config/install records and cannot be uninstalled.`);
131
- throw new Error(`Plugin not found: ${id}`);
132
- }
133
- const result = await uninstallPlugin({
134
- config,
135
- pluginId,
136
- deleteFiles: !keepFiles
137
- });
138
- if (!result.ok) throw new Error(result.error);
139
- saveConfig(result.config);
140
- const removed = [];
141
- if (result.actions.entry) removed.push("config entry");
142
- if (result.actions.install) removed.push("install record");
143
- if (result.actions.allowlist) removed.push("allowlist");
144
- if (result.actions.loadPath) removed.push("load path");
145
- if (result.actions.directory) removed.push("directory");
146
- return {
147
- message: `Uninstalled plugin "${pluginId}". Removed: ${removed.length > 0 ? removed.join(", ") : "nothing"}.`,
148
- warnings: result.warnings
149
- };
150
- }
151
- async function installPluginMutation(pathOrSpec, opts = {}) {
152
- const fileSpec = resolveFileNpmSpecToLocalPath(pathOrSpec);
153
- if (fileSpec && !fileSpec.ok) throw new Error(fileSpec.error);
154
- const resolved = resolve(expandHome(fileSpec && fileSpec.ok ? fileSpec.path : pathOrSpec));
155
- const config = loadConfig();
156
- if (existsSync(resolved)) return installPluginFromLocalPath(config, resolved, Boolean(opts.link));
157
- if (opts.link) throw new Error("`--link` requires a local path.");
158
- if (looksLikePath(pathOrSpec)) throw new Error(`Path not found: ${resolved}`);
159
- return installPluginFromRegistrySpec(config, pathOrSpec);
160
- }
161
- //#endregion
162
- export { disablePluginMutation, enablePluginMutation, installPluginMutation, uninstallPluginMutation };
163
-
164
- //# sourceMappingURL=plugin-mutation-actions.utils.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"plugin-mutation-actions.utils.js","names":[],"sources":["../../../src/commands/plugin/plugin-mutation-actions.utils.ts"],"sourcesContent":["import {\n addPluginLoadPath,\n buildPluginStatusReport,\n disablePluginInConfig,\n enablePluginInConfig,\n installPluginFromNpmSpec,\n installPluginFromPath,\n recordPluginInstall,\n uninstallPlugin,\n} from \"@nextclaw/openclaw-compat\";\nimport { existsSync } from \"node:fs\";\nimport { resolve } from \"node:path\";\nimport { expandHome, getWorkspacePath, loadConfig, saveConfig } from \"@nextclaw/core\";\nimport { buildReservedPluginLoadOptions } from \"./plugin-command.utils.js\";\nimport type { PluginsInstallOptions, PluginsUninstallOptions } from \"../../shared/types/cli.types.js\";\n\nexport type PluginMutationResult = {\n message: string;\n};\n\nexport type PluginUninstallMutationResult = PluginMutationResult & {\n warnings: string[];\n};\n\nconst pluginInstallLogger = {\n info: (message: string) => console.log(message),\n warn: (message: string) => console.warn(message)\n};\n\nfunction resolveFileNpmSpecToLocalPath(\n raw: string,\n): { ok: true; path: string } | { ok: false; error: string } | null {\n const trimmed = raw.trim();\n if (!trimmed.toLowerCase().startsWith(\"file:\")) {\n return null;\n }\n const rest = trimmed.slice(\"file:\".length);\n if (!rest) {\n return { ok: false, error: \"unsupported file: spec: missing path\" };\n }\n if (rest.startsWith(\"///\")) {\n return { ok: true, path: rest.slice(2) };\n }\n if (rest.startsWith(\"//localhost/\")) {\n return { ok: true, path: rest.slice(\"//localhost\".length) };\n }\n if (rest.startsWith(\"//\")) {\n return {\n ok: false,\n error: 'unsupported file: URL host (expected \"file:<path>\" or \"file:///abs/path\")'\n };\n }\n return { ok: true, path: rest };\n}\n\nfunction looksLikePath(raw: string): boolean {\n return (\n raw.startsWith(\".\") ||\n raw.startsWith(\"~\") ||\n raw.startsWith(\"/\") ||\n raw.endsWith(\".ts\") ||\n raw.endsWith(\".js\") ||\n raw.endsWith(\".mjs\") ||\n raw.endsWith(\".cjs\") ||\n raw.endsWith(\".tgz\") ||\n raw.endsWith(\".tar.gz\") ||\n raw.endsWith(\".tar\") ||\n raw.endsWith(\".zip\")\n );\n}\n\nfunction isArchivePath(filePath: string): boolean {\n const lower = filePath.toLowerCase();\n return lower.endsWith(\".zip\") || lower.endsWith(\".tgz\") || lower.endsWith(\".tar.gz\") || lower.endsWith(\".tar\");\n}\n\nfunction saveLinkedPluginInstall(\n config: ReturnType<typeof loadConfig>,\n params: {\n resolvedPath: string;\n pluginId: string;\n version?: string | null;\n },\n): PluginMutationResult {\n let next = addPluginLoadPath(config, params.resolvedPath);\n next = enablePluginInConfig(next, params.pluginId);\n next = recordPluginInstall(next, {\n pluginId: params.pluginId,\n source: \"path\",\n sourcePath: params.resolvedPath,\n installPath: params.resolvedPath,\n version: params.version ?? undefined\n });\n saveConfig(next);\n return {\n message: `Linked plugin path: ${params.resolvedPath}`,\n };\n}\n\nfunction saveInstalledPluginResult(\n config: ReturnType<typeof loadConfig>,\n params: {\n pluginId: string;\n installPath: string;\n version?: string | null;\n source: \"archive\" | \"path\" | \"npm\";\n sourcePath?: string;\n spec?: string;\n },\n): PluginMutationResult {\n let next = enablePluginInConfig(config, params.pluginId);\n next = recordPluginInstall(next, {\n pluginId: params.pluginId,\n source: params.source,\n sourcePath: params.sourcePath,\n spec: params.spec,\n installPath: params.installPath,\n version: params.version ?? undefined\n });\n saveConfig(next);\n return {\n message: `Installed plugin: ${params.pluginId}`,\n };\n}\n\nasync function installPluginFromLocalPath(\n config: ReturnType<typeof loadConfig>,\n resolvedPath: string,\n link: boolean,\n): Promise<PluginMutationResult> {\n if (link) {\n const probe = await installPluginFromPath({ path: resolvedPath, dryRun: true });\n if (!probe.ok) {\n throw new Error(probe.error);\n }\n return saveLinkedPluginInstall(config, {\n resolvedPath,\n pluginId: probe.pluginId,\n version: probe.version\n });\n }\n\n const result = await installPluginFromPath({\n path: resolvedPath,\n logger: pluginInstallLogger\n });\n if (!result.ok) {\n throw new Error(result.error);\n }\n\n return saveInstalledPluginResult(config, {\n pluginId: result.pluginId,\n source: isArchivePath(resolvedPath) ? \"archive\" : \"path\",\n sourcePath: resolvedPath,\n installPath: result.targetDir,\n version: result.version\n });\n}\n\nasync function installPluginFromRegistrySpec(\n config: ReturnType<typeof loadConfig>,\n spec: string,\n): Promise<PluginMutationResult> {\n const result = await installPluginFromNpmSpec({\n spec,\n logger: pluginInstallLogger\n });\n if (!result.ok) {\n throw new Error(result.error);\n }\n\n return saveInstalledPluginResult(config, {\n pluginId: result.pluginId,\n source: \"npm\",\n spec,\n installPath: result.targetDir,\n version: result.version\n });\n}\n\nexport async function enablePluginMutation(id: string): Promise<PluginMutationResult> {\n const config = loadConfig();\n const next = enablePluginInConfig(config, id);\n saveConfig(next);\n return {\n message: `Enabled plugin \"${id}\".`,\n };\n}\n\nexport async function disablePluginMutation(id: string): Promise<PluginMutationResult> {\n const config = loadConfig();\n const next = disablePluginInConfig(config, id);\n saveConfig(next);\n return {\n message: `Disabled plugin \"${id}\".`,\n };\n}\n\nexport async function uninstallPluginMutation(\n id: string,\n opts: PluginsUninstallOptions = {},\n): Promise<PluginUninstallMutationResult> {\n const config = loadConfig();\n const workspaceDir = getWorkspacePath(config.agents.defaults.workspace);\n const report = buildPluginStatusReport({\n config,\n workspaceDir,\n ...buildReservedPluginLoadOptions()\n });\n\n const keepFiles = Boolean(opts.keepFiles || opts.keepConfig);\n const plugin = report.plugins.find((entry) => entry.id === id || entry.name === id);\n const pluginId = plugin?.id ?? id;\n\n const hasEntry = pluginId in (config.plugins.entries ?? {});\n const hasInstall = pluginId in (config.plugins.installs ?? {});\n\n if (!hasEntry && !hasInstall) {\n if (plugin) {\n throw new Error(\n `Plugin \"${pluginId}\" is not managed by plugins config/install records and cannot be uninstalled.`,\n );\n }\n throw new Error(`Plugin not found: ${id}`);\n }\n\n const result = await uninstallPlugin({\n config,\n pluginId,\n deleteFiles: !keepFiles\n });\n\n if (!result.ok) {\n throw new Error(result.error);\n }\n\n saveConfig(result.config);\n\n const removed: string[] = [];\n if (result.actions.entry) {\n removed.push(\"config entry\");\n }\n if (result.actions.install) {\n removed.push(\"install record\");\n }\n if (result.actions.allowlist) {\n removed.push(\"allowlist\");\n }\n if (result.actions.loadPath) {\n removed.push(\"load path\");\n }\n if (result.actions.directory) {\n removed.push(\"directory\");\n }\n\n return {\n message: `Uninstalled plugin \"${pluginId}\". Removed: ${removed.length > 0 ? removed.join(\", \") : \"nothing\"}.`,\n warnings: result.warnings,\n };\n}\n\nexport async function installPluginMutation(\n pathOrSpec: string,\n opts: PluginsInstallOptions = {},\n): Promise<PluginMutationResult> {\n const fileSpec = resolveFileNpmSpecToLocalPath(pathOrSpec);\n if (fileSpec && !fileSpec.ok) {\n throw new Error(fileSpec.error);\n }\n const normalized = fileSpec && fileSpec.ok ? fileSpec.path : pathOrSpec;\n const resolved = resolve(expandHome(normalized));\n const config = loadConfig();\n\n if (existsSync(resolved)) {\n return installPluginFromLocalPath(config, resolved, Boolean(opts.link));\n }\n\n if (opts.link) {\n throw new Error(\"`--link` requires a local path.\");\n }\n\n if (looksLikePath(pathOrSpec)) {\n throw new Error(`Path not found: ${resolved}`);\n }\n\n return installPluginFromRegistrySpec(config, pathOrSpec);\n}\n"],"mappings":"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"}
@@ -1,32 +0,0 @@
1
- import { NextclawGatewayRuntime } from "../nextclaw-gateway-runtime.service.js";
2
- import { Config } from "@nextclaw/core";
3
- import * as _$_nextclaw_openclaw_compat0 from "@nextclaw/openclaw-compat";
4
- import { PluginChannelBinding } from "@nextclaw/openclaw-compat";
5
-
6
- //#region src/shared/services/gateway/managers/gateway-plugin.manager.d.ts
7
- declare class GatewayPluginManager {
8
- private readonly gateway;
9
- private gatewayHandles;
10
- constructor(gateway: NextclawGatewayRuntime);
11
- getChannelBindings: () => PluginChannelBinding[];
12
- getUiMetadata: () => _$_nextclaw_openclaw_compat0.PluginUiMetadata[];
13
- load: () => Promise<void>;
14
- reloadForConfigChange: (params: {
15
- config: Config;
16
- changedPaths: string[];
17
- }) => Promise<{
18
- restartChannels: boolean;
19
- }>;
20
- reloadForDevHotReload: (changedPaths: string[]) => Promise<void>;
21
- startGateways: () => Promise<void>;
22
- publishConfigChanges: () => void;
23
- restartGateways: () => Promise<void>;
24
- stopGateways: () => Promise<void>;
25
- private startChannelGateways;
26
- private resolveGatewayAccountIds;
27
- private reportGatewayStartFailure;
28
- private isChannelEnabled;
29
- }
30
- //#endregion
31
- export { GatewayPluginManager };
32
- //# sourceMappingURL=gateway-plugin.manager.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"gateway-plugin.manager.d.ts","names":[],"sources":["../../../../../src/shared/services/gateway/managers/gateway-plugin.manager.ts"],"mappings":";;;;;;cAea,oBAAA;EAAA,iBAGkB,OAAA;EAAA,QAFrB,cAAA;cAEqB,OAAA,EAAS,sBAAA;EAEtC,kBAAA,QAAyB,oBAAA;EAEzB,aAAA,QAF6C,4BAAA,CAEhC,gBAAA;EAEb,IAAA,QAAiB,OAAA;EAmCjB,qBAAA,GAA+B,MAAA;IAC7B,MAAA,EAAQ,MAAA;IACR,YAAA;EAAA,MACE,OAAA;IAAU,eAAA;EAAA;EAad,qBAAA,GAA+B,YAAA,eAAyB,OAAA;EAWxD,aAAA,QAA0B,OAAA;EAuB1B,oBAAA;EAWA,eAAA,QAA4B,OAAA;EAK5B,YAAA,QAAyB,OAAA;EAAA,QAYjB,oBAAA;EAAA,QAgEA,wBAAA;EAAA,QAcA,yBAAA;EAAA,QA0BA,gBAAA;AAAA"}
@@ -1,176 +0,0 @@
1
- import { logPluginDiagnostics } from "../../../../commands/plugin/index.js";
2
- import { logPluginGatewayDiagnostics, pluginGatewayLogger } from "../service-startup-support.service.js";
3
- import { toPluginConfigView } from "@nextclaw/openclaw-compat";
4
- import { eventKeys } from "@nextclaw/shared";
5
- //#region src/shared/services/gateway/managers/gateway-plugin.manager.ts
6
- var GatewayPluginManager = class {
7
- gatewayHandles = [];
8
- constructor(gateway) {
9
- this.gateway = gateway;
10
- }
11
- getChannelBindings = () => this.gateway.kernel.extensions.getChannelBindings();
12
- getUiMetadata = () => this.gateway.kernel.extensions.getUiMetadata();
13
- load = async () => {
14
- const config = this.gateway.configManager.loadConfig();
15
- let totalPluginCount = 0;
16
- this.gateway.bootstrapStatus.markChannelsPending();
17
- try {
18
- const result = await this.gateway.kernel.extensions.load({
19
- config,
20
- onLoadStart: ({ totalPluginCount: nextTotalPluginCount }) => {
21
- totalPluginCount = nextTotalPluginCount;
22
- this.gateway.bootstrapStatus.markPluginHydrationRunning({ totalPluginCount: nextTotalPluginCount });
23
- },
24
- onPluginProcessed: ({ loadedPluginCount: nextCount }) => {
25
- this.gateway.bootstrapStatus.markPluginHydrationProgress({
26
- loadedPluginCount: nextCount,
27
- totalPluginCount
28
- });
29
- }
30
- });
31
- logPluginDiagnostics({ diagnostics: result.diagnostics });
32
- if (result.shouldRestartChannels) await this.gateway.configManager.rebuildChannels(config, { start: false });
33
- this.publishConfigChanges();
34
- this.gateway.bootstrapStatus.markPluginHydrationReady({
35
- loadedPluginCount: result.loadedPluginCount,
36
- totalPluginCount
37
- });
38
- } catch (error) {
39
- this.gateway.bootstrapStatus.markPluginHydrationError(error instanceof Error ? error.message : String(error));
40
- throw error;
41
- }
42
- };
43
- reloadForConfigChange = async (params) => {
44
- const result = await this.gateway.kernel.extensions.reloadForConfigChange({
45
- config: params.config,
46
- changedPaths: params.changedPaths
47
- });
48
- logPluginDiagnostics({ diagnostics: result.diagnostics });
49
- if (result.shouldRestartChannels) await this.restartGateways();
50
- this.publishConfigChanges();
51
- return { restartChannels: result.shouldRestartChannels };
52
- };
53
- reloadForDevHotReload = async (changedPaths) => {
54
- const config = this.gateway.configManager.loadConfig();
55
- if ((await this.reloadForConfigChange({
56
- config,
57
- changedPaths
58
- })).restartChannels) await this.gateway.configManager.rebuildChannels(config, { start: true });
59
- };
60
- startGateways = async () => {
61
- const config = this.gateway.configManager.loadConfig();
62
- const diagnostics = [];
63
- const handles = [];
64
- const channelBindings = this.gateway.kernel.extensions.getChannelBindings();
65
- const configView = toPluginConfigView(config, channelBindings);
66
- for (const binding of channelBindings) {
67
- if (!this.isChannelEnabled(binding.channelId, configView)) continue;
68
- await this.startChannelGateways({
69
- binding,
70
- configView,
71
- diagnostics,
72
- handles
73
- });
74
- }
75
- this.gatewayHandles = handles;
76
- logPluginGatewayDiagnostics(diagnostics);
77
- };
78
- publishConfigChanges = () => {
79
- this.gateway.appEventBus.emit(eventKeys.configUpdated, { path: "channels" }, {
80
- emittedAt: (/* @__PURE__ */ new Date()).toISOString(),
81
- source: "backend"
82
- });
83
- this.gateway.appEventBus.emit(eventKeys.configUpdated, { path: "plugins" }, {
84
- emittedAt: (/* @__PURE__ */ new Date()).toISOString(),
85
- source: "backend"
86
- });
87
- };
88
- restartGateways = async () => {
89
- await this.stopGateways();
90
- await this.startGateways();
91
- };
92
- stopGateways = async () => {
93
- for (const handle of this.gatewayHandles) try {
94
- handle.abort?.();
95
- await handle.stop?.();
96
- } catch {}
97
- this.gatewayHandles = [];
98
- };
99
- startChannelGateways = async (params) => {
100
- const { binding, configView, diagnostics, handles } = params;
101
- const gateway = binding.channel.gateway;
102
- if (!gateway?.startAccount) return;
103
- const accountIds = this.resolveGatewayAccountIds(binding, configView);
104
- for (const accountId of accountIds) {
105
- const abortController = new AbortController();
106
- let stopGateway;
107
- const startTask = Promise.resolve().then(async () => await gateway.startAccount?.({
108
- accountId,
109
- channelId: binding.channelId,
110
- cfg: configView,
111
- abortSignal: abortController.signal,
112
- runtime: {
113
- log: pluginGatewayLogger.info,
114
- info: pluginGatewayLogger.info,
115
- warn: pluginGatewayLogger.warn,
116
- error: pluginGatewayLogger.error,
117
- debug: pluginGatewayLogger.debug
118
- },
119
- setStatus: () => void 0,
120
- log: pluginGatewayLogger
121
- })).then((started) => {
122
- if (started && typeof started === "object" && "stop" in started && typeof started.stop === "function") stopGateway = started.stop.bind(started);
123
- }).catch((error) => {
124
- if (abortController.signal.aborted) return;
125
- this.reportGatewayStartFailure({
126
- accountId,
127
- binding,
128
- diagnostics,
129
- error
130
- });
131
- });
132
- handles.push({
133
- pluginId: binding.pluginId,
134
- channelId: binding.channelId,
135
- accountId,
136
- abort: () => abortController.abort(),
137
- stop: async () => {
138
- abortController.abort();
139
- await startTask;
140
- await stopGateway?.();
141
- }
142
- });
143
- }
144
- };
145
- resolveGatewayAccountIds = (binding, configView) => {
146
- const accountIdsRaw = binding.channel.config?.listAccountIds?.(configView) ?? [binding.channel.config?.defaultAccountId?.(configView) ?? "default"];
147
- const accountIds = Array.from(new Set(accountIdsRaw.map((id) => typeof id === "string" ? id.trim() : "").filter(Boolean)));
148
- return accountIds.length > 0 ? accountIds : ["default"];
149
- };
150
- reportGatewayStartFailure = (params) => {
151
- const { accountId, binding, diagnostics, error } = params;
152
- const raw = String(error);
153
- const lower = raw.toLowerCase();
154
- const level = lower.includes("required") || lower.includes("not configured") || lower.includes("missing") ? "warn" : "error";
155
- const message = `failed to start channel gateway for ${binding.channelId}/${accountId}: ${raw}`;
156
- diagnostics.push({
157
- level,
158
- pluginId: binding.pluginId,
159
- message
160
- });
161
- if (level === "error") {
162
- pluginGatewayLogger.error(message);
163
- return;
164
- }
165
- pluginGatewayLogger.warn(message);
166
- };
167
- isChannelEnabled = (channelId, configView) => {
168
- const channelConfig = (configView.channels && typeof configView.channels === "object" && !Array.isArray(configView.channels) ? configView.channels : {})[channelId];
169
- if (!channelConfig || typeof channelConfig !== "object" || Array.isArray(channelConfig)) return false;
170
- return channelConfig.enabled === true;
171
- };
172
- };
173
- //#endregion
174
- export { GatewayPluginManager };
175
-
176
- //# sourceMappingURL=gateway-plugin.manager.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"gateway-plugin.manager.js","names":[],"sources":["../../../../../src/shared/services/gateway/managers/gateway-plugin.manager.ts"],"sourcesContent":["import type { Config } from \"@nextclaw/core\";\nimport { eventKeys } from \"@nextclaw/shared\";\nimport {\n toPluginConfigView,\n type PluginChannelBinding,\n type PluginChannelGatewayHandle,\n type PluginDiagnostic,\n} from \"@nextclaw/openclaw-compat\";\nimport { logPluginDiagnostics } from \"@nextclaw-service/commands/plugin/index.js\";\nimport {\n logPluginGatewayDiagnostics,\n pluginGatewayLogger,\n} from \"@nextclaw-service/shared/services/gateway/service-startup-support.service.js\";\nimport type { NextclawGatewayRuntime } from \"@nextclaw-service/shared/services/gateway/nextclaw-gateway-runtime.service.js\";\n\nexport class GatewayPluginManager {\n private gatewayHandles: PluginChannelGatewayHandle[] = [];\n\n constructor(private readonly gateway: NextclawGatewayRuntime) {}\n\n getChannelBindings = (): PluginChannelBinding[] => this.gateway.kernel.extensions.getChannelBindings();\n\n getUiMetadata = () => this.gateway.kernel.extensions.getUiMetadata();\n\n load = async (): Promise<void> => {\n const config = this.gateway.configManager.loadConfig();\n let totalPluginCount = 0;\n this.gateway.bootstrapStatus.markChannelsPending();\n\n try {\n const result = await this.gateway.kernel.extensions.load({\n config,\n onLoadStart: ({ totalPluginCount: nextTotalPluginCount }) => {\n totalPluginCount = nextTotalPluginCount;\n this.gateway.bootstrapStatus.markPluginHydrationRunning({ totalPluginCount: nextTotalPluginCount });\n },\n onPluginProcessed: ({ loadedPluginCount: nextCount }) => {\n this.gateway.bootstrapStatus.markPluginHydrationProgress({\n loadedPluginCount: nextCount,\n totalPluginCount,\n });\n }\n });\n logPluginDiagnostics({ diagnostics: result.diagnostics });\n\n if (result.shouldRestartChannels) {\n await this.gateway.configManager.rebuildChannels(config, { start: false });\n }\n this.publishConfigChanges();\n this.gateway.bootstrapStatus.markPluginHydrationReady({\n loadedPluginCount: result.loadedPluginCount,\n totalPluginCount,\n });\n } catch (error) {\n this.gateway.bootstrapStatus.markPluginHydrationError(error instanceof Error ? error.message : String(error));\n throw error;\n }\n };\n\n reloadForConfigChange = async (params: {\n config: Config;\n changedPaths: string[];\n }): Promise<{ restartChannels: boolean }> => {\n const result = await this.gateway.kernel.extensions.reloadForConfigChange({\n config: params.config,\n changedPaths: params.changedPaths,\n });\n logPluginDiagnostics({ diagnostics: result.diagnostics });\n if (result.shouldRestartChannels) {\n await this.restartGateways();\n }\n this.publishConfigChanges();\n return { restartChannels: result.shouldRestartChannels };\n };\n\n reloadForDevHotReload = async (changedPaths: string[]): Promise<void> => {\n const config = this.gateway.configManager.loadConfig();\n const result = await this.reloadForConfigChange({\n config,\n changedPaths,\n });\n if (result.restartChannels) {\n await this.gateway.configManager.rebuildChannels(config, { start: true });\n }\n };\n\n startGateways = async (): Promise<void> => {\n const config = this.gateway.configManager.loadConfig();\n const diagnostics: PluginDiagnostic[] = [];\n const handles: PluginChannelGatewayHandle[] = [];\n const channelBindings = this.gateway.kernel.extensions.getChannelBindings();\n const configView = toPluginConfigView(config, channelBindings);\n\n for (const binding of channelBindings) {\n if (!this.isChannelEnabled(binding.channelId, configView)) {\n continue;\n }\n await this.startChannelGateways({\n binding,\n configView,\n diagnostics,\n handles,\n });\n }\n\n this.gatewayHandles = handles;\n logPluginGatewayDiagnostics(diagnostics);\n };\n\n publishConfigChanges = (): void => {\n this.gateway.appEventBus.emit(eventKeys.configUpdated, { path: \"channels\" }, {\n emittedAt: new Date().toISOString(),\n source: \"backend\",\n });\n this.gateway.appEventBus.emit(eventKeys.configUpdated, { path: \"plugins\" }, {\n emittedAt: new Date().toISOString(),\n source: \"backend\",\n });\n };\n\n restartGateways = async (): Promise<void> => {\n await this.stopGateways();\n await this.startGateways();\n };\n\n stopGateways = async (): Promise<void> => {\n for (const handle of this.gatewayHandles) {\n try {\n handle.abort?.();\n await handle.stop?.();\n } catch {\n // Ignore stop failures during shutdown.\n }\n }\n this.gatewayHandles = [];\n };\n\n private startChannelGateways = async (params: {\n binding: PluginChannelBinding;\n configView: Record<string, unknown>;\n diagnostics: PluginDiagnostic[];\n handles: PluginChannelGatewayHandle[];\n }): Promise<void> => {\n const { binding, configView, diagnostics, handles } = params;\n const gateway = binding.channel.gateway;\n if (!gateway?.startAccount) {\n return;\n }\n const accountIds = this.resolveGatewayAccountIds(binding, configView);\n for (const accountId of accountIds) {\n const abortController = new AbortController();\n let stopGateway: (() => void | Promise<void>) | undefined;\n const startTask = Promise.resolve()\n .then(async () =>\n await gateway.startAccount?.({\n accountId,\n channelId: binding.channelId,\n cfg: configView as Config,\n abortSignal: abortController.signal,\n runtime: {\n log: pluginGatewayLogger.info,\n info: pluginGatewayLogger.info,\n warn: pluginGatewayLogger.warn,\n error: pluginGatewayLogger.error,\n debug: pluginGatewayLogger.debug,\n },\n setStatus: () => undefined,\n log: pluginGatewayLogger,\n })\n )\n .then((started) => {\n if (started && typeof started === \"object\" && \"stop\" in started && typeof started.stop === \"function\") {\n stopGateway = started.stop.bind(started);\n }\n })\n .catch((error) => {\n if (abortController.signal.aborted) {\n return;\n }\n this.reportGatewayStartFailure({\n accountId,\n binding,\n diagnostics,\n error,\n });\n });\n\n handles.push({\n pluginId: binding.pluginId,\n channelId: binding.channelId,\n accountId,\n abort: () => abortController.abort(),\n stop: async () => {\n abortController.abort();\n await startTask;\n await stopGateway?.();\n },\n });\n }\n };\n\n private resolveGatewayAccountIds = (\n binding: PluginChannelBinding,\n configView: Record<string, unknown>,\n ): string[] => {\n const accountIdsRaw =\n binding.channel.config?.listAccountIds?.(configView) ?? [\n binding.channel.config?.defaultAccountId?.(configView) ?? \"default\",\n ];\n const accountIds = Array.from(\n new Set(accountIdsRaw.map((id) => (typeof id === \"string\" ? id.trim() : \"\")).filter(Boolean)),\n );\n return accountIds.length > 0 ? accountIds : [\"default\"];\n };\n\n private reportGatewayStartFailure = (params: {\n accountId: string;\n binding: PluginChannelBinding;\n diagnostics: PluginDiagnostic[];\n error: unknown;\n }): void => {\n const { accountId, binding, diagnostics, error } = params;\n const raw = String(error);\n const lower = raw.toLowerCase();\n const level =\n lower.includes(\"required\") || lower.includes(\"not configured\") || lower.includes(\"missing\")\n ? \"warn\"\n : \"error\";\n const message = `failed to start channel gateway for ${binding.channelId}/${accountId}: ${raw}`;\n diagnostics.push({\n level,\n pluginId: binding.pluginId,\n message,\n });\n if (level === \"error\") {\n pluginGatewayLogger.error(message);\n return;\n }\n pluginGatewayLogger.warn(message);\n };\n\n private isChannelEnabled = (\n channelId: string,\n configView: Record<string, unknown>,\n ): boolean => {\n const channels =\n configView.channels && typeof configView.channels === \"object\" && !Array.isArray(configView.channels)\n ? (configView.channels as Record<string, unknown>)\n : {};\n const channelConfig = channels[channelId];\n if (!channelConfig || typeof channelConfig !== \"object\" || Array.isArray(channelConfig)) {\n return false;\n }\n return (channelConfig as { enabled?: unknown }).enabled === true;\n };\n\n}\n"],"mappings":"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"}
@@ -1,25 +0,0 @@
1
- import { ServiceFileWatcherRegistry } from "../../gateway/service-startup-support.service.js";
2
-
3
- //#region src/shared/services/plugin/utils/plugin-dev-hot-reload.utils.d.ts
4
- declare const DEV_PLUGIN_HOT_RELOAD_TARGETS_ENV = "NEXTCLAW_DEV_PLUGIN_HOT_RELOAD_TARGETS";
5
- type DevPluginHotReloadTarget = {
6
- pluginId: string;
7
- pluginPath: string;
8
- watchPaths: string[];
9
- };
10
- declare function resolveDevPluginHotReloadTargets(rawValue?: string | undefined): DevPluginHotReloadTarget[];
11
- declare function startDevPluginHotReloadWatcher(params: {
12
- watcherRegistry: ServiceFileWatcherRegistry;
13
- reloadPlugins: (pluginIds: string[]) => Promise<void>;
14
- targets?: DevPluginHotReloadTarget[];
15
- }): void;
16
- declare function wrapStartChannelsWithDevPluginHotReload(params: {
17
- startChannels: () => Promise<void>;
18
- watcherRegistry: ServiceFileWatcherRegistry;
19
- isRuntimeActive: () => boolean;
20
- reloadPlugins: (pluginIds: string[]) => Promise<void>;
21
- startupSettleMs: number;
22
- }): () => Promise<void>;
23
- //#endregion
24
- export { DEV_PLUGIN_HOT_RELOAD_TARGETS_ENV, DevPluginHotReloadTarget, resolveDevPluginHotReloadTargets, startDevPluginHotReloadWatcher, wrapStartChannelsWithDevPluginHotReload };
25
- //# sourceMappingURL=plugin-dev-hot-reload.utils.d.ts.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"plugin-dev-hot-reload.utils.d.ts","names":[],"sources":["../../../../../src/shared/services/plugin/utils/plugin-dev-hot-reload.utils.ts"],"mappings":";;;cAIa,iCAAA;AAAA,KAED,wBAAA;EACV,QAAA;EACA,UAAA;EACA,UAAA;AAAA;AAAA,iBAiCc,gCAAA,CACd,QAAA,wBACC,wBAAA;AAAA,iBA+Ca,8BAAA,CAA+B,MAAA;EAC7C,eAAA,EAAiB,0BAAA;EACjB,aAAA,GAAgB,SAAA,eAAwB,OAAA;EACxC,OAAA,GAAU,wBAAA;AAAA;AAAA,iBA+EI,uCAAA,CAAwC,MAAA;EACtD,aAAA,QAAqB,OAAA;EACrB,eAAA,EAAiB,0BAAA;EACjB,eAAA;EACA,aAAA,GAAgB,SAAA,eAAwB,OAAA;EACxC,eAAA;AAAA,UACQ,OAAA"}