diff --git a/__tests__/github/summary.test.ts b/__tests__/github/summary.test.ts new file mode 100644 index 00000000..62bd1e2b --- /dev/null +++ b/__tests__/github/summary.test.ts @@ -0,0 +1,58 @@ +/** + * Copyright 2026 actions-toolkit authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import {afterEach, describe, expect, test, vi} from 'vitest'; +import * as core from '@actions/core'; + +import {GitHubSummary} from '../../src/github/summary.js'; + +afterEach(() => { + core.summary.emptyBuffer(); + vi.restoreAllMocks(); +}); + +describe('writeBuildSummary', () => { + test.each([1, 11])('escapes a build error with %i lines', async lines => { + const error = Array(lines).fill('unknown instruction: & value').join('\n'); + const encodedError = Array(lines).fill('unknown instruction: <tag> & value').join('\n'); + const write = vi.spyOn(core.summary, 'write').mockResolvedValue(core.summary); + + await GitHubSummary.writeBuildSummary({ + exportRes: { + dockerbuildFilename: 'build.dockerbuild', + dockerbuildSize: 0, + builderName: 'builder', + nodeName: 'node', + refs: ['buildref'], + summaries: { + buildref: { + name: 'build', + status: 'failed', + duration: '1s', + numCachedSteps: 0, + numTotalSteps: 1, + numCompletedSteps: 0, + error + } + } + } + }); + + expect(write).toHaveBeenCalledOnce(); + expect(core.summary.stringify()).toContain(`
${encodedError}
`); + expect(core.summary.stringify().includes('
Error')).toBe(lines > 10); + }); +}); diff --git a/package.json b/package.json index 272b67ac..bc62f3e3 100644 --- a/package.json +++ b/package.json @@ -57,7 +57,7 @@ "csv-parse": "^7.0.3", "gunzip-maybe": "^1.4.2", "handlebars": "^4.7.10", - "he": "^1.2.0", + "he": "^2.0.0", "js-yaml": "^5.4.3", "jwt-decode": "^4.0.0", "semver": "^7.8.5", diff --git a/src/github/summary.ts b/src/github/summary.ts index 9da84419..ac4e453f 100644 --- a/src/github/summary.ts +++ b/src/github/summary.ts @@ -14,7 +14,7 @@ * limitations under the License. */ -import he from 'he'; +import * as he from 'he'; import {dump as yamldump} from 'js-yaml'; import os from 'os'; import * as core from '@actions/core'; diff --git a/yarn.lock b/yarn.lock index b1a98b83..e0ff11a3 100644 --- a/yarn.lock +++ b/yarn.lock @@ -502,7 +502,7 @@ __metadata: globals: "npm:^17.3.0" gunzip-maybe: "npm:^1.4.2" handlebars: "npm:^4.7.10" - he: "npm:^1.2.0" + he: "npm:^2.0.0" js-yaml: "npm:^5.4.3" jwt-decode: "npm:^4.0.0" prettier: "npm:^3.8.1" @@ -3138,12 +3138,12 @@ __metadata: languageName: node linkType: hard -"he@npm:^1.2.0": - version: 1.2.0 - resolution: "he@npm:1.2.0" +"he@npm:^2.0.0": + version: 2.0.0 + resolution: "he@npm:2.0.0" bin: - he: bin/he - checksum: 10/d09b2243da4e23f53336e8de3093e5c43d2c39f8d0d18817abfa32ce3e9355391b2edb4bb5edc376aea5d4b0b59d6a0482aab4c52bc02ef95751e4b818e847f1 + he: bin/he.mjs + checksum: 10/f554704a474bf74e169f7420ec23d4c21dadfdc5b0d88e8de35d24b6610bb177fb189bd6dfc10caae35edac0df2e79c8778a90d59ae3718a50b00f3bdd544999 languageName: node linkType: hard