feat(FN-1798): merge fusion/fn-1798

This commit is contained in:
gsxdsm
2026-04-14 12:45:09 -07:00
parent 66dafb0e96
commit a10151d234
10 changed files with 102 additions and 110 deletions

View File

@@ -221,14 +221,12 @@ function readJsonObject(path: string): Record<string, any> {
function createReadOnlyPiSettingsView(cwd: string, agentDir: string): PackageManagerSettingsView {
const globalSettings = readJsonObject(join(agentDir, "settings.json"));
const legacyProjectSettings = readJsonObject(join(cwd, ".pi", "settings.json"));
const fusionProjectSettings = readJsonObject(join(cwd, ".fusion", "settings.json"));
const projectSettings = { ...legacyProjectSettings, ...fusionProjectSettings };
const mergedSettings = { ...globalSettings, ...projectSettings };
const mergedSettings = { ...globalSettings, ...fusionProjectSettings };
return {
getGlobalSettings: () => structuredClone(globalSettings),
getProjectSettings: () => structuredClone(projectSettings),
getProjectSettings: () => structuredClone(fusionProjectSettings),
getNpmCommand: () => Array.isArray(mergedSettings.npmCommand)
? [...mergedSettings.npmCommand]
: undefined,

View File

@@ -297,41 +297,17 @@ describe("resolveSessionSkills", () => {
});
});
describe("reads from .fusion/settings.json primary and .pi/settings.json fallback", () => {
it("prefers .fusion/settings.json over .pi/settings.json", () => {
const dir = createMockProjectDir(null);
// Create .pi/settings.json (legacy)
mockFiles.set(`${dir}/.pi/settings.json`, JSON.stringify({
skills: ["+skills/legacy/SKILL.md"],
}));
// Create .fusion/settings.json (newer, should win)
mockFiles.set(`${dir}/.fusion/settings.json`, JSON.stringify({
describe("reads from .fusion/settings.json only", () => {
it("reads from .fusion/settings.json", () => {
const dir = createMockProjectDir({
skills: ["+skills/fusion/SKILL.md"],
}));
});
const result = resolveSessionSkills({
projectRootDir: dir,
});
expect(result.allowedSkillPaths.has("skills/fusion/SKILL.md")).toBe(true);
expect(result.allowedSkillPaths.has("skills/legacy/SKILL.md")).toBe(false);
});
it("falls back to .pi/settings.json when .fusion/settings.json doesn't exist", () => {
const dir = createMockProjectDir(null);
// Create only .pi/settings.json (legacy)
mockFiles.set(`${dir}/.pi/settings.json`, JSON.stringify({
skills: ["+skills/legacy/SKILL.md"],
}));
const result = resolveSessionSkills({
projectRootDir: dir,
});
expect(result.allowedSkillPaths.has("skills/legacy/SKILL.md")).toBe(true);
});
});

View File

@@ -104,13 +104,11 @@ function readJsonObject(path: string): Record<string, unknown> {
}
/**
* Read project settings from .fusion/settings.json with .pi/settings.json fallback.
* Read project settings from .fusion/settings.json.
*/
function readProjectSettings(projectRootDir: string): ProjectSkillSettings {
const fusionSettings = join(projectRootDir, ".fusion", "settings.json");
const legacySettings = join(projectRootDir, ".pi", "settings.json");
// Try .fusion first, then .pi
if (existsSync(fusionSettings)) {
const parsed = readJsonObject(fusionSettings);
// Only return skill-relevant fields
@@ -120,14 +118,6 @@ function readProjectSettings(projectRootDir: string): ProjectSkillSettings {
};
}
if (existsSync(legacySettings)) {
const parsed = readJsonObject(legacySettings);
return {
skills: Array.isArray(parsed.skills) ? (parsed.skills as string[]) : undefined,
packages: Array.isArray(parsed.packages) ? (parsed.packages as Array<string | { source: string; skills?: string[] }>) : undefined,
};
}
return {};
}