fix local git setup
This commit is contained in:
@@ -20,7 +20,7 @@ import {
|
|||||||
revokeInstallationToken,
|
revokeInstallationToken,
|
||||||
setupGitHubInstallationToken,
|
setupGitHubInstallationToken,
|
||||||
} from "./utils/github.ts";
|
} from "./utils/github.ts";
|
||||||
import { setupGitAuth, setupGitBranch, setupGitConfig } from "./utils/setup.ts";
|
import { restoreGitConfig, setupGitAuth, setupGitBranch, setupGitConfig } from "./utils/setup.ts";
|
||||||
|
|
||||||
// runtime validation using agents (needed for ArkType)
|
// runtime validation using agents (needed for ArkType)
|
||||||
// Note: The AgentName type is defined in external.ts, this is the runtime validator
|
// Note: The AgentName type is defined in external.ts, this is the runtime validator
|
||||||
@@ -96,6 +96,8 @@ export async function main(inputs: Inputs): Promise<MainResult> {
|
|||||||
error: errorMessage,
|
error: errorMessage,
|
||||||
};
|
};
|
||||||
} finally {
|
} finally {
|
||||||
|
restoreGitConfig();
|
||||||
|
|
||||||
if (pollInterval) {
|
if (pollInterval) {
|
||||||
clearInterval(pollInterval);
|
clearInterval(pollInterval);
|
||||||
}
|
}
|
||||||
|
|||||||
+105
-22
@@ -5,6 +5,9 @@ import { log } from "./cli.ts";
|
|||||||
import type { RepoContext } from "./github.ts";
|
import type { RepoContext } from "./github.ts";
|
||||||
import { $ } from "./shell.ts";
|
import { $ } from "./shell.ts";
|
||||||
|
|
||||||
|
// Store original remote URL for cleanup (only thing we need to restore)
|
||||||
|
let originalRemoteUrl: string | null = null;
|
||||||
|
|
||||||
export interface SetupOptions {
|
export interface SetupOptions {
|
||||||
tempDir: string;
|
tempDir: string;
|
||||||
repoUrl?: string;
|
repoUrl?: string;
|
||||||
@@ -43,20 +46,22 @@ export function setupTestRepo(options: SetupOptions): void {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Setup git configuration to avoid identity errors
|
* Setup git configuration to avoid identity errors
|
||||||
* Only runs in GitHub Actions environment to avoid overwriting local git config
|
* Uses --local flag to scope config to the current repo only
|
||||||
*/
|
*/
|
||||||
export function setupGitConfig(): void {
|
export function setupGitConfig(): void {
|
||||||
// Only set up git config in GitHub Actions environment
|
const repoDir = process.cwd();
|
||||||
// In local development, use the user's existing git config
|
|
||||||
if (!process.env.GITHUB_ACTIONS) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
log.info("🔧 Setting up git configuration...");
|
log.info("🔧 Setting up git configuration...");
|
||||||
try {
|
try {
|
||||||
execSync('git config user.email "action@pullfrog.ai"', { stdio: "pipe" });
|
// Use --local to scope config to this repo only, preventing leakage to user's global config
|
||||||
execSync('git config user.name "Pullfrog Action"', { stdio: "pipe" });
|
execSync('git config --local user.email "action@pullfrog.ai"', {
|
||||||
log.debug("setupGitConfig: ✓ Git configuration set successfully");
|
cwd: repoDir,
|
||||||
|
stdio: "pipe",
|
||||||
|
});
|
||||||
|
execSync('git config --local user.name "Pullfrog Action"', {
|
||||||
|
cwd: repoDir,
|
||||||
|
stdio: "pipe",
|
||||||
|
});
|
||||||
|
log.debug("setupGitConfig: ✓ Git configuration set successfully (scoped to repo)");
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
// If git config fails, log warning but don't fail the action
|
// If git config fails, log warning but don't fail the action
|
||||||
// This can happen if we're not in a git repo or git isn't available
|
// This can happen if we're not in a git repo or git isn't available
|
||||||
@@ -67,30 +72,43 @@ export function setupGitConfig(): void {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Setup git authentication using GitHub token
|
* Setup git authentication using GitHub installation token
|
||||||
* Only runs in GitHub Actions environment to avoid breaking local git remotes
|
* Always uses the installation token, scoped to the current repo only
|
||||||
*/
|
*/
|
||||||
export function setupGitAuth(githubToken: string, repoContext: RepoContext): void {
|
export function setupGitAuth(githubToken: string, repoContext: RepoContext): void {
|
||||||
// Only set up git auth in GitHub Actions environment
|
const repoDir = process.cwd();
|
||||||
// In local testing, this would overwrite the real git remote with fake credentials
|
|
||||||
if (!process.env.GITHUB_ACTIONS) {
|
// Store original remote URL for cleanup
|
||||||
return;
|
try {
|
||||||
|
originalRemoteUrl =
|
||||||
|
execSync("git config --local --get remote.origin.url", {
|
||||||
|
cwd: repoDir,
|
||||||
|
stdio: "pipe",
|
||||||
|
encoding: "utf-8",
|
||||||
|
}).trim() || null;
|
||||||
|
} catch {
|
||||||
|
originalRemoteUrl = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
log.info("🔐 Setting up git authentication...");
|
log.info("🔐 Setting up git authentication...");
|
||||||
|
|
||||||
// Remove existing git auth headers that actions/checkout might have set
|
// Remove existing git auth headers that actions/checkout might have set
|
||||||
|
// Use --local to scope to this repo only
|
||||||
try {
|
try {
|
||||||
execSync("git config --unset-all http.https://github.com/.extraheader", { stdio: "inherit" });
|
execSync("git config --local --unset-all http.https://github.com/.extraheader", {
|
||||||
|
cwd: repoDir,
|
||||||
|
stdio: "pipe",
|
||||||
|
});
|
||||||
log.info("✓ Removed existing authentication headers");
|
log.info("✓ Removed existing authentication headers");
|
||||||
} catch {
|
} catch {
|
||||||
log.info("No existing authentication headers to remove");
|
log.debug("No existing authentication headers to remove");
|
||||||
}
|
}
|
||||||
|
|
||||||
// Update remote URL to embed the token
|
// Update remote URL to embed the token
|
||||||
|
// This is scoped to the repo's .git/config, not the user's global config
|
||||||
const remoteUrl = `https://x-access-token:${githubToken}@github.com/${repoContext.owner}/${repoContext.name}.git`;
|
const remoteUrl = `https://x-access-token:${githubToken}@github.com/${repoContext.owner}/${repoContext.name}.git`;
|
||||||
$("git", ["remote", "set-url", "origin", remoteUrl]);
|
$("git", ["remote", "set-url", "origin", remoteUrl], { cwd: repoDir });
|
||||||
log.info("✓ Updated remote URL with authentication token");
|
log.info("✓ Updated remote URL with authentication token (scoped to repo)");
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -99,6 +117,7 @@ export function setupGitAuth(githubToken: string, repoContext: RepoContext): voi
|
|||||||
*/
|
*/
|
||||||
export function setupGitBranch(payload: Payload): void {
|
export function setupGitBranch(payload: Payload): void {
|
||||||
const branch = payload.event.branch;
|
const branch = payload.event.branch;
|
||||||
|
const repoDir = process.cwd();
|
||||||
|
|
||||||
if (!branch) {
|
if (!branch) {
|
||||||
log.debug("No branch specified in payload, using default branch");
|
log.debug("No branch specified in payload, using default branch");
|
||||||
@@ -110,11 +129,17 @@ export function setupGitBranch(payload: Payload): void {
|
|||||||
try {
|
try {
|
||||||
// Fetch the branch from origin
|
// Fetch the branch from origin
|
||||||
log.debug(`Fetching branch from origin: ${branch}`);
|
log.debug(`Fetching branch from origin: ${branch}`);
|
||||||
execSync(`git fetch origin ${branch}`, { stdio: "pipe" });
|
execSync(`git fetch origin ${branch}`, {
|
||||||
|
cwd: repoDir,
|
||||||
|
stdio: "pipe",
|
||||||
|
});
|
||||||
|
|
||||||
// Checkout the branch, creating local tracking branch
|
// Checkout the branch, creating local tracking branch
|
||||||
log.debug(`Checking out branch: ${branch}`);
|
log.debug(`Checking out branch: ${branch}`);
|
||||||
execSync(`git checkout -B ${branch} origin/${branch}`, { stdio: "pipe" });
|
execSync(`git checkout -B ${branch} origin/${branch}`, {
|
||||||
|
cwd: repoDir,
|
||||||
|
stdio: "pipe",
|
||||||
|
});
|
||||||
|
|
||||||
log.info(`✓ Successfully checked out branch: ${branch}`);
|
log.info(`✓ Successfully checked out branch: ${branch}`);
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
@@ -125,3 +150,61 @@ export function setupGitBranch(payload: Payload): void {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Clean up local git configuration after action completes
|
||||||
|
* Removes the --local config entries we added so the repo returns to its original state
|
||||||
|
* Only runs in local development (not in GitHub Actions)
|
||||||
|
*/
|
||||||
|
export function restoreGitConfig(): void {
|
||||||
|
if (process.env.GITHUB_ACTIONS) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
const repoDir = process.cwd();
|
||||||
|
log.info("🔄 Cleaning up git configuration...");
|
||||||
|
|
||||||
|
try {
|
||||||
|
try {
|
||||||
|
execSync("git config --local --unset user.email", {
|
||||||
|
cwd: repoDir,
|
||||||
|
stdio: "pipe",
|
||||||
|
});
|
||||||
|
log.debug("✓ Removed local user.email");
|
||||||
|
} catch {
|
||||||
|
// Ignore if unset fails (config might not exist)
|
||||||
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
execSync("git config --local --unset user.name", {
|
||||||
|
cwd: repoDir,
|
||||||
|
stdio: "pipe",
|
||||||
|
});
|
||||||
|
log.debug("✓ Removed local user.name");
|
||||||
|
} catch {
|
||||||
|
// Ignore if unset fails (config might not exist)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Restore original remote URL if we stored it
|
||||||
|
if (originalRemoteUrl !== null) {
|
||||||
|
try {
|
||||||
|
$("git", ["remote", "set-url", "origin", originalRemoteUrl], { cwd: repoDir });
|
||||||
|
log.debug("✓ Restored original remote URL");
|
||||||
|
} catch (error) {
|
||||||
|
log.warning(
|
||||||
|
`Failed to restore remote URL: ${error instanceof Error ? error.message : String(error)}`
|
||||||
|
);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
log.info("✓ Git configuration cleanup completed");
|
||||||
|
} catch (error) {
|
||||||
|
// Log warning but don't fail - this is cleanup
|
||||||
|
log.warning(
|
||||||
|
`Failed to clean up git config: ${error instanceof Error ? error.message : String(error)}`
|
||||||
|
);
|
||||||
|
} finally {
|
||||||
|
// Clear stored remote URL
|
||||||
|
originalRemoteUrl = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user