Skip to content

Commit dee9732

Browse files
[test optimization] support TypeScript 6 in browser integration tests (#8137)
1 parent bb5fa49 commit dee9732

17 files changed

Lines changed: 227 additions & 52 deletions

integration-tests/cypress/cypress-atr.spec.js

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -94,10 +94,7 @@ moduleTypes.forEach(({
9494

9595
// cypress-fail-fast is required as an incompatible plugin.
9696
// typescript is required to compile .cy.ts spec files in the pre-compiled JS tests.
97-
// typescript@5 is pinned because typescript@6 emits "use strict" on line 1 for
98-
// non-module files, shifting compiled line numbers and breaking source map resolution.
99-
// TODO: Update tests files accordingly and test with different TS versions
100-
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript@5'], true)
97+
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript'], true)
10198

10299
before(async function () {
103100
// Note: Cypress binary is already installed during useSandbox() via the postinstall script

integration-tests/cypress/cypress-efd.spec.js

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -91,10 +91,7 @@ moduleTypes.forEach(({
9191

9292
// cypress-fail-fast is required as an incompatible plugin.
9393
// typescript is required to compile .cy.ts spec files in the pre-compiled JS tests.
94-
// typescript@5 is pinned because typescript@6 emits "use strict" on line 1 for
95-
// non-module files, shifting compiled line numbers and breaking source map resolution.
96-
// TODO: Update tests files accordingly and test with different TS versions
97-
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript@5'], true)
94+
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript'], true)
9895

9996
before(async function () {
10097
// Note: Cypress binary is already installed during useSandbox() via the postinstall script

integration-tests/cypress/cypress-final-status.spec.js

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -88,10 +88,7 @@ moduleTypes.forEach(({
8888

8989
// cypress-fail-fast is required as an incompatible plugin.
9090
// typescript is required to compile .cy.ts spec files in the pre-compiled JS tests.
91-
// typescript@5 is pinned because typescript@6 emits "use strict" on line 1 for
92-
// non-module files, shifting compiled line numbers and breaking source map resolution.
93-
// TODO: Update tests files accordingly and test with different TS versions
94-
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript@5'], true)
91+
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript'], true)
9592

9693
before(async function () {
9794
// Note: Cypress binary is already installed during useSandbox() via the postinstall script

integration-tests/cypress/cypress-impacted-tests.spec.js

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -102,10 +102,7 @@ moduleTypes.forEach(({
102102

103103
// cypress-fail-fast is required as an incompatible plugin.
104104
// typescript is required to compile .cy.ts spec files in the pre-compiled JS tests.
105-
// typescript@5 is pinned because typescript@6 emits "use strict" on line 1 for
106-
// non-module files, shifting compiled line numbers and breaking source map resolution.
107-
// TODO: Update tests files accordingly and test with different TS versions
108-
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript@5'], true)
105+
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript'], true)
109106

110107
before(async function () {
111108
// Note: Cypress binary is already installed during useSandbox() via the postinstall script

integration-tests/cypress/cypress-itr.spec.js

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -90,10 +90,7 @@ moduleTypes.forEach(({
9090

9191
// cypress-fail-fast is required as an incompatible plugin.
9292
// typescript is required to compile .cy.ts spec files in the pre-compiled JS tests.
93-
// typescript@5 is pinned because typescript@6 emits "use strict" on line 1 for
94-
// non-module files, shifting compiled line numbers and breaking source map resolution.
95-
// TODO: Update tests files accordingly and test with different TS versions
96-
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript@5'], true)
93+
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript'], true)
9794

9895
before(async function () {
9996
// Note: Cypress binary is already installed during useSandbox() via the postinstall script

integration-tests/cypress/cypress-reporting.spec.js

Lines changed: 90 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,10 @@ const {
3939
const { DD_HOST_CPU_COUNT } = require('../../packages/dd-trace/src/plugins/util/env')
4040
const { ERROR_MESSAGE, ERROR_TYPE, COMPONENT } = require('../../packages/dd-trace/src/constants')
4141
const { DD_MAJOR, NODE_MAJOR } = require('../../version')
42-
const { resolveSourceLineForTest } = require('../../packages/datadog-plugin-cypress/src/source-map-utils')
42+
const {
43+
resolveOriginalSourceFile,
44+
resolveSourceLineForTest,
45+
} = require('../../packages/datadog-plugin-cypress/src/source-map-utils')
4346

4447
const RECEIVER_STOP_TIMEOUT = 20000
4548
const version = process.env.CYPRESS_VERSION
@@ -59,6 +62,30 @@ function compilePrecompiledTypeScriptSpecs (cwd, env) {
5962
}
6063
}
6164

65+
/**
66+
* @param {string} cwd
67+
* @returns {void}
68+
*/
69+
function configureCypressTypeScriptCompilation (cwd) {
70+
// Cypress's webpack preprocessor resolves TypeScript config from the spec directory.
71+
const tsconfig = {
72+
compilerOptions: {
73+
rootDir: '.',
74+
target: 'ES2020',
75+
module: 'commonjs',
76+
sourceMap: true,
77+
skipLibCheck: true,
78+
},
79+
}
80+
81+
const typescriptVersion = require(path.join(cwd, 'node_modules/typescript/package.json')).version
82+
if (semver.gte(typescriptVersion, '6.0.0')) {
83+
tsconfig.compilerOptions.ignoreDeprecations = '6.0'
84+
}
85+
86+
fs.writeFileSync(path.join(cwd, 'cypress/e2e/tsconfig.json'), JSON.stringify(tsconfig, null, 2))
87+
}
88+
6289
function shouldTestsRun (type) {
6390
if (DD_MAJOR === 5) {
6491
if (NODE_MAJOR <= 16) {
@@ -119,10 +146,7 @@ moduleTypes.forEach(({
119146

120147
// cypress-fail-fast is required as an incompatible plugin.
121148
// typescript is required to compile .cy.ts spec files in the pre-compiled JS tests.
122-
// typescript@5 is pinned because typescript@6 emits "use strict" on line 1 for
123-
// non-module files, shifting compiled line numbers and breaking source map resolution.
124-
// TODO: Update tests files accordingly and test with different TS versions
125-
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript@5'], true)
149+
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript'], true)
126150

127151
before(async function () {
128152
// Note: Cypress binary is already installed during useSandbox() via the postinstall script
@@ -676,6 +700,7 @@ moduleTypes.forEach(({
676700
)
677701

678702
over10It('reports tests with a TypeScript config file', async () => {
703+
let testOutput = ''
679704
const receiverPromise = receiver
680705
.gatherPayloadsMaxTimeout(({ url }) => url.endsWith('/api/v2/citestcycle'), (payloads) => {
681706
const events = payloads
@@ -690,7 +715,13 @@ moduleTypes.forEach(({
690715
[TEST_STATUS]: 'pass',
691716
[TEST_FRAMEWORK]: 'cypress',
692717
},
693-
})
718+
}, `got events: ${JSON.stringify(events.map(event => ({
719+
resource: event.content.resource,
720+
sourceFile: event.content.meta?.[TEST_SOURCE_FILE],
721+
status: event.content.meta?.[TEST_STATUS],
722+
framework: event.content.meta?.[TEST_FRAMEWORK],
723+
error: event.content.meta?.[ERROR_MESSAGE],
724+
})), null, 2)}\nCypress output:\n${testOutput}`)
694725
}, 20000)
695726

696727
const envVars = getCiVisAgentlessConfig(receiver.port)
@@ -706,6 +737,12 @@ moduleTypes.forEach(({
706737
},
707738
}
708739
)
740+
childProcess.stdout?.on('data', chunk => {
741+
testOutput += chunk.toString()
742+
})
743+
childProcess.stderr?.on('data', chunk => {
744+
testOutput += chunk.toString()
745+
})
709746

710747
const [[exitCode]] = await Promise.all([
711748
once(childProcess, 'exit'),
@@ -1294,6 +1331,33 @@ moduleTypes.forEach(({
12941331
}
12951332
})
12961333

1334+
over12It('resolves source file when generated first line is unmapped', () => {
1335+
const tempDir = fs.mkdtempSync(path.join(os.tmpdir(), 'dd-cypress-source-map-'))
1336+
const compiledFilePath = path.join(tempDir, 'spec-prologue.js')
1337+
const sourceMapPath = `${compiledFilePath}.map`
1338+
1339+
try {
1340+
fs.writeFileSync(compiledFilePath, [
1341+
'"use strict";',
1342+
'it("source mapped title", () => {})',
1343+
'',
1344+
].join('\n'))
1345+
1346+
fs.writeFileSync(sourceMapPath, JSON.stringify({
1347+
version: 3,
1348+
file: 'spec-prologue.js',
1349+
sourceRoot: '',
1350+
sources: ['spec-prologue.ts'],
1351+
names: [],
1352+
mappings: ';AAEA',
1353+
}))
1354+
1355+
assert.strictEqual(resolveOriginalSourceFile(compiledFilePath), path.join(tempDir, 'spec-prologue.ts'))
1356+
} finally {
1357+
fs.rmSync(tempDir, { recursive: true, force: true })
1358+
}
1359+
})
1360+
12971361
over12It('uses declaration scanning fallback when invocationDetails line is invalid', async function () {
12981362
const envVars = getCiVisAgentlessConfig(receiver.port)
12991363

@@ -1429,6 +1493,8 @@ moduleTypes.forEach(({
14291493
over12It('reports correct source file and line for typescript test files compiled by cypress', async function () {
14301494
// Remove any pre-compiled dist files to ensure Cypress compiles the .ts file itself
14311495
cleanupPrecompiledSourceLineDist(cwd)
1496+
configureCypressTypeScriptCompilation(cwd)
1497+
let testOutput = ''
14321498

14331499
const receiverPromise = receiver
14341500
.gatherPayloadsMaxTimeout(({ url }) => url.endsWith('/api/v2/citestcycle'), (payloads) => {
@@ -1438,7 +1504,18 @@ moduleTypes.forEach(({
14381504
event.content.resource.includes('spec source line')
14391505
)
14401506

1441-
assert.strictEqual(tsTestEvents.length, 2, 'should have two typescript test events')
1507+
assert.strictEqual(
1508+
tsTestEvents.length,
1509+
2,
1510+
`should have two typescript test events, got events: ${JSON.stringify(events.map(event => ({
1511+
type: event.type,
1512+
resource: event.content.resource,
1513+
sourceFile: event.content.meta?.[TEST_SOURCE_FILE],
1514+
sourceStart: event.content.metrics?.[TEST_SOURCE_START],
1515+
status: event.content.meta?.[TEST_STATUS],
1516+
error: event.content.meta?.[ERROR_MESSAGE],
1517+
})), null, 2)}\nCypress output:\n${testOutput}`
1518+
)
14421519

14431520
const itTestEvent = tsTestEvents.find(e => e.content.resource.includes('reports correct line number'))
14441521
const testTestEvent = tsTestEvents.find(
@@ -1482,6 +1559,12 @@ moduleTypes.forEach(({
14821559
SPEC_PATTERN: 'cypress/e2e/spec-source-line.cy.ts',
14831560
},
14841561
})
1562+
childProcess.stdout?.on('data', chunk => {
1563+
testOutput += chunk.toString()
1564+
})
1565+
childProcess.stderr?.on('data', chunk => {
1566+
testOutput += chunk.toString()
1567+
})
14851568

14861569
const [[exitCode]] = await Promise.all([once(childProcess, 'exit'), receiverPromise])
14871570
assert.strictEqual(exitCode, 0, 'cypress process should exit successfully')

integration-tests/cypress/cypress-test-management.spec.js

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -97,10 +97,7 @@ moduleTypes.forEach(({
9797

9898
// cypress-fail-fast is required as an incompatible plugin.
9999
// typescript is required to compile .cy.ts spec files in the pre-compiled JS tests.
100-
// typescript@5 is pinned because typescript@6 emits "use strict" on line 1 for
101-
// non-module files, shifting compiled line numbers and breaking source map resolution.
102-
// TODO: Update tests files accordingly and test with different TS versions
103-
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript@5'], true)
100+
useSandbox([`cypress@${version}`, 'cypress-fail-fast@7.1.0', 'typescript'], true)
104101

105102
before(async function () {
106103
// Note: Cypress binary is already installed during useSandbox() via the postinstall script

integration-tests/playwright/playwright-active-test-span.spec.js

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -50,8 +50,7 @@ versions.forEach((version) => {
5050
this.retries(2)
5151
this.timeout(80000)
5252

53-
// TODO: Update tests files accordingly and test with different TS versions
54-
useSandbox([`@playwright/test@${version}`, '@types/node', 'typescript@5'], true)
53+
useSandbox([`@playwright/test@${version}`, '@types/node', 'typescript'], true)
5554

5655
before(function (done) {
5756
// Increase timeout for this hook specifically to account for slow chromium installation in CI

integration-tests/playwright/playwright-atr.spec.js

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -45,8 +45,7 @@ versions.forEach((version) => {
4545
this.retries(2)
4646
this.timeout(80000)
4747

48-
// TODO: Update tests files accordingly and test with different TS versions
49-
useSandbox([`@playwright/test@${version}`, '@types/node', 'typescript@5'], true)
48+
useSandbox([`@playwright/test@${version}`, '@types/node', 'typescript'], true)
5049

5150
before(function (done) {
5251
// Increase timeout for this hook specifically to account for slow chromium installation in CI

integration-tests/playwright/playwright-efd.spec.js

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -51,8 +51,7 @@ versions.forEach((version) => {
5151
this.retries(2)
5252
this.timeout(80000)
5353

54-
// TODO: Update tests files accordingly and test with different TS versions
55-
useSandbox([`@playwright/test@${version}`, '@types/node', 'typescript@5'], true)
54+
useSandbox([`@playwright/test@${version}`, '@types/node', 'typescript'], true)
5655

5756
before(function (done) {
5857
// Increase timeout for this hook specifically to account for slow chromium installation in CI

0 commit comments

Comments
 (0)