@@ -5,6 +5,7 @@
|
||||
*/
|
||||
import * as path from "node:path";
|
||||
import { logger, parseFrontmatter, tryParseJson } from "@oh-my-pi/pi-utils";
|
||||
import { YAML } from "bun";
|
||||
import { registerProvider } from "../capability";
|
||||
import { type ContextFile, contextFileCapability } from "../capability/context-file";
|
||||
import { type Extension, type ExtensionManifest, extensionCapability } from "../capability/extension";
|
||||
@@ -778,22 +779,46 @@ async function loadSettings(ctx: LoadContext): Promise<LoadResult<Settings>> {
|
||||
const items: Settings[] = [];
|
||||
const warnings: string[] = [];
|
||||
|
||||
const parseYamlSettings = (content: string, filePath: string): Record<string, unknown> | null => {
|
||||
try {
|
||||
const data = YAML.parse(content);
|
||||
if (!data || typeof data !== "object" || Array.isArray(data)) return {};
|
||||
return data as Record<string, unknown>;
|
||||
} catch {
|
||||
warnings.push(`Failed to parse ${filePath}`);
|
||||
return null;
|
||||
}
|
||||
};
|
||||
|
||||
for (const { dir, level } of await getConfigDirs(ctx)) {
|
||||
const settingsPath = path.join(dir, "settings.json");
|
||||
const content = await readFile(settingsPath);
|
||||
if (!content) continue;
|
||||
|
||||
const data = tryParseJson<Record<string, unknown>>(content);
|
||||
if (!data) {
|
||||
warnings.push(`Failed to parse ${settingsPath}`);
|
||||
continue;
|
||||
const settingsContent = await readFile(settingsPath);
|
||||
if (settingsContent) {
|
||||
const data = tryParseJson<Record<string, unknown>>(settingsContent);
|
||||
if (data) {
|
||||
items.push({
|
||||
path: settingsPath,
|
||||
data,
|
||||
level,
|
||||
_source: createSourceMeta(PROVIDER_ID, settingsPath, level),
|
||||
});
|
||||
} else {
|
||||
warnings.push(`Failed to parse ${settingsPath}`);
|
||||
}
|
||||
}
|
||||
|
||||
const configPath = path.join(dir, "config.yml");
|
||||
const configContent = await readFile(configPath);
|
||||
if (!configContent) continue;
|
||||
|
||||
const data = parseYamlSettings(configContent, configPath);
|
||||
if (!data) continue;
|
||||
|
||||
items.push({
|
||||
path: settingsPath,
|
||||
path: configPath,
|
||||
data,
|
||||
level,
|
||||
_source: createSourceMeta(PROVIDER_ID, settingsPath, level),
|
||||
_source: createSourceMeta(PROVIDER_ID, configPath, level),
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
@@ -54,6 +54,15 @@ describe("autocompleteMaxVisible setting", () => {
|
||||
const settings = await Settings.init({ cwd: projectDir, agentDir });
|
||||
expect(settings.get("autocompleteMaxVisible")).toBe(15);
|
||||
});
|
||||
|
||||
it("should let project config.yml override global config.yml", async () => {
|
||||
await Bun.write(path.join(agentDir, "config.yml"), YAML.stringify({ autocompleteMaxVisible: 15 }, null, 2));
|
||||
await Bun.write(path.join(getProjectAgentDir(projectDir), "config.yml"), YAML.stringify({ autocompleteMaxVisible: 20 }, null, 2));
|
||||
|
||||
const settings = await Settings.init({ cwd: projectDir, agentDir });
|
||||
|
||||
expect(settings.get("autocompleteMaxVisible")).toBe(20);
|
||||
});
|
||||
|
||||
it("should coerce submenu string values for live editor updates", () => {
|
||||
const setAutocompleteMaxVisible = vi.fn();
|
||||
|
||||
Reference in New Issue
Block a user