Attempt to make this work

This commit is contained in:
Mark Wylde
2025-05-30 22:52:37 +01:00
parent e1be245c51
commit bbf8371776
3 changed files with 301 additions and 81 deletions

View File

@@ -12,6 +12,7 @@ import {
} from "../github/context"; } from "../github/context";
import { GITEA_SERVER_URL } from "../github/api/config"; import { GITEA_SERVER_URL } from "../github/api/config";
import { checkAndDeleteEmptyBranch } from "../github/operations/branch-cleanup"; import { checkAndDeleteEmptyBranch } from "../github/operations/branch-cleanup";
import { branchHasChanges, fetchBranch, branchExists, remoteBranchExists } from "../github/utils/local-git";
async function run() { async function run() {
try { try {
@@ -105,8 +106,84 @@ async function run() {
const containsPRUrl = currentBody.match(prUrlPattern); const containsPRUrl = currentBody.match(prUrlPattern);
if (!containsPRUrl) { if (!containsPRUrl) {
// Use direct SHA comparison for all Git platforms // Check if we're using Gitea or GitHub
console.log("Using SHA comparison for PR link check"); const giteaApiUrl = process.env.GITEA_API_URL?.trim();
const isGitea = giteaApiUrl &&
giteaApiUrl !== "" &&
!giteaApiUrl.includes("api.github.com") &&
!giteaApiUrl.includes("github.com");
if (isGitea) {
// Use local git commands for Gitea
console.log("Using local git commands for PR link check (Gitea mode)");
try {
// Fetch latest changes from remote
await fetchBranch(claudeBranch);
await fetchBranch(baseBranch);
// Check if branch exists and has changes
const { hasChanges, branchSha, baseSha } = await branchHasChanges(claudeBranch, baseBranch);
if (branchSha && baseSha) {
if (hasChanges) {
console.log(
`Branch ${claudeBranch} appears to have changes (different SHA from base)`,
);
const entityType = context.isPR ? "PR" : "Issue";
const prTitle = encodeURIComponent(
`${entityType} #${context.entityNumber}: Changes from Claude`,
);
const prBody = encodeURIComponent(
`This PR addresses ${entityType.toLowerCase()} #${context.entityNumber}\n\nGenerated with [Claude Code](https://claude.ai/code)`,
);
const prUrl = `${serverUrl}/${owner}/${repo}/compare/${baseBranch}...${claudeBranch}?quick_pull=1&title=${prTitle}&body=${prBody}`;
prLink = `\n[Create a PR](${prUrl})`;
} else {
console.log(
`Branch ${claudeBranch} has same SHA as base, no PR link needed`,
);
}
} else {
// If we can't get SHAs, check if branch exists at all
const localExists = await branchExists(claudeBranch);
const remoteExists = await remoteBranchExists(claudeBranch);
if (localExists || remoteExists) {
console.log(`Branch ${claudeBranch} exists but SHA comparison failed, adding PR link to be safe`);
const entityType = context.isPR ? "PR" : "Issue";
const prTitle = encodeURIComponent(
`${entityType} #${context.entityNumber}: Changes from Claude`,
);
const prBody = encodeURIComponent(
`This PR addresses ${entityType.toLowerCase()} #${context.entityNumber}\n\nGenerated with [Claude Code](https://claude.ai/code)`,
);
const prUrl = `${serverUrl}/${owner}/${repo}/compare/${baseBranch}...${claudeBranch}?quick_pull=1&title=${prTitle}&body=${prBody}`;
prLink = `\n[Create a PR](${prUrl})`;
} else {
console.log(
`Branch ${claudeBranch} does not exist yet - no PR link needed`,
);
prLink = "";
}
}
} catch (error: any) {
console.error("Error checking branch with git commands:", error);
// For errors, add PR link to be safe
console.log("Adding PR link as fallback due to git command error");
const entityType = context.isPR ? "PR" : "Issue";
const prTitle = encodeURIComponent(
`${entityType} #${context.entityNumber}: Changes from Claude`,
);
const prBody = encodeURIComponent(
`This PR addresses ${entityType.toLowerCase()} #${context.entityNumber}\n\nGenerated with [Claude Code](https://claude.ai/code)`,
);
const prUrl = `${serverUrl}/${owner}/${repo}/compare/${baseBranch}...${claudeBranch}?quick_pull=1&title=${prTitle}&body=${prBody}`;
prLink = `\n[Create a PR](${prUrl})`;
}
} else {
// Use API calls for GitHub
console.log("Using API calls for PR link check (GitHub mode)");
try { try {
// Get the branch info to see if it exists and has commits // Get the branch info to see if it exists and has commits
@@ -171,6 +248,7 @@ async function run() {
} }
} }
} }
}
// Check if action failed and read output file for execution details // Check if action failed and read output file for execution details
let executionDetails: { let executionDetails: {

View File

@@ -1,5 +1,6 @@
import type { GitHubClient } from "../api/client"; import type { GitHubClient } from "../api/client";
import { GITEA_SERVER_URL } from "../api/config"; import { GITEA_SERVER_URL } from "../api/config";
import { branchHasChanges, fetchBranch, branchExists, remoteBranchExists } from "../utils/local-git";
export async function checkAndDeleteEmptyBranch( export async function checkAndDeleteEmptyBranch(
client: GitHubClient, client: GitHubClient,
@@ -12,8 +13,64 @@ export async function checkAndDeleteEmptyBranch(
let shouldDeleteBranch = false; let shouldDeleteBranch = false;
if (claudeBranch) { if (claudeBranch) {
// Use direct SHA comparison for both GitHub and Gitea // Check if we're using Gitea or GitHub
console.log("Using SHA comparison for branch check"); const giteaApiUrl = process.env.GITEA_API_URL?.trim();
const isGitea = giteaApiUrl &&
giteaApiUrl !== "" &&
!giteaApiUrl.includes("api.github.com") &&
!giteaApiUrl.includes("github.com");
if (isGitea) {
// Use local git operations for Gitea
console.log("Using local git commands for branch check (Gitea mode)");
try {
// Fetch latest changes from remote
await fetchBranch(claudeBranch);
await fetchBranch(baseBranch);
// Check if branch exists and has changes
const { hasChanges, branchSha, baseSha } = await branchHasChanges(claudeBranch, baseBranch);
if (branchSha && baseSha) {
if (hasChanges) {
console.log(
`Branch ${claudeBranch} appears to have commits (different SHA from base)`,
);
const branchUrl = `${GITEA_SERVER_URL}/${owner}/${repo}/tree/${claudeBranch}`;
branchLink = `\n[View branch](${branchUrl})`;
} else {
console.log(
`Branch ${claudeBranch} has same SHA as base, marking for deletion`,
);
shouldDeleteBranch = true;
}
} else {
// If we can't get SHAs, check if branch exists at all
const localExists = await branchExists(claudeBranch);
const remoteExists = await remoteBranchExists(claudeBranch);
if (localExists || remoteExists) {
console.log(`Branch ${claudeBranch} exists but SHA comparison failed, assuming it has commits`);
const branchUrl = `${GITEA_SERVER_URL}/${owner}/${repo}/tree/${claudeBranch}`;
branchLink = `\n[View branch](${branchUrl})`;
} else {
console.log(
`Branch ${claudeBranch} does not exist yet - this is normal during workflow`,
);
branchLink = "";
}
}
} catch (error: any) {
console.error("Error checking branch with git commands:", error);
// For errors, assume the branch has commits to be safe
console.log("Assuming branch exists due to git command error");
const branchUrl = `${GITEA_SERVER_URL}/${owner}/${repo}/tree/${claudeBranch}`;
branchLink = `\n[View branch](${branchUrl})`;
}
} else {
// Use API calls for GitHub
console.log("Using API calls for branch check (GitHub mode)");
try { try {
// Get the branch info to see if it exists and has commits // Get the branch info to see if it exists and has commits
@@ -60,6 +117,7 @@ export async function checkAndDeleteEmptyBranch(
} }
} }
} }
}
// Delete the branch if it has no commits // Delete the branch if it has no commits
if (shouldDeleteBranch && claudeBranch) { if (shouldDeleteBranch && claudeBranch) {

View File

@@ -0,0 +1,84 @@
#!/usr/bin/env bun
import { $ } from "bun";
/**
* Check if a branch exists locally using git commands
*/
export async function branchExists(branchName: string): Promise<boolean> {
try {
await $`git show-ref --verify --quiet refs/heads/${branchName}`;
return true;
} catch {
return false;
}
}
/**
* Check if a remote branch exists using git commands
*/
export async function remoteBranchExists(branchName: string): Promise<boolean> {
try {
await $`git show-ref --verify --quiet refs/remotes/origin/${branchName}`;
return true;
} catch {
return false;
}
}
/**
* Get the SHA of a branch using git commands
*/
export async function getBranchSha(branchName: string): Promise<string | null> {
try {
// Try local branch first
if (await branchExists(branchName)) {
const result = await $`git rev-parse refs/heads/${branchName}`;
return result.text().trim();
}
// Try remote branch if local doesn't exist
if (await remoteBranchExists(branchName)) {
const result = await $`git rev-parse refs/remotes/origin/${branchName}`;
return result.text().trim();
}
return null;
} catch (error) {
console.error(`Error getting SHA for branch ${branchName}:`, error);
return null;
}
}
/**
* Check if a branch has commits different from base branch
*/
export async function branchHasChanges(branchName: string, baseBranch: string): Promise<{ hasChanges: boolean; branchSha: string | null; baseSha: string | null }> {
try {
const branchSha = await getBranchSha(branchName);
const baseSha = await getBranchSha(baseBranch);
if (!branchSha || !baseSha) {
return { hasChanges: false, branchSha, baseSha };
}
const hasChanges = branchSha !== baseSha;
return { hasChanges, branchSha, baseSha };
} catch (error) {
console.error(`Error comparing branches ${branchName} and ${baseBranch}:`, error);
return { hasChanges: false, branchSha: null, baseSha: null };
}
}
/**
* Fetch latest changes from remote to ensure we have up-to-date branch info
*/
export async function fetchBranch(branchName: string): Promise<boolean> {
try {
await $`git fetch origin ${branchName}`;
return true;
} catch (error) {
console.log(`Could not fetch branch ${branchName} from remote (may not exist yet)`);
return false;
}
}