diff --git a/src/cli/config-manager/config-context.ts b/src/cli/config-manager/config-context.ts index 78eb88d77..d01e8ba85 100644 --- a/src/cli/config-manager/config-context.ts +++ b/src/cli/config-manager/config-context.ts @@ -1,8 +1,13 @@ +import { basename, extname, join } from "node:path" + import { getOpenCodeConfigPaths } from "../../shared" +import { detectPluginConfigFile } from "../../shared/jsonc-parser" +import { migrateLegacyConfigFile } from "../../shared/migrate-legacy-config-file" import type { OpenCodeBinaryType, OpenCodeConfigPaths, } from "../../shared/opencode-config-dir-types" +import { CONFIG_BASENAME, LEGACY_CONFIG_BASENAME } from "../../shared/plugin-identity" export interface ConfigContext { binary: OpenCodeBinaryType @@ -42,5 +47,20 @@ export function getConfigJsonc(): string { } export function getOmoConfigPath(): string { - return getConfigContext().paths.omoConfig + const configDir = getConfigContext().paths.configDir + const detectedConfig = detectPluginConfigFile(configDir) + + if ( + detectedConfig.format !== "none" + && basename(detectedConfig.path).startsWith(LEGACY_CONFIG_BASENAME) + ) { + const canonicalPath = join( + configDir, + `${CONFIG_BASENAME}${extname(detectedConfig.path)}`, + ) + const migrated = migrateLegacyConfigFile(detectedConfig.path) + return migrated ? canonicalPath : detectedConfig.path + } + + return detectedConfig.path } diff --git a/src/cli/config-manager/write-omo-config.test.ts b/src/cli/config-manager/write-omo-config.test.ts index 5701b53dc..83b70e9d3 100644 --- a/src/cli/config-manager/write-omo-config.test.ts +++ b/src/cli/config-manager/write-omo-config.test.ts @@ -1,5 +1,5 @@ import { afterEach, beforeEach, describe, expect, it } from "bun:test" -import { mkdirSync, readFileSync, rmSync, writeFileSync } from "node:fs" +import { existsSync, mkdirSync, readFileSync, rmSync, writeFileSync } from "node:fs" import { tmpdir } from "node:os" import { join } from "node:path" @@ -34,7 +34,7 @@ describe("writeOmoConfig", () => { beforeEach(() => { testConfigDir = join(tmpdir(), `omo-write-config-${Date.now()}-${Math.random().toString(36).slice(2)}`) - testConfigPath = join(testConfigDir, "oh-my-opencode.json") + testConfigPath = join(testConfigDir, "oh-my-openagent.json") mkdirSync(testConfigDir, { recursive: true }) process.env.OPENCODE_CONFIG_DIR = testConfigDir @@ -77,4 +77,41 @@ describe("writeOmoConfig", () => { expect(savedConfig).toHaveProperty(defaultKey) } }) + + it("migrates legacy oh-my-opencode.json to canonical oh-my-openagent.json before merging", () => { + // given + const legacyConfigPath = join(testConfigDir, "oh-my-opencode.json") + const canonicalConfigPath = join(testConfigDir, "oh-my-openagent.json") + const legacyBackupPath = `${legacyConfigPath}.bak` + writeFileSync( + legacyConfigPath, + JSON.stringify( + { + agents: { + sisyphus: { + model: "custom/provider-model", + }, + }, + }, + null, + 2, + ) + "\n", + "utf-8", + ) + + // when + const result = writeOmoConfig(installConfig) + + // then + expect(result.success).toBe(true) + expect(result.configPath).toEndWith("oh-my-openagent.json") + expect(existsSync(legacyConfigPath)).toBe(false) + expect(existsSync(legacyBackupPath)).toBe(true) + expect(existsSync(canonicalConfigPath)).toBe(true) + + const savedConfig = parseJsonc>(readFileSync(canonicalConfigPath, "utf-8")) + const savedAgents = getRecord(savedConfig.agents) + const savedSisyphus = getRecord(savedAgents.sisyphus) + expect(savedSisyphus.model).toBe("custom/provider-model") + }) }) diff --git a/src/shared/opencode-config-dir.test.ts b/src/shared/opencode-config-dir.test.ts index 5d6cf3ef5..7ddf8e009 100644 --- a/src/shared/opencode-config-dir.test.ts +++ b/src/shared/opencode-config-dir.test.ts @@ -289,7 +289,7 @@ describe("opencode-config-dir", () => { expect(paths.configJson).toBe(join(expectedDir, "opencode.json")) expect(paths.configJsonc).toBe(join(expectedDir, "opencode.jsonc")) expect(paths.packageJson).toBe(join(expectedDir, "package.json")) - expect(paths.omoConfig).toBe(join(expectedDir, "oh-my-opencode.json")) + expect(paths.omoConfig).toBe(join(expectedDir, "oh-my-openagent.json")) }) test("returns all config paths for desktop binary", () => { @@ -305,7 +305,7 @@ describe("opencode-config-dir", () => { expect(paths.configJson).toBe(join(expectedDir, "opencode.json")) expect(paths.configJsonc).toBe(join(expectedDir, "opencode.jsonc")) expect(paths.packageJson).toBe(join(expectedDir, "package.json")) - expect(paths.omoConfig).toBe(join(expectedDir, "oh-my-opencode.json")) + expect(paths.omoConfig).toBe(join(expectedDir, "oh-my-openagent.json")) }) }) diff --git a/src/shared/opencode-config-dir.ts b/src/shared/opencode-config-dir.ts index e1dedc401..7e07d4bb9 100644 --- a/src/shared/opencode-config-dir.ts +++ b/src/shared/opencode-config-dir.ts @@ -7,6 +7,7 @@ import type { OpenCodeConfigDirOptions, OpenCodeConfigPaths, } from "./opencode-config-dir-types" +import { CONFIG_BASENAME } from "./plugin-identity" export type { OpenCodeBinaryType, @@ -97,7 +98,7 @@ export function getOpenCodeConfigPaths(options: OpenCodeConfigDirOptions): OpenC configJson: join(configDir, "opencode.json"), configJsonc: join(configDir, "opencode.jsonc"), packageJson: join(configDir, "package.json"), - omoConfig: join(configDir, "oh-my-opencode.json"), + omoConfig: join(configDir, `${CONFIG_BASENAME}.json`), } }