From 62d84fee8e76579b251e706177d72d802a5c9402 Mon Sep 17 00:00:00 2001 From: gonzaloriestra <14979109+gonzaloriestra@users.noreply.github.com> Date: Sun, 6 Sep 2026 00:16:45 +0000 Subject: [PATCH] [Security] Prevent option injection in removeGitRemote Validate remoteName parameter in removeGitRemote to ensure it does not start with a hyphen, preventing option injection attacks. --- packages/cli-kit/src/public/node/git.test.ts | 10 ++++++++++ packages/cli-kit/src/public/node/git.ts | 5 +++++ 2 files changed, 15 insertions(+) diff --git a/packages/cli-kit/src/public/node/git.test.ts b/packages/cli-kit/src/public/node/git.test.ts index 15a317fac8a..ba3c8d8749d 100644 --- a/packages/cli-kit/src/public/node/git.test.ts +++ b/packages/cli-kit/src/public/node/git.test.ts @@ -546,4 +546,14 @@ describe('removeGitRemote()', () => { expect(mockedExeca).toHaveBeenCalledWith('git', ['remote'], {cwd: directory}) expect(mockedExeca).not.toHaveBeenCalledWith('git', ['remote', 'remove', remoteName], {cwd: directory}) }) + + test('throws an error if remoteName starts with a hyphen', async () => { + const directory = '/test/directory' + const remoteName = '-invalid-remote' + + await expect(git.removeGitRemote(directory, remoteName)).rejects.toThrowError( + /Invalid remote name: -invalid-remote. Remote names can't start with a hyphen./, + ) + expect(mockedExeca).not.toHaveBeenCalled() + }) }) diff --git a/packages/cli-kit/src/public/node/git.ts b/packages/cli-kit/src/public/node/git.ts index cc535196dfb..0bb5fb5fae7 100644 --- a/packages/cli-kit/src/public/node/git.ts +++ b/packages/cli-kit/src/public/node/git.ts @@ -435,6 +435,11 @@ export async function getLatestTag(directory?: string): Promise { + // Guard against option injection attacks if remoteName starts with '-' + if (remoteName.startsWith('-')) { + throw new AbortError(`Invalid remote name: ${remoteName}. Remote names can't start with a hyphen.`) + } + outputDebug(outputContent`Removing git remote ${remoteName} from ${outputToken.path(directory)}...`) await ensureGitIsPresentOrAbort()