a reactive (signals based) hypermedia web framework (wip)
stormlightlabs.github.io/volt/
hypermedia
frontend
signals
1import { clearPlugins, getRegisteredPlugins, hasPlugin, registerPlugin, unregisterPlugin } from "$core/plugin";
2import { beforeEach, describe, expect, it, vi } from "vitest";
3
4describe("plugin system", () => {
5 beforeEach(() => {
6 clearPlugins();
7 });
8
9 describe("registerPlugin", () => {
10 it("registers a plugin with a given name", () => {
11 const handler = vi.fn();
12 registerPlugin("test", handler);
13 expect(hasPlugin("test")).toBe(true);
14 });
15
16 it("allows overwriting existing plugins with a warning", () => {
17 const warnSpy = vi.spyOn(console, "warn").mockImplementation(() => {});
18 const handler1 = vi.fn();
19 const handler2 = vi.fn();
20
21 registerPlugin("test", handler1);
22 registerPlugin("test", handler2);
23
24 expect(warnSpy).toHaveBeenCalledWith("Plugin \"test\" is already registered. Overwriting.");
25 expect(hasPlugin("test")).toBe(true);
26
27 warnSpy.mockRestore();
28 });
29
30 it("registers multiple plugins independently", () => {
31 const handler1 = vi.fn();
32 const handler2 = vi.fn();
33
34 registerPlugin("plugin1", handler1);
35 registerPlugin("plugin2", handler2);
36
37 expect(hasPlugin("plugin1")).toBe(true);
38 expect(hasPlugin("plugin2")).toBe(true);
39 });
40 });
41
42 describe("hasPlugin", () => {
43 it("returns true for registered plugins", () => {
44 const handler = vi.fn();
45 registerPlugin("test", handler);
46 expect(hasPlugin("test")).toBe(true);
47 });
48
49 it("returns false for unregistered plugins", () => {
50 expect(hasPlugin("nonexistent")).toBe(false);
51 });
52
53 it("returns false after plugin is unregistered", () => {
54 const handler = vi.fn();
55 registerPlugin("test", handler);
56 unregisterPlugin("test");
57
58 expect(hasPlugin("test")).toBe(false);
59 });
60 });
61
62 describe("unregisterPlugin", () => {
63 it("unregisters a plugin and returns true", () => {
64 const handler = vi.fn();
65 registerPlugin("test", handler);
66
67 const result = unregisterPlugin("test");
68
69 expect(result).toBe(true);
70 expect(hasPlugin("test")).toBe(false);
71 });
72
73 it("returns false when unregistering nonexistent plugin", () => {
74 const result = unregisterPlugin("nonexistent");
75 expect(result).toBe(false);
76 });
77 });
78
79 describe("getRegisteredPlugins", () => {
80 it("returns empty array when no plugins registered", () => {
81 expect(getRegisteredPlugins()).toEqual([]);
82 });
83
84 it("returns array of registered plugin names", () => {
85 const handler = vi.fn();
86 registerPlugin("plugin1", handler);
87 registerPlugin("plugin2", handler);
88 registerPlugin("plugin3", handler);
89
90 const plugins = getRegisteredPlugins();
91 expect(plugins).toHaveLength(3);
92 expect(plugins).toContain("plugin1");
93 expect(plugins).toContain("plugin2");
94 expect(plugins).toContain("plugin3");
95 });
96
97 it("updates when plugins are added or removed", () => {
98 const handler = vi.fn();
99
100 registerPlugin("plugin1", handler);
101 expect(getRegisteredPlugins()).toEqual(["plugin1"]);
102
103 registerPlugin("plugin2", handler);
104 expect(getRegisteredPlugins()).toHaveLength(2);
105
106 unregisterPlugin("plugin1");
107 expect(getRegisteredPlugins()).toEqual(["plugin2"]);
108 });
109 });
110
111 describe("clearPlugins", () => {
112 it("removes all registered plugins", () => {
113 const handler = vi.fn();
114
115 registerPlugin("plugin1", handler);
116 registerPlugin("plugin2", handler);
117 registerPlugin("plugin3", handler);
118 clearPlugins();
119
120 expect(getRegisteredPlugins()).toEqual([]);
121 expect(hasPlugin("plugin1")).toBe(false);
122 expect(hasPlugin("plugin2")).toBe(false);
123 expect(hasPlugin("plugin3")).toBe(false);
124 });
125 });
126});