Agents for developpement added + frontend add + backend added. Git viewer created + agent and template creator + layout and project creator
95 lines
3.1 KiB
TypeScript
95 lines
3.1 KiB
TypeScript
/**
|
|
* L5 — the in-memory {@link MockProfileGateway}: first-run flag lifecycle,
|
|
* reference catalogue, simulated detection (only `claude` installed), and the
|
|
* save/list/delete/configure CRUD.
|
|
*/
|
|
import { describe, it, expect } from "vitest";
|
|
|
|
import type { AgentProfile } from "@/domain";
|
|
import { MockProfileGateway, MOCK_REFERENCE_PROFILES } from "./index";
|
|
|
|
function customProfile(id: string, command: string): AgentProfile {
|
|
return {
|
|
id,
|
|
name: `Custom ${id}`,
|
|
command,
|
|
args: [],
|
|
contextInjection: { strategy: "stdin" },
|
|
detect: null,
|
|
cwdTemplate: "{projectRoot}",
|
|
};
|
|
}
|
|
|
|
describe("MockProfileGateway", () => {
|
|
it("firstRunState is first-run with the four reference profiles", async () => {
|
|
const gw = new MockProfileGateway();
|
|
const state = await gw.firstRunState();
|
|
expect(state.isFirstRun).toBe(true);
|
|
expect(state.referenceProfiles.map((p) => p.command)).toEqual([
|
|
"claude",
|
|
"codex",
|
|
"gemini",
|
|
"aider",
|
|
]);
|
|
});
|
|
|
|
it("referenceProfiles returns a clone of the catalogue", async () => {
|
|
const gw = new MockProfileGateway();
|
|
const refs = await gw.referenceProfiles();
|
|
expect(refs).toEqual(MOCK_REFERENCE_PROFILES);
|
|
refs[0].command = "mutated";
|
|
const again = await gw.referenceProfiles();
|
|
expect(again[0].command).toBe("claude");
|
|
});
|
|
|
|
it("detectProfiles marks only claude as installed", async () => {
|
|
const gw = new MockProfileGateway();
|
|
const results = await gw.detectProfiles([...MOCK_REFERENCE_PROFILES]);
|
|
const byCommand = Object.fromEntries(
|
|
results.map((r) => [r.profile.command, r.available]),
|
|
);
|
|
expect(byCommand).toEqual({
|
|
claude: true,
|
|
codex: false,
|
|
gemini: false,
|
|
aider: false,
|
|
});
|
|
});
|
|
|
|
it("saveProfile upserts and listProfiles reflects it", async () => {
|
|
const gw = new MockProfileGateway();
|
|
await gw.saveProfile(customProfile("c1", "foo"));
|
|
await gw.saveProfile(customProfile("c1", "bar")); // same id ⇒ replace
|
|
const list = await gw.listProfiles();
|
|
expect(list).toHaveLength(1);
|
|
expect(list[0].command).toBe("bar");
|
|
});
|
|
|
|
it("deleteProfile removes by id", async () => {
|
|
const gw = new MockProfileGateway();
|
|
await gw.saveProfile(customProfile("a", "a"));
|
|
await gw.saveProfile(customProfile("b", "b"));
|
|
await gw.deleteProfile("a");
|
|
const list = await gw.listProfiles();
|
|
expect(list.map((p) => p.id)).toEqual(["b"]);
|
|
});
|
|
|
|
it("configureProfiles persists the batch and closes the first run", async () => {
|
|
const gw = new MockProfileGateway();
|
|
expect((await gw.firstRunState()).isFirstRun).toBe(true);
|
|
|
|
const chosen = [customProfile("x", "x")];
|
|
const out = await gw.configureProfiles(chosen);
|
|
expect(out).toEqual(chosen);
|
|
|
|
expect((await gw.firstRunState()).isFirstRun).toBe(false);
|
|
expect(await gw.listProfiles()).toEqual(chosen);
|
|
});
|
|
|
|
it("configureProfiles with an empty list still closes the first run", async () => {
|
|
const gw = new MockProfileGateway();
|
|
await gw.configureProfiles([]);
|
|
expect((await gw.firstRunState()).isFirstRun).toBe(false);
|
|
});
|
|
});
|