From 62ab0e33a2988989c67b9b7e429874d4cbc0473f Mon Sep 17 00:00:00 2001 From: Jimmy Lai Date: Thu, 12 Oct 2023 15:57:09 +0200 Subject: [PATCH] ci: add job summary to the test suite runs (#56742) This PR adds Github Actions summaries to the test suite that runs in the CI so that you can easily visualise which tests failed + what the relevant log was instead of parsing the logs yourself. Example here https://github.com/vercel/next.js/actions/runs/6495658699 ![CleanShot 2023-10-12 at 14 57 32@2x](https://github.com/vercel/next.js/assets/11064311/7d65496b-6e28-460a-8bef-3f2e91266d00) --- package.json | 1 + pnpm-lock.yaml | 34 +++++++++++++++++++++++++++++++++ run-tests.js | 51 ++++++++++++++++++++++++++++++++++++++++++++++++++ 3 files changed, 86 insertions(+) diff --git a/package.json b/package.json index 6d854c552f15d..1ffad6d76e11e 100644 --- a/package.json +++ b/package.json @@ -58,6 +58,7 @@ "update-google-fonts": "node ./scripts/update-google-fonts.js" }, "devDependencies": { + "@actions/core": "1.10.1", "@babel/core": "7.18.0", "@babel/eslint-parser": "7.18.2", "@babel/generator": "7.18.0", diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index 6db612a66bd21..53fa9069b9ea1 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -20,6 +20,9 @@ importers: .: devDependencies: + '@actions/core': + specifier: 1.10.1 + version: 1.10.1 '@babel/core': specifier: 7.18.0 version: 7.18.0 @@ -1594,6 +1597,20 @@ importers: packages: + /@actions/core@1.10.1: + resolution: {integrity: sha512-3lBR9EDAY+iYIpTnTIXmWcNbX3T2kCkAEQGIQx4NVQ0575nk2k3GRZDTPQG+vVtS2izSLmINlxXf0uLtnrTP+g==} + dependencies: + '@actions/http-client': 2.2.0 + uuid: 8.3.2 + dev: true + + /@actions/http-client@2.2.0: + resolution: {integrity: sha512-q+epW0trjVUUHboliPb4UF9g2msf+w61b32tAkFEwL/IwP0DQWgbCMM0Hbe3e3WXSKz5VcUXbzJQgy8Hkra/Lg==} + dependencies: + tunnel: 0.0.6 + undici: 5.26.3 + dev: true + /@adobe/css-tools@4.3.1: resolution: {integrity: sha512-/62yikz7NLScCGAAST5SHdnjaDJQBDq0M2muyRTpf2VQhw6StBg2ALiu73zSJQ4fMVLA+0uBhBHAle7Wg+2kSg==} dev: true @@ -5225,6 +5242,11 @@ packages: - supports-color dev: false + /@fastify/busboy@2.0.0: + resolution: {integrity: sha512-JUFJad5lv7jxj926GPgymrWQxxjPYuJNiNjNMzqT+HiuP6Vl3dk5xzG+8sTX96np0ZAluvaMzPsjhHZ5rNuNQQ==} + engines: {node: '>=14'} + dev: true + /@firebase/analytics-types@0.3.1: resolution: {integrity: sha512-63vVJ5NIBh/JF8l9LuPrQYSzFimk7zYHySQB4Dk9rVdJ8kV/vGQoVTvRu1UW05sEc2Ug5PqtEChtTHU+9hvPcA==} dev: true @@ -25341,6 +25363,11 @@ packages: safe-buffer: 5.2.1 dev: true + /tunnel@0.0.6: + resolution: {integrity: sha512-1h/Lnq9yajKY2PEbBadPXj3VxsDDu844OnaAo52UVmIzIvwwtBPIuNvkjuzBlTWpfJyUbG3ez0KSBibQkj4ojg==} + engines: {node: '>=0.6.11 <=0.7.0 || >=0.7.3'} + dev: true + /turbo-darwin-64@1.10.9: resolution: {integrity: sha512-Avz3wsYYb8/vjyHPVRFbNbowIiaF33vcBRklIUkPchTLvZekrT5x3ltQBCflyoi2zJV9g08hK4xXTGuCxeVvPA==} cpu: [x64] @@ -25583,6 +25610,13 @@ packages: busboy: 1.6.0 dev: true + /undici@5.26.3: + resolution: {integrity: sha512-H7n2zmKEWgOllKkIUkLvFmsJQj062lSm3uA4EYApG8gLuiOM0/go9bIoC3HVaSnfg4xunowDE2i9p8drkXuvDw==} + engines: {node: '>=14.0'} + dependencies: + '@fastify/busboy': 2.0.0 + dev: true + /unfetch@4.2.0: resolution: {integrity: sha512-F9p7yYCn6cIW9El1zi0HI6vqpeIvBsr3dSuRO6Xuppb1u5rXpCPmMvLSyECLhybr9isec8Ohl0hPekMVrEinDA==} dev: true diff --git a/run-tests.js b/run-tests.js index b6178477b0691..23c73a83b2fc0 100644 --- a/run-tests.js +++ b/run-tests.js @@ -11,6 +11,7 @@ const { spawn, exec: execOrig } = require('child_process') const { createNextInstall } = require('./test/lib/create-next-install') const glob = promisify(_glob) const exec = promisify(execOrig) +const core = require('@actions/core') function escapeRegexp(str) { return str.replace(/[.*+?^${}()|[\]\\]/g, '\\$&') @@ -73,6 +74,45 @@ const mockTrace = () => ({ // which types we have configured to run separate const configuredTestTypes = Object.values(testFilters) +const errorsPerTests = new Map() + +async function maybeLogSummary() { + if (process.env.CI && errorsPerTests.size > 0) { + const outputTemplate = ` +${Array.from(errorsPerTests.entries()) + .map(([test, output]) => { + return ` +
+${test} + +\`\`\` +${output} +\`\`\` + +
+` + }) + .join('\n')}` + + await core.summary + .addHeading('Tests failures') + .addTable([ + [ + { + data: 'Test suite', + header: true, + }, + ], + ...Array.from(errorsPerTests.entries()).map(([test]) => { + return [ + `${test}`, + ] + }), + ]) + .addRaw(outputTemplate) + .write() + } +} const cleanUpAndExit = async (code) => { if (process.env.NEXT_TEST_STARTER) { @@ -81,6 +121,9 @@ const cleanUpAndExit = async (code) => { if (process.env.NEXT_TEST_TEMP_REPO) { await fs.remove(process.env.NEXT_TEST_TEMP_REPO) } + if (process.env.CI) { + await maybeLogSummary() + } console.log(`exiting with code ${code}`) setTimeout(() => { @@ -472,11 +515,19 @@ ${ENDGROUP}`) } else { process.stdout.write(`${GROUP}❌ ${test.file} output\n`) } + + let output = '' // limit out to last 64kb so that we don't // run out of log room in CI for (const { chunk } of outputChunks) { process.stdout.write(chunk) + output += chunk.toString() } + + if (process.env.CI && !killed) { + errorsPerTests.set(test.file, output) + } + if (isExpanded) { process.stdout.write(`end of ${test.file} output\n`) } else {