import path from 'node:path'; import { z } from 'zod'; import { config } from '../../config.js'; import { vendorBinExists } from '../../lib/frameworks/composer.js'; import { runCommand } from '../../lib/runCommand.js'; import { errorResult, jsonResult, toErrorMessage } from '../shared.js'; import { requireCodeIgniter } from './requireCodeIgniter.js'; function vendorBin(root, bin) { const suffix = process.platform === 'win32' ? '.bat' : ''; return path.join(root, 'vendor', 'bin', `${bin}${suffix}`); } function parsePhpUnitSummary(output) { const ok = output.match(/OK\s*\((\d+)\s+tests?,\s*(\d+)\s+assertions?\)/i); if (ok) { return { passed: true, tests: Number(ok[1]), assertions: Number(ok[2]), failures: 0, errors: 0 }; } const summary = output.match(/Tests:\s*(\d+),\s*Assertions:\s*(\d+)(?:,\s*Errors:\s*(\d+))?(?:,\s*Failures:\s*(\d+))?(?:,\s*Skipped:\s*(\d+))?/i); if (summary) { return { passed: !/FAILURES!|ERRORS!/i.test(output), tests: Number(summary[1]), assertions: Number(summary[2]), errors: Number(summary[3] ?? 0), failures: Number(summary[4] ?? 0), skipped: Number(summary[5] ?? 0), }; } return { passed: null, note: 'Could not parse a pass/fail summary from the runner output.' }; } export function registerCodeIgniterTestTool(server) { server.registerTool('run_codeigniter_tests', { title: 'Run CodeIgniter Tests', description: "Run the CodeIgniter 4 project's PHPUnit-based test suite (CIUnitTestCase) via vendor/bin/phpunit, " + 'or `php spark test` as a fallback. Returns parsed pass/fail counts when possible.', inputSchema: { extraArgs: z .array(z.string()) .optional() .describe('Extra CLI args, e.g. ["--filter", "UserTest"].'), }, }, async ({ extraArgs }) => { try { const ci = requireCodeIgniter(); const args = extraArgs ?? []; let command; let cmdArgs; if (vendorBinExists(ci.root, 'phpunit')) { command = vendorBin(ci.root, 'phpunit'); cmdArgs = args; } else if (vendorBinExists(ci.root, 'spark')) { // CI4 does not ship a built-in `spark test` command out of the box, // but projects sometimes add one. If phpunit is missing, try it. command = 'php'; cmdArgs = ['spark', 'test', ...args]; } else { return errorResult(`No vendor/bin/phpunit found at ${ci.root}. Run composer install (or run_install) first.`); } const result = await runCommand(command, cmdArgs, { cwd: ci.root, timeoutMs: config.scaffoldCommandTimeoutMs, }); return jsonResult({ runner: 'phpunit', summary: parsePhpUnitSummary(result.output), ...result }); } catch (error) { return errorResult(toErrorMessage(error)); } }); } //# sourceMappingURL=runCodeIgniterTests.js.map