Clean up logs
This commit is contained in:
+9
-9
@@ -147,7 +147,7 @@ export async function installFromNpmTarball({
|
||||
let resolvedVersion = version;
|
||||
if (version.startsWith("^") || version.startsWith("~") || version === "latest") {
|
||||
const npmRegistry = process.env.NPM_REGISTRY || "https://registry.npmjs.org";
|
||||
log.info(`Resolving version for ${version}...`);
|
||||
log.debug(`» resolving version for ${version}...`);
|
||||
try {
|
||||
const registryResponse = await fetch(`${npmRegistry}/${packageName}`);
|
||||
if (!registryResponse.ok) {
|
||||
@@ -155,7 +155,7 @@ export async function installFromNpmTarball({
|
||||
}
|
||||
const registryData = (await registryResponse.json()) as NpmRegistryData;
|
||||
resolvedVersion = registryData["dist-tags"].latest;
|
||||
log.info(`Resolved to version ${resolvedVersion}`);
|
||||
log.debug(`» resolved to version ${resolvedVersion}`);
|
||||
} catch (error) {
|
||||
log.warning(
|
||||
`Failed to resolve version from registry: ${error instanceof Error ? error.message : String(error)}`
|
||||
@@ -164,7 +164,7 @@ export async function installFromNpmTarball({
|
||||
}
|
||||
}
|
||||
|
||||
log.info(`📦 Installing ${packageName}@${resolvedVersion}...`);
|
||||
log.debug(`» installing ${packageName}@${resolvedVersion}...`);
|
||||
|
||||
const tempDir = process.env.PULLFROG_TEMP_DIR!;
|
||||
const tarballPath = join(tempDir, "package.tgz");
|
||||
@@ -181,7 +181,7 @@ export async function installFromNpmTarball({
|
||||
tarballUrl = `${npmRegistry}/${packageName}/-/${packageName}-${resolvedVersion}.tgz`;
|
||||
}
|
||||
|
||||
log.info(`Downloading from ${tarballUrl}...`);
|
||||
log.debug(`» downloading from ${tarballUrl}...`);
|
||||
const response = await fetch(tarballUrl);
|
||||
if (!response.ok) {
|
||||
throw new Error(`Failed to download tarball: ${response.status} ${response.statusText}`);
|
||||
@@ -191,10 +191,10 @@ export async function installFromNpmTarball({
|
||||
if (!response.body) throw new Error("Response body is null");
|
||||
const fileStream = createWriteStream(tarballPath);
|
||||
await pipeline(response.body, fileStream);
|
||||
log.info(`Downloaded tarball to ${tarballPath}`);
|
||||
log.debug(`» downloaded tarball to ${tarballPath}`);
|
||||
|
||||
// Extract tarball
|
||||
log.info(`Extracting tarball...`);
|
||||
log.debug(`» extracting tarball...`);
|
||||
const extractResult = spawnSync("tar", ["-xzf", tarballPath, "-C", tempDir], {
|
||||
stdio: "pipe",
|
||||
encoding: "utf-8",
|
||||
@@ -215,7 +215,7 @@ export async function installFromNpmTarball({
|
||||
|
||||
// Install dependencies if requested
|
||||
if (installDependencies) {
|
||||
log.info(`Installing dependencies for ${packageName}...`);
|
||||
log.debug(`» installing dependencies for ${packageName}...`);
|
||||
const installResult = spawnSync("npm", ["install", "--production"], {
|
||||
cwd: extractedDir,
|
||||
stdio: "pipe",
|
||||
@@ -226,13 +226,13 @@ export async function installFromNpmTarball({
|
||||
`Failed to install dependencies: ${installResult.stderr || installResult.stdout || "Unknown error"}`
|
||||
);
|
||||
}
|
||||
log.info(`✓ Dependencies installed`);
|
||||
log.debug(`» dependencies installed`);
|
||||
}
|
||||
|
||||
// Make the file executable
|
||||
chmodSync(cliPath, 0o755);
|
||||
|
||||
log.info(`✓ ${packageName} installed at ${cliPath}`);
|
||||
log.debug(`» ${packageName} installed at ${cliPath}`);
|
||||
|
||||
return cliPath;
|
||||
}
|
||||
|
||||
@@ -89750,11 +89750,11 @@ function isGitHubActionsEnvironment() {
|
||||
return Boolean(process.env.GITHUB_ACTIONS);
|
||||
}
|
||||
async function acquireTokenViaOIDC() {
|
||||
log.info("Generating OIDC token...");
|
||||
log.debug("\xBB generating OIDC token...");
|
||||
const oidcToken = await core2.getIDToken("pullfrog-api");
|
||||
log.info("OIDC token generated successfully");
|
||||
log.debug("\xBB OIDC token generated successfully");
|
||||
const apiUrl = process.env.API_URL || "https://pullfrog.com";
|
||||
log.info("Exchanging OIDC token for installation token...");
|
||||
log.debug("\xBB exchanging OIDC token for installation token...");
|
||||
const timeoutMs = 5e3;
|
||||
const controller = new AbortController();
|
||||
const timeoutId = setTimeout(() => controller.abort(), timeoutMs);
|
||||
@@ -89772,7 +89772,7 @@ async function acquireTokenViaOIDC() {
|
||||
throw new Error(`Token exchange failed: ${tokenResponse.status} ${tokenResponse.statusText}`);
|
||||
}
|
||||
const tokenData = await tokenResponse.json();
|
||||
log.info(`Installation token obtained for ${tokenData.repository || "all repositories"}`);
|
||||
log.debug(`\xBB installation token obtained for ${tokenData.repository || "all repositories"}`);
|
||||
return tokenData.token;
|
||||
} catch (error42) {
|
||||
clearTimeout(timeoutId);
|
||||
@@ -89913,7 +89913,7 @@ async function revokeGitHubInstallationToken() {
|
||||
"X-GitHub-Api-Version": "2022-11-28"
|
||||
}
|
||||
});
|
||||
log.info("Installation token revoked");
|
||||
log.debug("\xBB installation token revoked");
|
||||
} catch (error42) {
|
||||
log.warning(
|
||||
`Failed to revoke installation token: ${error42 instanceof Error ? error42.message : String(error42)}`
|
||||
@@ -89960,7 +89960,7 @@ async function installFromNpmTarball({
|
||||
let resolvedVersion = version3;
|
||||
if (version3.startsWith("^") || version3.startsWith("~") || version3 === "latest") {
|
||||
const npmRegistry2 = process.env.NPM_REGISTRY || "https://registry.npmjs.org";
|
||||
log.info(`Resolving version for ${version3}...`);
|
||||
log.debug(`\xBB resolving version for ${version3}...`);
|
||||
try {
|
||||
const registryResponse = await fetch(`${npmRegistry2}/${packageName}`);
|
||||
if (!registryResponse.ok) {
|
||||
@@ -89968,7 +89968,7 @@ async function installFromNpmTarball({
|
||||
}
|
||||
const registryData = await registryResponse.json();
|
||||
resolvedVersion = registryData["dist-tags"].latest;
|
||||
log.info(`Resolved to version ${resolvedVersion}`);
|
||||
log.debug(`\xBB resolved to version ${resolvedVersion}`);
|
||||
} catch (error42) {
|
||||
log.warning(
|
||||
`Failed to resolve version from registry: ${error42 instanceof Error ? error42.message : String(error42)}`
|
||||
@@ -89976,7 +89976,7 @@ async function installFromNpmTarball({
|
||||
throw error42;
|
||||
}
|
||||
}
|
||||
log.info(`\u{1F4E6} Installing ${packageName}@${resolvedVersion}...`);
|
||||
log.debug(`\xBB installing ${packageName}@${resolvedVersion}...`);
|
||||
const tempDir = process.env.PULLFROG_TEMP_DIR;
|
||||
const tarballPath = join4(tempDir, "package.tgz");
|
||||
const npmRegistry = process.env.NPM_REGISTRY || "https://registry.npmjs.org";
|
||||
@@ -89988,7 +89988,7 @@ async function installFromNpmTarball({
|
||||
} else {
|
||||
tarballUrl = `${npmRegistry}/${packageName}/-/${packageName}-${resolvedVersion}.tgz`;
|
||||
}
|
||||
log.info(`Downloading from ${tarballUrl}...`);
|
||||
log.debug(`\xBB downloading from ${tarballUrl}...`);
|
||||
const response = await fetch(tarballUrl);
|
||||
if (!response.ok) {
|
||||
throw new Error(`Failed to download tarball: ${response.status} ${response.statusText}`);
|
||||
@@ -89996,8 +89996,8 @@ async function installFromNpmTarball({
|
||||
if (!response.body) throw new Error("Response body is null");
|
||||
const fileStream = createWriteStream2(tarballPath);
|
||||
await pipeline(response.body, fileStream);
|
||||
log.info(`Downloaded tarball to ${tarballPath}`);
|
||||
log.info(`Extracting tarball...`);
|
||||
log.debug(`\xBB downloaded tarball to ${tarballPath}`);
|
||||
log.debug(`\xBB extracting tarball...`);
|
||||
const extractResult = spawnSync("tar", ["-xzf", tarballPath, "-C", tempDir], {
|
||||
stdio: "pipe",
|
||||
encoding: "utf-8"
|
||||
@@ -90013,7 +90013,7 @@ async function installFromNpmTarball({
|
||||
throw new Error(`Executable not found in extracted package at ${cliPath}`);
|
||||
}
|
||||
if (installDependencies) {
|
||||
log.info(`Installing dependencies for ${packageName}...`);
|
||||
log.debug(`\xBB installing dependencies for ${packageName}...`);
|
||||
const installResult = spawnSync("npm", ["install", "--production"], {
|
||||
cwd: extractedDir,
|
||||
stdio: "pipe",
|
||||
@@ -90024,10 +90024,10 @@ async function installFromNpmTarball({
|
||||
`Failed to install dependencies: ${installResult.stderr || installResult.stdout || "Unknown error"}`
|
||||
);
|
||||
}
|
||||
log.info(`\u2713 Dependencies installed`);
|
||||
log.debug(`\xBB dependencies installed`);
|
||||
}
|
||||
chmodSync(cliPath, 493);
|
||||
log.info(`\u2713 ${packageName} installed at ${cliPath}`);
|
||||
log.debug(`\xBB ${packageName} installed at ${cliPath}`);
|
||||
return cliPath;
|
||||
}
|
||||
async function fetchWithRetry(url2, headers, errorMessage) {
|
||||
@@ -95104,7 +95104,7 @@ function buildPullfrogFooter(params) {
|
||||
if (params.workflowRun) {
|
||||
const baseUrl = `https://github.com/${params.workflowRun.owner}/${params.workflowRun.repo}/actions/runs/${params.workflowRun.runId}`;
|
||||
const url2 = params.workflowRun.jobId ? `${baseUrl}/job/${params.workflowRun.jobId}` : baseUrl;
|
||||
parts.push(`[View workflow run](${url2})`);
|
||||
parts.push(`[workflow run](${url2})`);
|
||||
}
|
||||
const allParts = [
|
||||
...parts,
|
||||
@@ -125578,26 +125578,26 @@ var installPythonDependencies = {
|
||||
// prep/index.ts
|
||||
var prepSteps = [installNodeDependencies, installPythonDependencies];
|
||||
async function runPrepPhase() {
|
||||
log.info("\u{1F527} starting prep phase...");
|
||||
log.debug("\xBB starting prep phase...");
|
||||
const startTime = Date.now();
|
||||
const results = [];
|
||||
for (const step of prepSteps) {
|
||||
const shouldRun = await step.shouldRun();
|
||||
if (!shouldRun) {
|
||||
log.info(`\u23ED\uFE0F skipping ${step.name} (not applicable)`);
|
||||
log.debug(`\xBB skipping ${step.name} (not applicable)`);
|
||||
continue;
|
||||
}
|
||||
log.info(`\u25B6\uFE0F running ${step.name}...`);
|
||||
log.debug(`\xBB running ${step.name}...`);
|
||||
const result = await step.run();
|
||||
results.push(result);
|
||||
if (result.dependenciesInstalled) {
|
||||
log.info(`\u2705 ${step.name}: dependencies installed`);
|
||||
log.debug(`\xBB ${step.name}: dependencies installed`);
|
||||
} else if (result.issues.length > 0) {
|
||||
log.warning(`\u26A0\uFE0F ${step.name}: ${result.issues[0]}`);
|
||||
}
|
||||
}
|
||||
const totalDurationMs = Date.now() - startTime;
|
||||
log.info(`\u{1F527} prep phase completed (${totalDurationMs}ms)`);
|
||||
log.debug(`\xBB prep phase completed (${totalDurationMs}ms)`);
|
||||
return results;
|
||||
}
|
||||
|
||||
@@ -125654,7 +125654,7 @@ ${error42}` : `\u274C ${error42}`;
|
||||
import { execSync as execSync2 } from "node:child_process";
|
||||
function setupGitConfig() {
|
||||
const repoDir = process.cwd();
|
||||
log.info("\u{1F527} Setting up git configuration...");
|
||||
log.info("\xBB setting up git configuration...");
|
||||
try {
|
||||
execSync2('git config --local user.email "team@pullfrog.com"', {
|
||||
cwd: repoDir,
|
||||
@@ -125670,7 +125670,7 @@ function setupGitConfig() {
|
||||
stdio: "pipe"
|
||||
});
|
||||
}
|
||||
log.debug("setupGitConfig: \u2713 Git configuration set successfully (scoped to repo)");
|
||||
log.debug("\xBB git configuration set successfully (scoped to repo)");
|
||||
} catch (error42) {
|
||||
log.warning(
|
||||
`Failed to set git config: ${error42 instanceof Error ? error42.message : String(error42)}`
|
||||
@@ -125679,20 +125679,20 @@ function setupGitConfig() {
|
||||
}
|
||||
async function setupGit(ctx) {
|
||||
const repoDir = process.cwd();
|
||||
log.info("\u{1F527} setting up git authentication...");
|
||||
log.info("\xBB setting up git authentication...");
|
||||
try {
|
||||
execSync2("git config --local --unset-all http.https://github.com/.extraheader", {
|
||||
cwd: repoDir,
|
||||
stdio: "pipe"
|
||||
});
|
||||
log.info("\u2713 removed existing authentication headers");
|
||||
log.info("\xBB removed existing authentication headers");
|
||||
} catch {
|
||||
log.debug("no existing authentication headers to remove");
|
||||
log.debug("\xBB no existing authentication headers to remove");
|
||||
}
|
||||
if (ctx.payload.event.is_pr !== true || !ctx.payload.event.issue_number) {
|
||||
const originUrl2 = `https://x-access-token:${ctx.githubInstallationToken}@github.com/${ctx.owner}/${ctx.name}.git`;
|
||||
$("git", ["remote", "set-url", "origin", originUrl2], { cwd: repoDir });
|
||||
log.info("\u2713 Updated origin URL with authentication token");
|
||||
log.info("\xBB updated origin URL with authentication token");
|
||||
return;
|
||||
}
|
||||
const prNumber = ctx.payload.event.issue_number;
|
||||
@@ -125711,7 +125711,7 @@ var Timer = class {
|
||||
checkpoint(name) {
|
||||
const now = Date.now();
|
||||
const duration4 = this.lastCheckpointTimestamp ? now - this.lastCheckpointTimestamp : now - this.initialTimestamp;
|
||||
log.info(`${name}: ${duration4}ms`);
|
||||
log.debug(`\xBB ${name}: ${duration4}ms`);
|
||||
this.lastCheckpointTimestamp = now;
|
||||
}
|
||||
};
|
||||
@@ -125731,24 +125731,6 @@ var Inputs = type({
|
||||
async function main(inputs) {
|
||||
let mcpServerClose;
|
||||
let payload;
|
||||
log.info(
|
||||
JSON.stringify(
|
||||
{
|
||||
log_level: process.env.LOG_LEVEL,
|
||||
home: process.env.HOME,
|
||||
xdg_config_home: process.env.XDG_CONFIG_HOME,
|
||||
path: process.env.PATH,
|
||||
node_env: process.env.NODE_ENV,
|
||||
github_token: process.env.GITHUB_TOKEN,
|
||||
github_event_name: process.env.GITHUB_EVENT_NAME,
|
||||
github_ref: process.env.GITHUB_REF,
|
||||
github_sha: process.env.GITHUB_SHA,
|
||||
github_actor: process.env.GITHUB_ACTOR
|
||||
},
|
||||
null,
|
||||
2
|
||||
)
|
||||
);
|
||||
try {
|
||||
const timer = new Timer();
|
||||
payload = parsePayload(inputs);
|
||||
@@ -125915,7 +125897,7 @@ function resolveAgent({
|
||||
}
|
||||
const isExplicitOverride = agentOverride !== void 0 || payload.agent !== null;
|
||||
if (isExplicitOverride) {
|
||||
log.info(`Selected configured agent: ${agentName2}`);
|
||||
log.info(`\xBB selected configured agent: ${agentName2}`);
|
||||
return { agentName: agentName2, agent: agent3 };
|
||||
}
|
||||
const hasMatchingKey = agent3.name === "opencode" ? Object.keys(inputs).some((key) => key.includes("api_key")) : agent3.apiKeyNames.some((inputKey) => inputs[inputKey]);
|
||||
@@ -125924,25 +125906,25 @@ function resolveAgent({
|
||||
`Repo default agent ${agentName2} has no matching API keys. Available agents: ${getAvailableAgents(inputs).map((a) => a.name).join(", ") || "none"}`
|
||||
);
|
||||
} else {
|
||||
log.info(`Selected configured agent: ${agentName2}`);
|
||||
log.info(`\xBB selected configured agent: ${agentName2}`);
|
||||
return { agentName: agentName2, agent: agent3 };
|
||||
}
|
||||
}
|
||||
const availableAgents = getAvailableAgents(inputs);
|
||||
const availableAgentNames = availableAgents.map((agent3) => agent3.name).join(", ");
|
||||
log.debug(`Available agents: ${availableAgentNames || "none"}`);
|
||||
log.debug(`\xBB available agents: ${availableAgentNames || "none"}`);
|
||||
if (availableAgents.length === 0) {
|
||||
throw new Error("no agents available - missing API keys");
|
||||
}
|
||||
const agentName = availableAgents[0].name;
|
||||
const agent2 = availableAgents[0];
|
||||
log.info(`No agent configured, defaulting to first available agent: ${agentName}`);
|
||||
log.info(`\xBB no agent configured, defaulting to first available agent: ${agentName}`);
|
||||
return { agentName, agent: agent2 };
|
||||
}
|
||||
async function setupTempDirectory(ctx) {
|
||||
ctx.sharedTempDir = await mkdtemp2(join11(tmpdir2(), "pullfrog-"));
|
||||
process.env.PULLFROG_TEMP_DIR = ctx.sharedTempDir;
|
||||
log.info(`\u{1F4C2} PULLFROG_TEMP_DIR has been created at ${ctx.sharedTempDir}`);
|
||||
log.debug(`\xBB created temp dir at ${ctx.sharedTempDir}`);
|
||||
}
|
||||
function parsePayload(inputs) {
|
||||
try {
|
||||
@@ -125970,7 +125952,7 @@ async function startMcpServer(ctx) {
|
||||
const workflowRunInfo = await fetchWorkflowRunInfo(ctx.runId);
|
||||
if (workflowRunInfo.progressCommentId) {
|
||||
process.env.PULLFROG_PROGRESS_COMMENT_ID = workflowRunInfo.progressCommentId;
|
||||
log.info(`\u{1F4DD} Using pre-created progress comment: ${workflowRunInfo.progressCommentId}`);
|
||||
log.info(`\xBB using pre-created progress comment: ${workflowRunInfo.progressCommentId}`);
|
||||
}
|
||||
}
|
||||
const jobName = process.env.GITHUB_JOB;
|
||||
@@ -125983,17 +125965,17 @@ async function startMcpServer(ctx) {
|
||||
const matchingJob = jobs.data.jobs.find((job) => job.name === jobName);
|
||||
if (matchingJob) {
|
||||
ctx.jobId = String(matchingJob.id);
|
||||
log.info(`\u{1F4CB} Found job ID: ${ctx.jobId}`);
|
||||
log.info(`\xBB found job ID: ${ctx.jobId}`);
|
||||
}
|
||||
}
|
||||
const { url: url2, close } = await startMcpHttpServer(ctx);
|
||||
ctx.mcpServerUrl = url2;
|
||||
ctx.mcpServerClose = close;
|
||||
log.info(`\u{1F680} MCP server started at ${url2}`);
|
||||
log.info(`\xBB MCP server started at ${url2}`);
|
||||
}
|
||||
function setupMcpServers(ctx) {
|
||||
ctx.mcpServers = createMcpConfigs(ctx.mcpServerUrl);
|
||||
log.debug(`\u{1F4CB} MCP Config: ${JSON.stringify(ctx.mcpServers, null, 2)}`);
|
||||
log.debug(`\xBB MCP config: ${JSON.stringify(ctx.mcpServers, null, 2)}`);
|
||||
}
|
||||
async function installAgentCli(ctx) {
|
||||
if (ctx.agentName === "gemini") {
|
||||
@@ -126026,7 +126008,7 @@ async function validateApiKey(ctx) {
|
||||
ctx.apiKeys = apiKeys;
|
||||
}
|
||||
async function runAgent(ctx) {
|
||||
log.info(`Running ${ctx.agentName}...`);
|
||||
log.info(`\xBB running ${ctx.agentName}...`);
|
||||
const { context: _context, ...eventWithoutContext } = ctx.payload.event;
|
||||
const promptContent = `${ctx.payload.prompt}
|
||||
|
||||
|
||||
@@ -55,25 +55,6 @@ export async function main(inputs: Inputs): Promise<MainResult> {
|
||||
let mcpServerClose: (() => Promise<void>) | undefined;
|
||||
let payload: Payload | undefined;
|
||||
|
||||
log.info(
|
||||
JSON.stringify(
|
||||
{
|
||||
log_level: process.env.LOG_LEVEL,
|
||||
home: process.env.HOME,
|
||||
xdg_config_home: process.env.XDG_CONFIG_HOME,
|
||||
path: process.env.PATH,
|
||||
node_env: process.env.NODE_ENV,
|
||||
github_token: process.env.GITHUB_TOKEN,
|
||||
github_event_name: process.env.GITHUB_EVENT_NAME,
|
||||
github_ref: process.env.GITHUB_REF,
|
||||
github_sha: process.env.GITHUB_SHA,
|
||||
github_actor: process.env.GITHUB_ACTOR,
|
||||
},
|
||||
null,
|
||||
2
|
||||
)
|
||||
);
|
||||
|
||||
try {
|
||||
const timer = new Timer();
|
||||
|
||||
@@ -377,7 +358,7 @@ function resolveAgent({
|
||||
const isExplicitOverride = agentOverride !== undefined || payload.agent !== null;
|
||||
|
||||
if (isExplicitOverride) {
|
||||
log.info(`Selected configured agent: ${agentName}`);
|
||||
log.info(`» selected configured agent: ${agentName}`);
|
||||
return { agentName, agent };
|
||||
}
|
||||
|
||||
@@ -396,14 +377,14 @@ function resolveAgent({
|
||||
);
|
||||
// fall through to auto-selection for repo defaults
|
||||
} else {
|
||||
log.info(`Selected configured agent: ${agentName}`);
|
||||
log.info(`» selected configured agent: ${agentName}`);
|
||||
return { agentName, agent };
|
||||
}
|
||||
}
|
||||
|
||||
const availableAgents = getAvailableAgents(inputs);
|
||||
const availableAgentNames = availableAgents.map((agent) => agent.name).join(", ");
|
||||
log.debug(`Available agents: ${availableAgentNames || "none"}`);
|
||||
log.debug(`» available agents: ${availableAgentNames || "none"}`);
|
||||
|
||||
if (availableAgents.length === 0) {
|
||||
// this will be caught and reported later in validateApiKey
|
||||
@@ -412,14 +393,14 @@ function resolveAgent({
|
||||
|
||||
const agentName = availableAgents[0].name;
|
||||
const agent = availableAgents[0];
|
||||
log.info(`No agent configured, defaulting to first available agent: ${agentName}`);
|
||||
log.info(`» no agent configured, defaulting to first available agent: ${agentName}`);
|
||||
return { agentName, agent };
|
||||
}
|
||||
|
||||
async function setupTempDirectory(ctx: Context): Promise<void> {
|
||||
ctx.sharedTempDir = await mkdtemp(join(tmpdir(), "pullfrog-"));
|
||||
process.env.PULLFROG_TEMP_DIR = ctx.sharedTempDir;
|
||||
log.info(`📂 PULLFROG_TEMP_DIR has been created at ${ctx.sharedTempDir}`);
|
||||
log.debug(`» created temp dir at ${ctx.sharedTempDir}`);
|
||||
}
|
||||
|
||||
function parsePayload(inputs: Inputs): Payload {
|
||||
@@ -452,7 +433,7 @@ async function startMcpServer(ctx: Context): Promise<void> {
|
||||
const workflowRunInfo = await fetchWorkflowRunInfo(ctx.runId);
|
||||
if (workflowRunInfo.progressCommentId) {
|
||||
process.env.PULLFROG_PROGRESS_COMMENT_ID = workflowRunInfo.progressCommentId;
|
||||
log.info(`📝 Using pre-created progress comment: ${workflowRunInfo.progressCommentId}`);
|
||||
log.info(`» using pre-created progress comment: ${workflowRunInfo.progressCommentId}`);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -467,19 +448,19 @@ async function startMcpServer(ctx: Context): Promise<void> {
|
||||
const matchingJob = jobs.data.jobs.find((job) => job.name === jobName);
|
||||
if (matchingJob) {
|
||||
ctx.jobId = String(matchingJob.id);
|
||||
log.info(`📋 Found job ID: ${ctx.jobId}`);
|
||||
log.info(`» found job ID: ${ctx.jobId}`);
|
||||
}
|
||||
}
|
||||
|
||||
const { url, close } = await startMcpHttpServer(ctx);
|
||||
ctx.mcpServerUrl = url;
|
||||
ctx.mcpServerClose = close;
|
||||
log.info(`🚀 MCP server started at ${url}`);
|
||||
log.info(`» MCP server started at ${url}`);
|
||||
}
|
||||
|
||||
function setupMcpServers(ctx: Context): void {
|
||||
ctx.mcpServers = createMcpConfigs(ctx.mcpServerUrl);
|
||||
log.debug(`📋 MCP Config: ${JSON.stringify(ctx.mcpServers, null, 2)}`);
|
||||
log.debug(`» MCP config: ${JSON.stringify(ctx.mcpServers, null, 2)}`);
|
||||
}
|
||||
|
||||
async function installAgentCli(ctx: Context): Promise<void> {
|
||||
@@ -524,7 +505,7 @@ async function validateApiKey(ctx: Context): Promise<void> {
|
||||
}
|
||||
|
||||
async function runAgent(ctx: Context): Promise<AgentResult> {
|
||||
log.info(`Running ${ctx.agentName}...`);
|
||||
log.info(`» running ${ctx.agentName}...`);
|
||||
// strip context from event
|
||||
const { context: _context, ...eventWithoutContext } = ctx.payload.event;
|
||||
// format: prompt + two newlines + TOON encoded event
|
||||
|
||||
+5
-5
@@ -13,30 +13,30 @@ const prepSteps: PrepDefinition[] = [installNodeDependencies, installPythonDepen
|
||||
* failures are logged as warnings but don't stop the run.
|
||||
*/
|
||||
export async function runPrepPhase(): Promise<PrepResult[]> {
|
||||
log.info("🔧 starting prep phase...");
|
||||
log.debug("» starting prep phase...");
|
||||
const startTime = Date.now();
|
||||
const results: PrepResult[] = [];
|
||||
|
||||
for (const step of prepSteps) {
|
||||
const shouldRun = await step.shouldRun();
|
||||
if (!shouldRun) {
|
||||
log.info(`⏭️ skipping ${step.name} (not applicable)`);
|
||||
log.debug(`» skipping ${step.name} (not applicable)`);
|
||||
continue;
|
||||
}
|
||||
|
||||
log.info(`▶️ running ${step.name}...`);
|
||||
log.debug(`» running ${step.name}...`);
|
||||
const result = await step.run();
|
||||
results.push(result);
|
||||
|
||||
if (result.dependenciesInstalled) {
|
||||
log.info(`✅ ${step.name}: dependencies installed`);
|
||||
log.debug(`» ${step.name}: dependencies installed`);
|
||||
} else if (result.issues.length > 0) {
|
||||
log.warning(`⚠️ ${step.name}: ${result.issues[0]}`);
|
||||
}
|
||||
}
|
||||
|
||||
const totalDurationMs = Date.now() - startTime;
|
||||
log.info(`🔧 prep phase completed (${totalDurationMs}ms)`);
|
||||
log.debug(`» prep phase completed (${totalDurationMs}ms)`);
|
||||
|
||||
return results;
|
||||
}
|
||||
|
||||
@@ -48,7 +48,7 @@ export function buildPullfrogFooter(params: BuildPullfrogFooterParams): string {
|
||||
if (params.workflowRun) {
|
||||
const baseUrl = `https://github.com/${params.workflowRun.owner}/${params.workflowRun.repo}/actions/runs/${params.workflowRun.runId}`;
|
||||
const url = params.workflowRun.jobId ? `${baseUrl}/job/${params.workflowRun.jobId}` : baseUrl;
|
||||
parts.push(`[View workflow run](${url})`);
|
||||
parts.push(`[workflow run](${url})`);
|
||||
}
|
||||
|
||||
const allParts = [
|
||||
|
||||
+5
-5
@@ -48,14 +48,14 @@ function isGitHubActionsEnvironment(): boolean {
|
||||
}
|
||||
|
||||
async function acquireTokenViaOIDC(): Promise<string> {
|
||||
log.info("Generating OIDC token...");
|
||||
log.debug("» generating OIDC token...");
|
||||
|
||||
const oidcToken = await core.getIDToken("pullfrog-api");
|
||||
log.info("OIDC token generated successfully");
|
||||
log.debug("» OIDC token generated successfully");
|
||||
|
||||
const apiUrl = process.env.API_URL || "https://pullfrog.com";
|
||||
|
||||
log.info("Exchanging OIDC token for installation token...");
|
||||
log.debug("» exchanging OIDC token for installation token...");
|
||||
|
||||
// Add timeout to prevent long waits (5 seconds)
|
||||
const timeoutMs = 5000;
|
||||
@@ -79,7 +79,7 @@ async function acquireTokenViaOIDC(): Promise<string> {
|
||||
}
|
||||
|
||||
const tokenData = (await tokenResponse.json()) as InstallationToken;
|
||||
log.info(`Installation token obtained for ${tokenData.repository || "all repositories"}`);
|
||||
log.debug(`» installation token obtained for ${tokenData.repository || "all repositories"}`);
|
||||
|
||||
return tokenData.token;
|
||||
} catch (error) {
|
||||
@@ -283,7 +283,7 @@ export async function revokeGitHubInstallationToken(): Promise<void> {
|
||||
"X-GitHub-Api-Version": "2022-11-28",
|
||||
},
|
||||
});
|
||||
log.info("Installation token revoked");
|
||||
log.debug("» installation token revoked");
|
||||
} catch (error) {
|
||||
log.warning(
|
||||
`Failed to revoke installation token: ${error instanceof Error ? error.message : String(error)}`
|
||||
|
||||
+10
-10
@@ -18,20 +18,20 @@ export function setupTestRepo(options: SetupOptions): void {
|
||||
|
||||
if (existsSync(tempDir)) {
|
||||
if (forceClean) {
|
||||
log.info("🗑️ Removing existing .temp directory...");
|
||||
log.info("» removing existing .temp directory...");
|
||||
rmSync(tempDir, { recursive: true, force: true });
|
||||
|
||||
log.info("📦 Cloning pullfrog/scratch into .temp...");
|
||||
log.info("» cloning pullfrog/scratch into .temp...");
|
||||
$("git", ["clone", "git@github.com:pullfrog/scratch.git", tempDir]);
|
||||
} else {
|
||||
log.info("📦 Resetting existing .temp repository...");
|
||||
log.info("» resetting existing .temp repository...");
|
||||
execSync("git reset --hard HEAD && git clean -fd", {
|
||||
cwd: tempDir,
|
||||
stdio: "inherit",
|
||||
});
|
||||
}
|
||||
} else {
|
||||
log.info("📦 Cloning pullfrog/scratch into .temp...");
|
||||
log.info("» cloning pullfrog/scratch into .temp...");
|
||||
$("git", ["clone", "git@github.com:pullfrog/scratch.git", tempDir]);
|
||||
}
|
||||
}
|
||||
@@ -42,7 +42,7 @@ export function setupTestRepo(options: SetupOptions): void {
|
||||
*/
|
||||
export function setupGitConfig(): void {
|
||||
const repoDir = process.cwd();
|
||||
log.info("🔧 Setting up git configuration...");
|
||||
log.info("» setting up git configuration...");
|
||||
try {
|
||||
// Use --local to scope config to this repo only, preventing leakage to user's global config
|
||||
execSync('git config --local user.email "team@pullfrog.com"', {
|
||||
@@ -61,7 +61,7 @@ export function setupGitConfig(): void {
|
||||
stdio: "pipe",
|
||||
});
|
||||
}
|
||||
log.debug("setupGitConfig: ✓ Git configuration set successfully (scoped to repo)");
|
||||
log.debug("» git configuration set successfully (scoped to repo)");
|
||||
} catch (error) {
|
||||
// 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
|
||||
@@ -83,7 +83,7 @@ export function setupGitConfig(): void {
|
||||
export async function setupGit(ctx: Context): Promise<void> {
|
||||
const repoDir = process.cwd();
|
||||
|
||||
log.info("🔧 setting up git authentication...");
|
||||
log.info("» setting up git authentication...");
|
||||
|
||||
// remove existing git auth headers that actions/checkout might have set
|
||||
try {
|
||||
@@ -91,16 +91,16 @@ export async function setupGit(ctx: Context): Promise<void> {
|
||||
cwd: repoDir,
|
||||
stdio: "pipe",
|
||||
});
|
||||
log.info("✓ removed existing authentication headers");
|
||||
log.info("» removed existing authentication headers");
|
||||
} catch {
|
||||
log.debug("no existing authentication headers to remove");
|
||||
log.debug("» no existing authentication headers to remove");
|
||||
}
|
||||
|
||||
// non-PR events: set up origin with token, stay on default branch
|
||||
if (ctx.payload.event.is_pr !== true || !ctx.payload.event.issue_number) {
|
||||
const originUrl = `https://x-access-token:${ctx.githubInstallationToken}@github.com/${ctx.owner}/${ctx.name}.git`;
|
||||
$("git", ["remote", "set-url", "origin", originUrl], { cwd: repoDir });
|
||||
log.info("✓ Updated origin URL with authentication token");
|
||||
log.info("» updated origin URL with authentication token");
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
+1
-1
@@ -14,7 +14,7 @@ export class Timer {
|
||||
? now - this.lastCheckpointTimestamp
|
||||
: now - this.initialTimestamp;
|
||||
|
||||
log.info(`${name}: ${duration}ms`);
|
||||
log.debug(`» ${name}: ${duration}ms`);
|
||||
this.lastCheckpointTimestamp = now;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user