diff --git a/agents/opencode.ts b/agents/opencode.ts index eb242fc..292d52d 100644 --- a/agents/opencode.ts +++ b/agents/opencode.ts @@ -1,4 +1,4 @@ -import { mkdirSync, writeFileSync } from "node:fs"; +import { existsSync, mkdirSync, readFileSync, writeFileSync } from "node:fs"; import { join } from "node:path"; import { log } from "../utils/cli.ts"; @@ -42,9 +42,17 @@ export const opencode = agent({ // 6. set up environment setupProcessAgentEnv({ HOME: tempHome }); + // DEBUG: log original process.env values before building env + log.startGroup("🔍 DEBUG: Environment analysis"); + log.info(`Original process.env.HOME: ${process.env.HOME}`); + log.info(`Original process.env.XDG_CONFIG_HOME: ${process.env.XDG_CONFIG_HOME || "(not set)"}`); + log.info(`Target tempHome: ${tempHome}`); + // build env vars: start with process.env (includes all API_KEY vars loaded by config()) // exclude GITHUB_TOKEN - OpenCode should use MCP server for GitHub operations, not direct token - // then override with apiKeys and HOME + // then override with apiKeys, HOME, and XDG_CONFIG_HOME + // XDG_CONFIG_HOME must be set because GitHub Actions sets it to a different path, + // and OpenCode follows XDG spec (checks XDG_CONFIG_HOME before falling back to $HOME/.config) const env: Record = { ...(Object.fromEntries( Object.entries(process.env).filter( @@ -52,6 +60,7 @@ export const opencode = agent({ ) ) as Record), HOME: tempHome, + XDG_CONFIG_HOME: join(tempHome, ".config"), }; // add/override API keys from apiKeys object (uppercase keys) @@ -59,19 +68,52 @@ export const opencode = agent({ env[key.toUpperCase()] = value; } + // DEBUG: verify env overrides worked + log.info(`Final env.HOME: ${env.HOME}`); + log.info(`Final env.XDG_CONFIG_HOME: ${env.XDG_CONFIG_HOME}`); + + // DEBUG: verify config file exists and log its contents + const configPath = join(env.HOME!, ".config", "opencode", "opencode.json"); + const configExists = existsSync(configPath); + log.info(`Config path: ${configPath}`); + log.info(`Config file exists: ${configExists}`); + if (configExists) { + const configContents = readFileSync(configPath, "utf-8"); + log.info(`Config file contents:\n${configContents}`); + } + + // DEBUG: check for alternative config locations OpenCode might use + const altConfigPaths = [ + join(env.HOME!, ".opencode", "config.json"), + join(env.HOME!, ".opencode.json"), + join(process.cwd(), ".opencode.json"), + join(process.cwd(), ".opencode", "config.json"), + ]; + for (const altPath of altConfigPaths) { + if (existsSync(altPath)) { + log.info(`⚠️ Alternative config found at: ${altPath}`); + } + } + + // DEBUG: test MCP server connectivity + const mcpUrl = "http://127.0.0.1:3764/mcp"; + try { + const response = await fetch(mcpUrl, { method: "GET" }); + log.info(`MCP server reachable: ${response.ok} (status: ${response.status})`); + } catch (error) { + log.warning( + `MCP server NOT reachable: ${error instanceof Error ? error.message : String(error)}` + ); + } + + log.endGroup(); + // run OpenCode in the repository directory (process.cwd() is set to GITHUB_WORKSPACE or repo dir) const repoDir = process.cwd(); log.info(`🚀 Starting OpenCode CLI: ${cliPath} ${args.join(" ")}`); log.info(`📁 Working directory: ${repoDir}`); - log.info(`🏠 HOME env var: ${env.HOME}`); - log.info(`📋 Config directory: ${join(env.HOME!, ".config", "opencode")}`); - // log key env vars (not values for security) - const envKeys = Object.keys(env).filter( - (k) => !k.includes("KEY") && !k.includes("TOKEN") && !k.includes("SECRET") - ); - log.info(`🔑 Environment keys (non-sensitive): ${envKeys.join(", ")}`); const startTime = Date.now(); let lastActivityTime = startTime; let eventCount = 0; diff --git a/entry b/entry index 74c8a85..e7ad3cb 100755 --- a/entry +++ b/entry @@ -91248,7 +91248,7 @@ function configureGeminiMcpServers({ mcpServers, cliPath }) { } // agents/opencode.ts -import { mkdirSync as mkdirSync4, writeFileSync as writeFileSync3 } from "node:fs"; +import { existsSync as existsSync3, mkdirSync as mkdirSync4, readFileSync as readFileSync2, writeFileSync as writeFileSync3 } from "node:fs"; import { join as join7 } from "node:path"; var opencode = agent({ name: "opencode", @@ -91272,26 +91272,57 @@ var opencode = agent({ log.info("\u{1F512} sandbox mode enabled: restricting to read-only operations"); } setupProcessAgentEnv({ HOME: tempHome }); + log.startGroup("\u{1F50D} DEBUG: Environment analysis"); + log.info(`Original process.env.HOME: ${process.env.HOME}`); + log.info(`Original process.env.XDG_CONFIG_HOME: ${process.env.XDG_CONFIG_HOME || "(not set)"}`); + log.info(`Target tempHome: ${tempHome}`); const env3 = { ...Object.fromEntries( Object.entries(process.env).filter( ([key, value2]) => value2 !== void 0 && key !== "GITHUB_TOKEN" ) ), - HOME: tempHome + HOME: tempHome, + XDG_CONFIG_HOME: join7(tempHome, ".config") }; for (const [key, value2] of Object.entries(apiKeys || {})) { env3[key.toUpperCase()] = value2; } + log.info(`Final env.HOME: ${env3.HOME}`); + log.info(`Final env.XDG_CONFIG_HOME: ${env3.XDG_CONFIG_HOME}`); + const configPath = join7(env3.HOME, ".config", "opencode", "opencode.json"); + const configExists = existsSync3(configPath); + log.info(`Config path: ${configPath}`); + log.info(`Config file exists: ${configExists}`); + if (configExists) { + const configContents = readFileSync2(configPath, "utf-8"); + log.info(`Config file contents: +${configContents}`); + } + const altConfigPaths = [ + join7(env3.HOME, ".opencode", "config.json"), + join7(env3.HOME, ".opencode.json"), + join7(process.cwd(), ".opencode.json"), + join7(process.cwd(), ".opencode", "config.json") + ]; + for (const altPath of altConfigPaths) { + if (existsSync3(altPath)) { + log.info(`\u26A0\uFE0F Alternative config found at: ${altPath}`); + } + } + const mcpUrl = "http://127.0.0.1:3764/mcp"; + try { + const response = await fetch(mcpUrl, { method: "GET" }); + log.info(`MCP server reachable: ${response.ok} (status: ${response.status})`); + } catch (error42) { + log.warning( + `MCP server NOT reachable: ${error42 instanceof Error ? error42.message : String(error42)}` + ); + } + log.endGroup(); const repoDir = process.cwd(); log.info(`\u{1F680} Starting OpenCode CLI: ${cliPath} ${args3.join(" ")}`); log.info(`\u{1F4C1} Working directory: ${repoDir}`); - log.info(`\u{1F3E0} HOME env var: ${env3.HOME}`); - log.info(`\u{1F4CB} Config directory: ${join7(env3.HOME, ".config", "opencode")}`); - const envKeys = Object.keys(env3).filter( - (k) => !k.includes("KEY") && !k.includes("TOKEN") && !k.includes("SECRET") - ); - log.info(`\u{1F511} Environment keys (non-sensitive): ${envKeys.join(", ")}`); const startTime = Date.now(); let lastActivityTime = startTime; let eventCount = 0; @@ -125049,7 +125080,7 @@ async function startMcpHttpServer(ctx) { } // prep/installNodeDependencies.ts -import { existsSync as existsSync3 } from "node:fs"; +import { existsSync as existsSync4 } from "node:fs"; import { join as join9 } from "node:path"; // ../node_modules/.pnpm/package-manager-detector@1.6.0/node_modules/package-manager-detector/dist/commands.mjs @@ -125383,7 +125414,7 @@ var installNodeDependencies = { name: "installNodeDependencies", shouldRun: () => { const packageJsonPath = join9(process.cwd(), "package.json"); - return existsSync3(packageJsonPath); + return existsSync4(packageJsonPath); }, run: async () => { const detected = await detect({ cwd: process.cwd() }); @@ -125443,7 +125474,7 @@ var installNodeDependencies = { }; // prep/installPythonDependencies.ts -import { existsSync as existsSync4 } from "node:fs"; +import { existsSync as existsSync5 } from "node:fs"; import { join as join10 } from "node:path"; var PYTHON_CONFIGS = [ { @@ -125516,11 +125547,11 @@ var installPythonDependencies = { return false; } const cwd2 = process.cwd(); - return PYTHON_CONFIGS.some((config3) => existsSync4(join10(cwd2, config3.file))); + return PYTHON_CONFIGS.some((config3) => existsSync5(join10(cwd2, config3.file))); }, run: async () => { const cwd2 = process.cwd(); - const config3 = PYTHON_CONFIGS.find((c) => existsSync4(join10(cwd2, c.file))); + const config3 = PYTHON_CONFIGS.find((c) => existsSync5(join10(cwd2, c.file))); if (!config3) { return { language: "python", diff --git a/fixtures/basic.txt b/fixtures/basic.txt index dd6429e..d110ef1 100644 --- a/fixtures/basic.txt +++ b/fixtures/basic.txt @@ -1 +1 @@ -review this https://github.com/pullfrog/colinhacks/pull/5 \ No newline at end of file +inspect your MCP servers, log them all, and call a tool as a test \ No newline at end of file