feat(FN-3763): add cli printing press wizard plugin
Implements a new `fusion-plugin-cli-printing-press` plugin with a multi-step wizard UI for authoring CLI commands, including draft storage, route registration, and validation — plus integration wiring in the dashboard's plugin view registry. Includes TypeScript build and ESM import fixes for the plu Fusion-Task-Id: FN-3763
This commit is contained in:
@@ -35,6 +35,12 @@ describe("pluginViewRegistry", () => {
|
||||
expect(getPluginViewComponent("plugin-b", "missing")).toBeNull();
|
||||
});
|
||||
|
||||
it("resolves cli printing press wizard entries", () => {
|
||||
const View = lazy(async () => ({ default: () => <div>Wizard</div> }));
|
||||
registerPluginView("fusion-plugin-cli-printing-press", "wizard", View);
|
||||
expect(getPluginViewComponent("fusion-plugin-cli-printing-press", "wizard")).toBe(View);
|
||||
});
|
||||
|
||||
it("keeps all registered plugin views discoverable by key iteration", () => {
|
||||
const ViewA = lazy(async () => ({ default: () => <div>A</div> }));
|
||||
const ViewB = lazy(async () => ({ default: () => <div>B</div> }));
|
||||
|
||||
@@ -8,6 +8,7 @@ import {
|
||||
|
||||
const MockDependencyGraphDashboardView = () => createElement("div", { "data-testid": "dep-graph-view" });
|
||||
const MockRoadmapDashboardView = () => createElement("div", { "data-testid": "roadmap-view" });
|
||||
const MockCliPrintingPressWizardView = () => createElement("div", { "data-testid": "cli-printing-press-view" });
|
||||
|
||||
vi.mock("@fusion-plugin-examples/dependency-graph/dashboard-view", () => ({
|
||||
DependencyGraphDashboardView: (...args: unknown[]) => MockDependencyGraphDashboardView(...args),
|
||||
@@ -17,17 +18,22 @@ vi.mock("@fusion-plugin-examples/roadmap/dashboard-view", () => ({
|
||||
RoadmapDashboardView: (...args: unknown[]) => MockRoadmapDashboardView(...args),
|
||||
}));
|
||||
|
||||
vi.mock("@fusion-plugin-examples/cli-printing-press/dashboard-view", () => ({
|
||||
CliPrintingPressWizardView: (...args: unknown[]) => MockCliPrintingPressWizardView(...args),
|
||||
}));
|
||||
|
||||
describe("registerBundledPluginViews", () => {
|
||||
beforeEach(() => {
|
||||
__test_clearPluginViewRegistry();
|
||||
__test_resetBundledPluginViewRegistration();
|
||||
});
|
||||
|
||||
it("registers dependency graph and roadmap bundled views", () => {
|
||||
it("registers dependency graph, roadmap, and cli printing press bundled views", () => {
|
||||
registerBundledPluginViews();
|
||||
|
||||
expect(getPluginViewComponent("fusion-plugin-dependency-graph", "graph")).toBeTruthy();
|
||||
expect(getPluginViewComponent("roadmap-planner", "roadmaps")).toBeTruthy();
|
||||
expect(getPluginViewComponent("fusion-plugin-cli-printing-press", "wizard")).toBeTruthy();
|
||||
});
|
||||
|
||||
it("is idempotent when called more than once", () => {
|
||||
@@ -45,6 +51,7 @@ describe("registerBundledPluginViews", () => {
|
||||
|
||||
expect(isPluginViewRegistered("fusion-plugin-dependency-graph", "graph")).toBe(true);
|
||||
expect(isPluginViewRegistered("roadmap-planner", "roadmaps")).toBe(true);
|
||||
expect(isPluginViewRegistered("fusion-plugin-cli-printing-press", "wizard")).toBe(true);
|
||||
// Unknown plugin/view should not be registered
|
||||
expect(isPluginViewRegistered("unknown-plugin", "unknown")).toBe(false);
|
||||
});
|
||||
|
||||
@@ -37,6 +37,18 @@ async function loadRoadmapView(): Promise<{ default: PluginViewComponent }> {
|
||||
return { default: component as PluginViewComponent };
|
||||
}
|
||||
|
||||
async function loadCliPrintingPressWizardView(): Promise<{ default: PluginViewComponent }> {
|
||||
const moduleId = "@fusion-plugin-examples/cli-printing-press/dashboard-view";
|
||||
const exportName = "CliPrintingPressWizardView";
|
||||
const mod = await import("@fusion-plugin-examples/cli-printing-press/dashboard-view") as unknown as Record<string, ComponentType<{ context?: PluginDashboardViewContext }>>;
|
||||
const component = mod[exportName];
|
||||
if (!component) {
|
||||
console.warn(`[plugin-views] Missing export ${exportName} from ${moduleId}`);
|
||||
return { default: createMissingPluginView(moduleId, exportName) };
|
||||
}
|
||||
return { default: component as PluginViewComponent };
|
||||
}
|
||||
|
||||
export function registerBundledPluginViews(): void {
|
||||
if (registered) return;
|
||||
registered = true;
|
||||
@@ -52,6 +64,12 @@ export function registerBundledPluginViews(): void {
|
||||
"roadmaps",
|
||||
lazy(loadRoadmapView),
|
||||
);
|
||||
|
||||
registerPluginView(
|
||||
"fusion-plugin-cli-printing-press",
|
||||
"wizard",
|
||||
lazy(loadCliPrintingPressWizardView),
|
||||
);
|
||||
}
|
||||
|
||||
export function __test_resetBundledPluginViewRegistration(): void {
|
||||
|
||||
@@ -79,6 +79,7 @@
|
||||
"@fusion-plugin-examples/openclaw-runtime": "workspace:*",
|
||||
"@fusion-plugin-examples/droid-runtime": "workspace:*",
|
||||
"@fusion-plugin-examples/cursor-runtime": "workspace:*",
|
||||
"@fusion-plugin-examples/cli-printing-press": "workspace:*",
|
||||
"@fusion-plugin-examples/paperclip-runtime": "workspace:*",
|
||||
"@fusion/core": "workspace:*",
|
||||
"@fusion/engine": "workspace:*",
|
||||
|
||||
Reference in New Issue
Block a user