mirror of
https://github.com/getcompanion-ai/co-mono.git
synced 2026-04-15 09:01:14 +00:00
fix(coding-agent): normalize local package removal paths (fixes #1243)
This commit is contained in:
parent
150aeebf7d
commit
b1c2c95f23
2 changed files with 65 additions and 3 deletions
|
|
@ -94,7 +94,7 @@ function expandTildePath(input: string): string {
|
|||
|
||||
function resolveLocalSourceFromInput(source: string, cwd: string): string {
|
||||
const expanded = expandTildePath(source);
|
||||
return isAbsolute(expanded) ? expanded : resolve(cwd, expanded);
|
||||
return isAbsolute(expanded) ? resolve(expanded) : resolve(cwd, expanded);
|
||||
}
|
||||
|
||||
function resolveLocalSourceFromSettings(source: string, baseDir: string): string {
|
||||
|
|
@ -172,18 +172,21 @@ function updatePackageSources(
|
|||
cwd: string,
|
||||
agentDir: string,
|
||||
action: "add" | "remove",
|
||||
): void {
|
||||
): boolean {
|
||||
const currentSettings = local ? settingsManager.getProjectSettings() : settingsManager.getGlobalSettings();
|
||||
const currentPackages = currentSettings.packages ?? [];
|
||||
const baseDir = local ? join(cwd, CONFIG_DIR_NAME) : agentDir;
|
||||
const normalizedSource = normalizePackageSourceForSettings(source, baseDir, cwd);
|
||||
|
||||
let nextPackages: PackageSource[];
|
||||
let changed = false;
|
||||
if (action === "add") {
|
||||
const exists = currentPackages.some((existing) => packageSourcesMatch(existing, source, baseDir, cwd));
|
||||
nextPackages = exists ? currentPackages : [...currentPackages, normalizedSource];
|
||||
changed = !exists;
|
||||
} else {
|
||||
nextPackages = currentPackages.filter((existing) => !packageSourcesMatch(existing, source, baseDir, cwd));
|
||||
changed = nextPackages.length !== currentPackages.length;
|
||||
}
|
||||
|
||||
if (local) {
|
||||
|
|
@ -191,6 +194,8 @@ function updatePackageSources(
|
|||
} else {
|
||||
settingsManager.setPackages(nextPackages);
|
||||
}
|
||||
|
||||
return changed;
|
||||
}
|
||||
|
||||
async function handlePackageCommand(args: string[]): Promise<boolean> {
|
||||
|
|
@ -230,7 +235,11 @@ async function handlePackageCommand(args: string[]): Promise<boolean> {
|
|||
process.exit(1);
|
||||
}
|
||||
await packageManager.remove(options.source, { local: options.local });
|
||||
updatePackageSources(settingsManager, options.source, options.local, cwd, agentDir, "remove");
|
||||
const removed = updatePackageSources(settingsManager, options.source, options.local, cwd, agentDir, "remove");
|
||||
if (!removed) {
|
||||
console.error(chalk.red(`No matching package found for ${options.source}`));
|
||||
process.exit(1);
|
||||
}
|
||||
console.log(chalk.green(`Removed ${options.source}`));
|
||||
return true;
|
||||
}
|
||||
|
|
|
|||
53
packages/coding-agent/test/package-command-paths.test.ts
Normal file
53
packages/coding-agent/test/package-command-paths.test.ts
Normal file
|
|
@ -0,0 +1,53 @@
|
|||
import { mkdirSync, readFileSync, rmSync } from "node:fs";
|
||||
import { tmpdir } from "node:os";
|
||||
import { join } from "node:path";
|
||||
import { afterEach, beforeEach, describe, expect, it } from "vitest";
|
||||
import { ENV_AGENT_DIR } from "../src/config.js";
|
||||
import { main } from "../src/main.js";
|
||||
|
||||
describe("package commands", () => {
|
||||
let tempDir: string;
|
||||
let agentDir: string;
|
||||
let projectDir: string;
|
||||
let packageDir: string;
|
||||
let originalCwd: string;
|
||||
let originalAgentDir: string | undefined;
|
||||
|
||||
beforeEach(() => {
|
||||
tempDir = join(tmpdir(), `pi-package-commands-${Date.now()}-${Math.random().toString(36).slice(2)}`);
|
||||
agentDir = join(tempDir, "agent");
|
||||
projectDir = join(tempDir, "project");
|
||||
packageDir = join(tempDir, "local-package");
|
||||
mkdirSync(agentDir, { recursive: true });
|
||||
mkdirSync(projectDir, { recursive: true });
|
||||
mkdirSync(packageDir, { recursive: true });
|
||||
|
||||
originalCwd = process.cwd();
|
||||
originalAgentDir = process.env[ENV_AGENT_DIR];
|
||||
process.env[ENV_AGENT_DIR] = agentDir;
|
||||
process.chdir(projectDir);
|
||||
});
|
||||
|
||||
afterEach(() => {
|
||||
process.chdir(originalCwd);
|
||||
if (originalAgentDir === undefined) {
|
||||
delete process.env[ENV_AGENT_DIR];
|
||||
} else {
|
||||
process.env[ENV_AGENT_DIR] = originalAgentDir;
|
||||
}
|
||||
rmSync(tempDir, { recursive: true, force: true });
|
||||
});
|
||||
|
||||
it("should remove local packages using a path with a trailing slash", async () => {
|
||||
await main(["install", `${packageDir}/`]);
|
||||
|
||||
const settingsPath = join(agentDir, "settings.json");
|
||||
const installedSettings = JSON.parse(readFileSync(settingsPath, "utf-8")) as { packages?: string[] };
|
||||
expect(installedSettings.packages?.length).toBe(1);
|
||||
|
||||
await main(["remove", `${packageDir}/`]);
|
||||
|
||||
const removedSettings = JSON.parse(readFileSync(settingsPath, "utf-8")) as { packages?: string[] };
|
||||
expect(removedSettings.packages ?? []).toHaveLength(0);
|
||||
});
|
||||
});
|
||||
Loading…
Add table
Add a link
Reference in a new issue