Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 12 additions & 0 deletions packages/web/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -47,17 +47,29 @@
},
"dependencies": {
"@aoagents/ao-core": "workspace:*",
"@aoagents/ao-plugin-agent-aider": "workspace:*",
"@aoagents/ao-plugin-agent-claude-code": "workspace:*",
"@aoagents/ao-plugin-agent-codex": "workspace:*",
"@aoagents/ao-plugin-agent-cursor": "workspace:*",
"@aoagents/ao-plugin-agent-grok": "workspace:*",
"@aoagents/ao-plugin-agent-kimicode": "workspace:*",
"@aoagents/ao-plugin-agent-opencode": "workspace:*",
"@aoagents/ao-plugin-notifier-composio": "workspace:*",
"@aoagents/ao-plugin-notifier-desktop": "workspace:*",
"@aoagents/ao-plugin-notifier-discord": "workspace:*",
"@aoagents/ao-plugin-notifier-openclaw": "workspace:*",
"@aoagents/ao-plugin-notifier-slack": "workspace:*",
"@aoagents/ao-plugin-notifier-webhook": "workspace:*",
"@aoagents/ao-plugin-runtime-process": "workspace:*",
"@aoagents/ao-plugin-runtime-tmux": "workspace:*",
"@aoagents/ao-plugin-scm-github": "workspace:*",
"@aoagents/ao-plugin-scm-gitlab": "workspace:*",
"@aoagents/ao-plugin-terminal-iterm2": "workspace:*",
"@aoagents/ao-plugin-terminal-web": "workspace:*",
"@aoagents/ao-plugin-tracker-github": "workspace:*",
"@aoagents/ao-plugin-tracker-gitlab": "workspace:*",
"@aoagents/ao-plugin-tracker-linear": "workspace:*",
"@aoagents/ao-plugin-workspace-clone": "workspace:*",
"@aoagents/ao-plugin-workspace-worktree": "workspace:*",
"@xterm/addon-fit": "0.12.0-beta.256",
"@xterm/addon-unicode11": "0.10.0-beta.256",
Expand Down
57 changes: 56 additions & 1 deletion packages/web/src/__tests__/services.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,28 @@ const {
mockCreateSessionManager,
mockRegistry,
tmuxPlugin,
processPlugin,
aiderPlugin,
claudePlugin,
codexPlugin,
cursorPlugin,
grokPlugin,
opencodePlugin,
worktreePlugin,
clonePlugin,
scmPlugin,
scmGitlabPlugin,
terminalIterm2Plugin,
terminalWebPlugin,
trackerGithubPlugin,
trackerGitlabPlugin,
trackerLinearPlugin,
notifierComposioPlugin,
notifierDesktopPlugin,
notifierDiscordPlugin,
notifierOpenClawPlugin,
notifierSlackPlugin,
notifierWebhookPlugin,
} = vi.hoisted(() => {
const mockLoadConfig = vi.fn();
const mockGetGlobalConfigPath = vi.fn();
Expand Down Expand Up @@ -43,14 +57,28 @@ const {
mockCreateSessionManager,
mockRegistry,
tmuxPlugin: { manifest: { name: "tmux" } },
processPlugin: { manifest: { name: "process" } },
aiderPlugin: { manifest: { name: "aider" } },
claudePlugin: { manifest: { name: "claude-code" } },
codexPlugin: { manifest: { name: "codex" } },
cursorPlugin: { manifest: { name: "cursor" } },
grokPlugin: { manifest: { name: "grok" } },
opencodePlugin: { manifest: { name: "opencode" } },
worktreePlugin: { manifest: { name: "worktree" } },
clonePlugin: { manifest: { name: "clone" } },
scmPlugin: { manifest: { name: "github" } },
scmGitlabPlugin: { manifest: { name: "gitlab" } },
terminalIterm2Plugin: { manifest: { name: "iterm2" } },
terminalWebPlugin: { manifest: { name: "web" } },
trackerGithubPlugin: { manifest: { name: "github" } },
trackerGitlabPlugin: { manifest: { name: "gitlab" } },
trackerLinearPlugin: { manifest: { name: "linear" } },
notifierComposioPlugin: { manifest: { name: "composio" } },
notifierDesktopPlugin: { manifest: { name: "desktop" } },
notifierDiscordPlugin: { manifest: { name: "discord" } },
notifierOpenClawPlugin: { manifest: { name: "openclaw" } },
notifierSlackPlugin: { manifest: { name: "slack" } },
notifierWebhookPlugin: { manifest: { name: "webhook" } },
};
});

Expand All @@ -70,14 +98,28 @@ vi.mock("@aoagents/ao-core", () => ({
}));

vi.mock("@aoagents/ao-plugin-runtime-tmux", () => ({ default: tmuxPlugin }));
vi.mock("@aoagents/ao-plugin-runtime-process", () => ({ default: processPlugin }));
vi.mock("@aoagents/ao-plugin-agent-aider", () => ({ default: aiderPlugin }));
vi.mock("@aoagents/ao-plugin-agent-claude-code", () => ({ default: claudePlugin }));
vi.mock("@aoagents/ao-plugin-agent-codex", () => ({ default: codexPlugin }));
vi.mock("@aoagents/ao-plugin-agent-cursor", () => ({ default: cursorPlugin }));
vi.mock("@aoagents/ao-plugin-agent-grok", () => ({ default: grokPlugin }));
vi.mock("@aoagents/ao-plugin-agent-opencode", () => ({ default: opencodePlugin }));
vi.mock("@aoagents/ao-plugin-workspace-worktree", () => ({ default: worktreePlugin }));
vi.mock("@aoagents/ao-plugin-workspace-clone", () => ({ default: clonePlugin }));
vi.mock("@aoagents/ao-plugin-scm-github", () => ({ default: scmPlugin }));
vi.mock("@aoagents/ao-plugin-scm-gitlab", () => ({ default: scmGitlabPlugin }));
vi.mock("@aoagents/ao-plugin-terminal-iterm2", () => ({ default: terminalIterm2Plugin }));
vi.mock("@aoagents/ao-plugin-terminal-web", () => ({ default: terminalWebPlugin }));
vi.mock("@aoagents/ao-plugin-tracker-github", () => ({ default: trackerGithubPlugin }));
vi.mock("@aoagents/ao-plugin-tracker-gitlab", () => ({ default: trackerGitlabPlugin }));
vi.mock("@aoagents/ao-plugin-tracker-linear", () => ({ default: trackerLinearPlugin }));
vi.mock("@aoagents/ao-plugin-notifier-composio", () => ({ default: notifierComposioPlugin }));
vi.mock("@aoagents/ao-plugin-notifier-desktop", () => ({ default: notifierDesktopPlugin }));
vi.mock("@aoagents/ao-plugin-notifier-discord", () => ({ default: notifierDiscordPlugin }));
vi.mock("@aoagents/ao-plugin-notifier-openclaw", () => ({ default: notifierOpenClawPlugin }));
vi.mock("@aoagents/ao-plugin-notifier-slack", () => ({ default: notifierSlackPlugin }));
vi.mock("@aoagents/ao-plugin-notifier-webhook", () => ({ default: notifierWebhookPlugin }));

describe("services", () => {
beforeEach(() => {
Expand Down Expand Up @@ -123,12 +165,25 @@ describe("services", () => {
expect(mockRegister).toHaveBeenCalledWith(codexPlugin);
});

it("registers the Grok agent plugin with web services", async () => {
it("registers built-in plugins that the web server must bundle statically", async () => {
const { getServices } = await import("../lib/services");

await getServices();

expect(mockRegister).toHaveBeenCalledWith(processPlugin);
expect(mockRegister).toHaveBeenCalledWith(aiderPlugin);
expect(mockRegister).toHaveBeenCalledWith(grokPlugin);
expect(mockRegister).toHaveBeenCalledWith(clonePlugin);
expect(mockRegister).toHaveBeenCalledWith(scmGitlabPlugin);
expect(mockRegister).toHaveBeenCalledWith(trackerGitlabPlugin);
expect(mockRegister).toHaveBeenCalledWith(notifierComposioPlugin);
expect(mockRegister).toHaveBeenCalledWith(notifierDesktopPlugin);
expect(mockRegister).toHaveBeenCalledWith(notifierDiscordPlugin);
expect(mockRegister).toHaveBeenCalledWith(notifierOpenClawPlugin);
expect(mockRegister).toHaveBeenCalledWith(notifierSlackPlugin);
expect(mockRegister).toHaveBeenCalledWith(notifierWebhookPlugin);
expect(mockRegister).toHaveBeenCalledWith(terminalIterm2Plugin);
expect(mockRegister).toHaveBeenCalledWith(terminalWebPlugin);
});

it("caches initialized services across repeated calls", async () => {
Expand Down
24 changes: 24 additions & 0 deletions packages/web/src/lib/services.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,16 +35,28 @@ import {
// Static plugin imports — webpack needs these to be string literals
import pluginRuntimeTmux from "@aoagents/ao-plugin-runtime-tmux";
import pluginRuntimeProcess from "@aoagents/ao-plugin-runtime-process";
import pluginAgentAider from "@aoagents/ao-plugin-agent-aider";
import pluginAgentClaudeCode from "@aoagents/ao-plugin-agent-claude-code";
import pluginAgentCodex from "@aoagents/ao-plugin-agent-codex";
import pluginAgentCursor from "@aoagents/ao-plugin-agent-cursor";
import pluginAgentKimicode from "@aoagents/ao-plugin-agent-kimicode";
import pluginAgentGrok from "@aoagents/ao-plugin-agent-grok";
import pluginAgentOpencode from "@aoagents/ao-plugin-agent-opencode";
import pluginWorkspaceWorktree from "@aoagents/ao-plugin-workspace-worktree";
import pluginWorkspaceClone from "@aoagents/ao-plugin-workspace-clone";
import pluginScmGithub from "@aoagents/ao-plugin-scm-github";
import pluginScmGitlab from "@aoagents/ao-plugin-scm-gitlab";
import pluginTerminalIterm2 from "@aoagents/ao-plugin-terminal-iterm2";
import pluginTerminalWeb from "@aoagents/ao-plugin-terminal-web";
import pluginTrackerGithub from "@aoagents/ao-plugin-tracker-github";
import pluginTrackerGitlab from "@aoagents/ao-plugin-tracker-gitlab";
import pluginTrackerLinear from "@aoagents/ao-plugin-tracker-linear";
import pluginNotifierComposio from "@aoagents/ao-plugin-notifier-composio";
import pluginNotifierDesktop from "@aoagents/ao-plugin-notifier-desktop";
import pluginNotifierDiscord from "@aoagents/ao-plugin-notifier-discord";
import pluginNotifierOpenClaw from "@aoagents/ao-plugin-notifier-openclaw";
import pluginNotifierSlack from "@aoagents/ao-plugin-notifier-slack";
import pluginNotifierWebhook from "@aoagents/ao-plugin-notifier-webhook";

export interface Services {
config: LoadedConfig;
Expand Down Expand Up @@ -108,16 +120,28 @@ async function initServices(): Promise<Services> {
// Register plugins explicitly (webpack can't handle dynamic import() in core)
registry.register(pluginRuntimeTmux);
registry.register(pluginRuntimeProcess);
registry.register(pluginAgentAider);
registry.register(pluginAgentClaudeCode);
registry.register(pluginAgentCodex);
registry.register(pluginAgentCursor);
registry.register(pluginAgentKimicode);
registry.register(pluginAgentGrok);
registry.register(pluginAgentOpencode);
registry.register(pluginWorkspaceWorktree);
registry.register(pluginWorkspaceClone);
registry.register(pluginScmGithub);
registry.register(pluginScmGitlab);
registry.register(pluginTerminalIterm2);
registry.register(pluginTerminalWeb);
registry.register(pluginTrackerGithub);
registry.register(pluginTrackerGitlab);
registry.register(pluginTrackerLinear);
registry.register(pluginNotifierComposio);
registry.register(pluginNotifierDesktop);
registry.register(pluginNotifierDiscord);
registry.register(pluginNotifierOpenClaw);
registry.register(pluginNotifierSlack);
registry.register(pluginNotifierWebhook);

const sessionManager = createSessionManager({ config, registry });

Expand Down
44 changes: 40 additions & 4 deletions pnpm-lock.yaml

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading