Files
mcp_web_dev_server/dist/tools/react/runReactTests.js
T
2026-07-31 13:12:54 -04:00

67 lines
2.9 KiB
JavaScript

import { z } from 'zod';
import { config } from '../../config.js';
import { detectJsPackageManager, runScriptCommandFor } from '../../lib/frameworks/packageManager.js';
import { runCommand } from '../../lib/runCommand.js';
import { errorResult, jsonResult, toErrorMessage } from '../shared.js';
import { requireReact } from './requireReact.js';
function parseReactTestingLibraryOutput(output) {
// Extract failing test names and common RTL errors for a quick summary.
const failingTests = output
.split(/\n(?=\s*FAIL|●)/)
.filter((chunk) => chunk.includes('●'))
.map((chunk) => {
const match = chunk.match(/●\s*(.+?)(?:\n|$)/);
return match?.[1]?.trim() ?? null;
})
.filter((item) => Boolean(item));
const rtlErrors = [];
if (/Unable to find an element/i.test(output))
rtlErrors.push('Unable to find an element (getBy/queryBy failed)');
if (/Found multiple elements/i.test(output))
rtlErrors.push('Found multiple elements with the same query');
if (/found accessibility element/i.test(output))
rtlErrors.push('Role/name based query mismatch');
if (/Timed out in waitFor/i.test(output))
rtlErrors.push('waitFor timeout (async assertion not satisfied)');
if (/Warning: An update to .* inside a test was not wrapped in act/i.test(output)) {
rtlErrors.push('Missing act() wrapper around state update');
}
const totalMatch = output.match(/Tests\s+(\d+)\s+passed/i) || output.match(/Test Suites?:\s*(\d+)\s+passed/i);
return {
failingTestCount: failingTests.length,
failingTests: failingTests.slice(0, 10),
rtlErrors: rtlErrors.slice(0, 10),
testsPassed: totalMatch ? Number(totalMatch[1]) : null,
};
}
export function registerRunReactTestsTool(server) {
server.registerTool('run_react_tests', {
title: 'Run React Tests',
description: 'Run the React test runner (Jest/Vitest + React Testing Library) via package.json "test" script and surface RTL-specific failures.',
inputSchema: {
extraArgs: z
.array(z.string())
.optional()
.describe('Extra CLI args, e.g. ["--filter", "UserCard"].'),
},
}, async ({ extraArgs }) => {
try {
const react = requireReact();
const pm = detectJsPackageManager(react.root);
const { command, args } = runScriptCommandFor(pm, 'test', extraArgs ?? []);
const result = await runCommand(command, args, {
cwd: react.root,
timeoutMs: config.scaffoldCommandTimeoutMs,
});
return jsonResult({
runner: 'npm-test-script',
summary: parseReactTestingLibraryOutput(result.output),
...result,
});
}
catch (error) {
return errorResult(toErrorMessage(error));
}
});
}
//# sourceMappingURL=runReactTests.js.map