Summary
In packages/cli/src/shared/agent-setup.ts:271, the GitHub token is base64-encoded and passed to the remote server via a shell environment variable:
const tokenB64 = Buffer.from(githubToken).toString('base64');
ghCmd = `export GITHUB_TOKEN=$(printf '%s' ${shellQuote(tokenB64)} | base64 -d) && ${ghCmd}`;
Vulnerability: Environment variables set inline with commands are visible in process listings (ps auxe, /proc/PID/environ) for the duration of command execution. If an attacker has local access or compromises a monitoring tool, they can extract the token.
Impact
Severity: MEDIUM
- Requires concurrent local/remote access during the brief window when
offerGithubAuth() runs
- Token grants GitHub API access scoped to the user's permissions
- Could enable unauthorized repo access, issue/PR manipulation, or package publishing
Remediation
Use a temp file approach instead:
const tmpFile = join(getTmpDir(), `spawn_gh_token_${Date.now()}_${Math.random().toString(36).slice(2)}`);
writeFileSync(tmpFile, githubToken, { mode: 0o600 });
ghCmd = `export GITHUB_TOKEN=$(cat ${shellQuote(tmpFile)}) && rm -f ${shellQuote(tmpFile)} && ${ghCmd}`;
This keeps the token out of process listings and cleans up immediately after sourcing.
References
- File:
packages/cli/src/shared/agent-setup.ts:271
- Function:
offerGithubAuth()
- Related: Similar pattern already used safely in
uploadConfigFile() (lines 88-118)
Summary
In
packages/cli/src/shared/agent-setup.ts:271, the GitHub token is base64-encoded and passed to the remote server via a shell environment variable:Vulnerability: Environment variables set inline with commands are visible in process listings (
ps auxe,/proc/PID/environ) for the duration of command execution. If an attacker has local access or compromises a monitoring tool, they can extract the token.Impact
Severity: MEDIUM
offerGithubAuth()runsRemediation
Use a temp file approach instead:
This keeps the token out of process listings and cleans up immediately after sourcing.
References
packages/cli/src/shared/agent-setup.ts:271offerGithubAuth()uploadConfigFile()(lines 88-118)