





















@@ -0,0 +1,140 @@
1+import { beforeEach, describe, expect, it, vi } from "vitest";
2+import { createWizardPrompter } from "../../test/helpers/wizard-prompter.js";
3+import { createNonExitingRuntime } from "../runtime.js";
4+import type { WizardPrompter } from "./prompts.js";
5+6+const ensureOnboardingPluginInstalled = vi.hoisted(() =>
7+vi.fn(async ({ cfg }: { cfg: Record<string, unknown> }) => ({
8+ cfg,
9+installed: true,
10+status: "installed",
11+})),
12+);
13+vi.mock("../commands/onboarding-plugin-install.js", () => ({
14+ ensureOnboardingPluginInstalled,
15+}));
16+17+import {
18+__testing,
19+resolveOfficialPluginOnboardingInstallEntries,
20+setupOfficialPluginInstalls,
21+} from "./setup.official-plugins.js";
22+23+describe("resolveOfficialPluginOnboardingInstallEntries", () => {
24+it("lists optional generic official plugins without channel, provider, or search-owned entries", () => {
25+const entries = resolveOfficialPluginOnboardingInstallEntries({ config: {} });
26+const pluginIds = entries.map((entry) => entry.pluginId);
27+28+expect(pluginIds).toContain("diagnostics-otel");
29+expect(pluginIds).toContain("diagnostics-prometheus");
30+expect(pluginIds).toContain("acpx");
31+expect(pluginIds).not.toContain("brave");
32+expect(pluginIds).not.toContain("codex");
33+expect(pluginIds).not.toContain("discord");
34+});
35+36+it("hides already configured official plugins", () => {
37+const entries = resolveOfficialPluginOnboardingInstallEntries({
38+config: {
39+plugins: {
40+entries: {
41+acpx: { enabled: true },
42+},
43+installs: {
44+"diagnostics-otel": {
45+source: "npm",
46+spec: "@openclaw/diagnostics-otel",
47+installPath: "/tmp/diagnostics-otel",
48+},
49+},
50+},
51+},
52+});
53+const pluginIds = entries.map((entry) => entry.pluginId);
54+55+expect(pluginIds).not.toContain("acpx");
56+expect(pluginIds).not.toContain("diagnostics-otel");
57+expect(pluginIds).toContain("diagnostics-prometheus");
58+});
59+});
60+61+describe("formatInstallHint", () => {
62+it("describes dual-source npm-default installs as npm first", () => {
63+expect(
64+__testing.formatInstallHint({
65+clawhubSpec: "clawhub:@openclaw/diagnostics-otel",
66+npmSpec: "@openclaw/diagnostics-otel",
67+defaultChoice: "npm",
68+}),
69+).toBe("npm, with ClawHub fallback");
70+});
71+72+it("keeps dual-source clawhub-default installs ClawHub first", () => {
73+expect(
74+__testing.formatInstallHint({
75+clawhubSpec: "clawhub:@openclaw/diagnostics-otel",
76+npmSpec: "@openclaw/diagnostics-otel",
77+defaultChoice: "clawhub",
78+}),
79+).toBe("ClawHub, with npm fallback");
80+});
81+});
82+83+describe("setupOfficialPluginInstalls", () => {
84+beforeEach(() => {
85+vi.clearAllMocks();
86+ensureOnboardingPluginInstalled.mockImplementation(async ({ cfg }) => ({
87+ cfg,
88+installed: true,
89+status: "installed",
90+}));
91+});
92+93+it("installs selected optional official plugins through the shared onboarding installer", async () => {
94+const multiselect = vi.fn(async () => ["diagnostics-otel"]);
95+const prompter = createWizardPrompter({
96+multiselect: multiselect as WizardPrompter["multiselect"],
97+});
98+99+await setupOfficialPluginInstalls({
100+config: {},
101+ prompter,
102+runtime: createNonExitingRuntime(),
103+workspaceDir: "/tmp/workspace",
104+});
105+106+expect(multiselect).toHaveBeenCalledWith(
107+expect.objectContaining({
108+message: "Install optional plugins",
109+}),
110+);
111+expect(ensureOnboardingPluginInstalled).toHaveBeenCalledWith(
112+expect.objectContaining({
113+entry: expect.objectContaining({
114+pluginId: "diagnostics-otel",
115+install: expect.objectContaining({
116+clawhubSpec: "clawhub:@openclaw/diagnostics-otel",
117+npmSpec: "@openclaw/diagnostics-otel",
118+defaultChoice: "npm",
119+}),
120+}),
121+promptInstall: false,
122+workspaceDir: "/tmp/workspace",
123+}),
124+);
125+});
126+127+it("does not install when the user skips optional plugins", async () => {
128+const prompter = createWizardPrompter({
129+multiselect: vi.fn(async () => ["__skip__"]) as WizardPrompter["multiselect"],
130+});
131+132+await setupOfficialPluginInstalls({
133+config: {},
134+ prompter,
135+runtime: createNonExitingRuntime(),
136+});
137+138+expect(ensureOnboardingPluginInstalled).not.toHaveBeenCalled();
139+});
140+});
此内容由惯性聚合(RSS阅读器)自动聚合整理,仅供阅读参考。 原文来自 — 版权归原作者所有。