export const AGENTS_CONTEXT_MESSAGE_TYPE = "pi-developer-messages/agents-md"; export const AGENTS_CONTEXT_MESSAGE_ID = "agents-md"; interface ContextFile { path: string; content: string; } interface AgentMessageLike { role?: string; customType?: string; } export interface AgentsContextMessage { role: "custom"; customType: typeof AGENTS_CONTEXT_MESSAGE_TYPE; content: string; display: false; timestamp: 0; } export function renderAgentsContext( contextFiles: readonly ContextFile[], cwd: string, agentDir = getAgentDir(), ): string | undefined { const files = contextFiles.filter((file) => file.content.trim().length > 0); if (files.length === 0) return undefined; const hasGlobalInstructions = resolve(dirname(files[0]!.path)) === resolve(agentDir); const codexBody = hasGlobalInstructions && files.length > 1 ? `${files[0]!.content}\n\n--- project-doc ---\n\n${files .slice(1) .map((file) => file.content) .join("\n\n")}` : files.map((file) => file.content).join("\n\n"); return `# AGENTS.md instructions for ${cwd.replaceAll("\\", "/")}\n\n\n${codexBody}\n`; } export function injectAgentsContext( messages: readonly T[], content: string | undefined, ): (T | AgentsContextMessage)[] | undefined { const filtered = messages.filter( (message) => message.role !== "custom" || message.customType !== AGENTS_CONTEXT_MESSAGE_TYPE, ); if (!content) return filtered.length === messages.length ? undefined : filtered; return [ { role: "custom", customType: AGENTS_CONTEXT_MESSAGE_TYPE, content, display: false, timestamp: 0, }, ...filtered, ]; } import { dirname, resolve } from "node:path"; import { getAgentDir } from "@earendil-works/pi-coding-agent";