codeceptjs 3.7.5-beta.15 → 3.7.5-beta.17

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "codeceptjs",
3
- "version": "3.7.5-beta.15",
3
+ "version": "3.7.5-beta.17",
4
4
  "description": "Supercharged End 2 End Testing Framework for NodeJS",
5
5
  "keywords": [
6
6
  "acceptance",
@@ -78,12 +78,12 @@
78
78
  "@codeceptjs/configure": "1.0.6",
79
79
  "@codeceptjs/helper": "2.0.4",
80
80
  "@cucumber/cucumber-expressions": "18",
81
- "@cucumber/gherkin": "32.1.2",
82
- "@cucumber/messages": "27.2.0",
81
+ "@cucumber/gherkin": "35.0.0",
82
+ "@cucumber/messages": "29.0.1",
83
83
  "@xmldom/xmldom": "0.9.8",
84
- "acorn": "8.14.1",
84
+ "acorn": "8.15.0",
85
85
  "arrify": "3.0.0",
86
- "axios": "1.11.0",
86
+ "axios": "1.12.2",
87
87
  "chalk": "4.1.2",
88
88
  "cheerio": "^1.0.0",
89
89
  "chokidar": "^4.0.3",
@@ -95,20 +95,20 @@
95
95
  "escape-string-regexp": "4.0.0",
96
96
  "figures": "3.2.0",
97
97
  "fn-args": "4.0.0",
98
- "fs-extra": "11.3.0",
98
+ "fs-extra": "11.3.2",
99
99
  "fuse.js": "^7.0.0",
100
100
  "glob": ">=9.0.0 <12",
101
101
  "html-minifier-terser": "7.2.0",
102
102
  "inquirer": "^8.2.7",
103
103
  "invisi-data": "^1.0.0",
104
- "joi": "17.13.3",
104
+ "joi": "18.0.1",
105
105
  "js-beautify": "1.15.4",
106
106
  "lodash.clonedeep": "4.5.0",
107
107
  "lodash.merge": "4.6.2",
108
108
  "lodash.shuffle": "4.2.0",
109
109
  "mkdirp": "3.0.1",
110
- "mocha": "11.6.0",
111
- "monocart-coverage-reports": "2.12.6",
110
+ "mocha": "11.7.2",
111
+ "monocart-coverage-reports": "2.12.9",
112
112
  "ms": "2.1.3",
113
113
  "multer": "^2.0.2",
114
114
  "ora-classic": "5.4.2",
@@ -120,20 +120,20 @@
120
120
  "uuid": "11.1.0"
121
121
  },
122
122
  "optionalDependencies": {
123
- "@codeceptjs/detox-helper": "1.1.8"
123
+ "@codeceptjs/detox-helper": "1.1.12"
124
124
  },
125
125
  "devDependencies": {
126
- "@apollo/server": "^4",
126
+ "@apollo/server": "^5",
127
127
  "@codeceptjs/expect-helper": "^1.0.2",
128
128
  "@codeceptjs/mock-request": "0.3.1",
129
129
  "@eslint/eslintrc": "3.3.1",
130
- "@eslint/js": "9.34.0",
130
+ "@eslint/js": "9.35.0",
131
131
  "@faker-js/faker": "9.8.0",
132
132
  "@pollyjs/adapter-puppeteer": "6.0.6",
133
133
  "@pollyjs/core": "6.0.6",
134
134
  "@types/chai": "5.2.2",
135
- "@types/inquirer": "9.0.7",
136
- "@types/node": "24.0.10",
135
+ "@types/inquirer": "9.0.9",
136
+ "@types/node": "24.5.0",
137
137
  "@wdio/sauce-service": "9.12.5",
138
138
  "@wdio/selenium-standalone-service": "8.15.0",
139
139
  "@wdio/utils": "9.15.0",
@@ -142,13 +142,13 @@
142
142
  "chai-as-promised": "7.1.2",
143
143
  "chai-subset": "1.6.0",
144
144
  "documentation": "14.0.3",
145
- "electron": "37.2.3",
146
- "eslint": "^9.24.0",
145
+ "electron": "38.1.0",
146
+ "eslint": "^9.35.0",
147
147
  "eslint-plugin-import": "2.32.0",
148
148
  "eslint-plugin-mocha": "11.1.0",
149
- "expect": "30.0.5",
149
+ "expect": "30.1.2",
150
150
  "express": "^5.1.0",
151
- "globals": "16.2.0",
151
+ "globals": "16.4.0",
152
152
  "graphql": "16.11.0",
153
153
  "graphql-tag": "^2.12.6",
154
154
  "husky": "9.1.7",
@@ -157,7 +157,7 @@
157
157
  "jsdoc-typeof-plugin": "1.0.0",
158
158
  "json-server": "0.17.4",
159
159
  "mochawesome": "^7.1.3",
160
- "playwright": "1.54.1",
160
+ "playwright": "1.55.0",
161
161
  "prettier": "^3.3.2",
162
162
  "puppeteer": "24.15.0",
163
163
  "qrcode-terminal": "0.12.0",
@@ -171,7 +171,7 @@
171
171
  "ts-node": "10.9.2",
172
172
  "tsd": "^0.33.0",
173
173
  "tsd-jsdoc": "2.5.0",
174
- "typedoc": "0.28.10",
174
+ "typedoc": "0.28.13",
175
175
  "typedoc-plugin-markdown": "4.8.1",
176
176
  "typescript": "5.8.3",
177
177
  "wdio-docker-service": "3.2.1",
@@ -189,5 +189,8 @@
189
189
  "compilerOptions": {
190
190
  "strict": false
191
191
  }
192
+ },
193
+ "overrides": {
194
+ "tmp": "0.2.5"
192
195
  }
193
196
  }
@@ -2738,6 +2738,8 @@ declare namespace CodeceptJS {
2738
2738
  // @ts-ignore
2739
2739
  // @ts-ignore
2740
2740
  // @ts-ignore
2741
+ // @ts-ignore
2742
+ // @ts-ignore
2741
2743
  type PlaywrightConfig = {
2742
2744
  url?: string;
2743
2745
  browser?: 'chromium' | 'firefox' | 'webkit' | 'electron';
@@ -6118,6 +6120,8 @@ declare namespace CodeceptJS {
6118
6120
  // @ts-ignore
6119
6121
  // @ts-ignore
6120
6122
  // @ts-ignore
6123
+ // @ts-ignore
6124
+ // @ts-ignore
6121
6125
  type PuppeteerConfig = {
6122
6126
  url: string;
6123
6127
  basicAuth?: any;
@@ -7927,6 +7931,8 @@ declare namespace CodeceptJS {
7927
7931
  // @ts-ignore
7928
7932
  // @ts-ignore
7929
7933
  // @ts-ignore
7934
+ // @ts-ignore
7935
+ // @ts-ignore
7930
7936
  type RESTConfig = {
7931
7937
  endpoint?: string;
7932
7938
  prettyPrintJson?: boolean;
@@ -9075,6 +9081,8 @@ declare namespace CodeceptJS {
9075
9081
  // @ts-ignore
9076
9082
  // @ts-ignore
9077
9083
  // @ts-ignore
9084
+ // @ts-ignore
9085
+ // @ts-ignore
9078
9086
  type WebDriverConfig = {
9079
9087
  url: string;
9080
9088
  browser: string;
@@ -2828,6 +2828,8 @@ declare namespace CodeceptJS {
2828
2828
  // @ts-ignore
2829
2829
  // @ts-ignore
2830
2830
  // @ts-ignore
2831
+ // @ts-ignore
2832
+ // @ts-ignore
2831
2833
  type PlaywrightConfig = {
2832
2834
  url?: string;
2833
2835
  browser?: 'chromium' | 'firefox' | 'webkit' | 'electron';
@@ -6359,6 +6361,8 @@ declare namespace CodeceptJS {
6359
6361
  // @ts-ignore
6360
6362
  // @ts-ignore
6361
6363
  // @ts-ignore
6364
+ // @ts-ignore
6365
+ // @ts-ignore
6362
6366
  type PuppeteerConfig = {
6363
6367
  url: string;
6364
6368
  basicAuth?: any;
@@ -8304,6 +8308,8 @@ declare namespace CodeceptJS {
8304
8308
  // @ts-ignore
8305
8309
  // @ts-ignore
8306
8310
  // @ts-ignore
8311
+ // @ts-ignore
8312
+ // @ts-ignore
8307
8313
  type RESTConfig = {
8308
8314
  endpoint?: string;
8309
8315
  prettyPrintJson?: boolean;
@@ -9512,6 +9518,8 @@ declare namespace CodeceptJS {
9512
9518
  // @ts-ignore
9513
9519
  // @ts-ignore
9514
9520
  // @ts-ignore
9521
+ // @ts-ignore
9522
+ // @ts-ignore
9515
9523
  type WebDriverConfig = {
9516
9524
  url: string;
9517
9525
  browser: string;
@@ -1,277 +0,0 @@
1
- const fs = require('fs')
2
- const path = require('path')
3
- const { getConfig, printError, getTestRoot, createOutputDir } = require('./utils')
4
- const Config = require('../config')
5
- const store = require('../store')
6
- const Codecept = require('../codecept')
7
- const output = require('../output')
8
- const Workers = require('../workers')
9
- const { tryOrDefault } = require('../utils')
10
-
11
- module.exports = async function (options) {
12
- // registering options globally to use in config
13
- if (options.profile) {
14
- process.env.profile = options.profile
15
- }
16
- if (options.verbose || options.debug) store.debugMode = true
17
-
18
- const configFile = options.config
19
- let config = getConfig(configFile)
20
-
21
- if (options.override) {
22
- config = Config.append(JSON.parse(options.override))
23
- }
24
-
25
- const testRoot = getTestRoot(configFile)
26
- createOutputDir(config, testRoot)
27
-
28
- // Determine failed tests file path - respect CodeceptJS output directory
29
- const failedTestsFile = options.file || 'failed-tests.json'
30
- const failedTestsPath = path.isAbsolute(failedTestsFile)
31
- ? failedTestsFile
32
- : path.resolve(global.output_dir || './output', failedTestsFile)
33
-
34
- // Check if failed tests file exists
35
- if (!fs.existsSync(failedTestsPath)) {
36
- output.error(`Failed tests file not found: ${failedTestsPath}`)
37
- output.print('Run tests first to generate a failed tests file, or specify a different file with --file option')
38
- process.exitCode = 1
39
- return
40
- }
41
-
42
- let failedTestsData
43
- try {
44
- const fileContent = fs.readFileSync(failedTestsPath, 'utf8')
45
- failedTestsData = JSON.parse(fileContent)
46
- } catch (error) {
47
- output.error(`Failed to read or parse failed tests file: ${error.message}`)
48
- process.exitCode = 1
49
- return
50
- }
51
-
52
- if (!failedTestsData.tests || failedTestsData.tests.length === 0) {
53
- output.print('No failed tests found in the file')
54
- return
55
- }
56
-
57
- output.print(`Found ${failedTestsData.tests.length} failed tests from ${failedTestsData.timestamp}`)
58
-
59
- // Debug: Show what's in the failed tests data
60
- if (options.verbose) {
61
- output.print('\nFailed tests data structure:')
62
- failedTestsData.tests.forEach((test, index) => {
63
- output.print(` ${index + 1}. Title: "${test.title}", UID: "${test.uid}", File: "${test.file}"`)
64
- })
65
- output.print('')
66
- }
67
-
68
- // Build test patterns from failed tests
69
- const testPatterns = []
70
- const testsByFile = new Map()
71
-
72
- // Group tests by file for more efficient execution
73
- failedTestsData.tests.forEach(test => {
74
- if (test.file) {
75
- if (!testsByFile.has(test.file)) {
76
- testsByFile.set(test.file, [])
77
- }
78
- testsByFile.get(test.file).push(test)
79
- }
80
- })
81
-
82
- // Build precise test selection from failed tests
83
- if (testsByFile.size > 0) {
84
- // Use file paths for loading tests
85
- for (const [file, tests] of testsByFile) {
86
- testPatterns.push(file)
87
- }
88
-
89
- // Create a map of exact test titles to target for filtering
90
- const failedTestTitles = new Set(failedTestsData.tests.map(test => test.title).filter(Boolean))
91
-
92
- if (failedTestTitles.size > 0) {
93
- output.print(`Targeting ${failedTestTitles.size} specific failed tests by exact title matching`)
94
- options.exactTestTitles = Array.from(failedTestTitles)
95
- } else {
96
- output.print('No specific test titles found, running all tests in files')
97
- }
98
- } else {
99
- // Fallback: use test titles with exact match grep
100
- const testTitles = failedTestsData.tests.map(test => test.title).filter(Boolean)
101
- if (testTitles.length > 0) {
102
- const grepPattern = testTitles.map(title => `^${title.replace(/[.*+?^${}()|[\]\\]/g, '\\$&')}$`).join('|')
103
- options.grep = grepPattern
104
- output.print(`Targeting failed tests by title pattern (no file info available)`)
105
- }
106
- }
107
-
108
- // Check if user wants to run with workers
109
- if (options.workers) {
110
- await runWithWorkers(config, options, testPatterns, failedTestsData)
111
- } else {
112
- await runWithoutWorkers(config, options, testPatterns, failedTestsData, testRoot)
113
- }
114
- }
115
-
116
- async function runWithWorkers(config, options, testPatterns, failedTestsData) {
117
- const numberOfWorkers = parseInt(options.workers, 10)
118
- const overrideConfigs = tryOrDefault(() => JSON.parse(options.override || '{}'), {})
119
-
120
- // Determine test split strategy
121
- let by = 'test' // default for failed tests
122
- if (options.by) {
123
- by = options.by
124
- } else if (options.suites) {
125
- by = 'suite'
126
- }
127
-
128
- // Validate the by option
129
- const validStrategies = ['test', 'suite', 'pool']
130
- if (!validStrategies.includes(by)) {
131
- throw new Error(`Invalid --by strategy: ${by}. Valid options are: ${validStrategies.join(', ')}`)
132
- }
133
-
134
- const workerConfig = {
135
- by,
136
- testConfig: options.config,
137
- options,
138
- selectedRuns: undefined,
139
- }
140
-
141
- // If we have specific test UIDs, override the worker test selection
142
- if (options.tests && options.tests.length > 0) {
143
- workerConfig.by = 'test' // Force test-level distribution for precise targeting
144
- output.print(`Using precise test UID targeting for ${options.tests.length} failed tests`)
145
- }
146
-
147
- output.print(`CodeceptJS v${require('../codecept').version()}`)
148
- output.print(`Re-running ${failedTestsData.tests.length} failed tests in ${output.styles.bold(numberOfWorkers)} workers...`)
149
- output.print()
150
- store.hasWorkers = true
151
-
152
- const workers = new Workers(numberOfWorkers, workerConfig)
153
- workers.overrideConfig(overrideConfigs)
154
-
155
- // Set up event listeners for worker output
156
- workers.on('test.failed', test => {
157
- output.test.failed(test)
158
- })
159
-
160
- workers.on('test.passed', test => {
161
- output.test.passed(test)
162
- })
163
-
164
- workers.on('test.skipped', test => {
165
- output.test.skipped(test)
166
- })
167
-
168
- workers.on('all.result', result => {
169
- workers.printResults()
170
- })
171
-
172
- try {
173
- if (options.verbose || options.debug) store.debugMode = true
174
-
175
- if (options.verbose) {
176
- output.print('\nFailed tests to re-run with workers:')
177
- failedTestsData.tests.forEach((test, index) => {
178
- output.print(` ${index + 1}. ${test.fullTitle || test.title} (${test.file || 'unknown file'})`)
179
- if (test.error && test.error.message) {
180
- output.print(` Error: ${test.error.message}`)
181
- }
182
- })
183
- output.print('')
184
-
185
- const { getMachineInfo } = require('./info')
186
- await getMachineInfo()
187
- }
188
-
189
- await workers.bootstrapAll()
190
- await workers.run()
191
- } catch (err) {
192
- printError(err)
193
- process.exitCode = 1
194
- } finally {
195
- await workers.teardownAll()
196
- }
197
- }
198
-
199
- async function runWithoutWorkers(config, options, testPatterns, failedTestsData, testRoot) {
200
- const codecept = new Codecept(config, options)
201
-
202
- try {
203
- codecept.init(testRoot)
204
- await codecept.bootstrap()
205
-
206
- // Load tests - if we have specific patterns, use them, otherwise load all and filter with grep
207
- if (testPatterns.length > 0) {
208
- codecept.loadTests(testPatterns.join(' '))
209
- } else {
210
- codecept.loadTests()
211
- }
212
-
213
- // If we have specific test titles, use exact matching
214
- if (options.exactTestTitles && options.exactTestTitles.length > 0) {
215
- // Store the exact failed tests globally for runtime verification
216
- global.__EXACT_FAILED_TESTS__ = failedTestsData.tests.map(test => ({
217
- fullTitle: test.fullTitle,
218
- stableId: test.stableId,
219
- title: test.title,
220
- file: test.file
221
- }))
222
-
223
- // Override the test loading mechanism to filter tests after loading
224
- const Container = require('../container')
225
- const mocha = Container.mocha()
226
-
227
- // Override Mocha's loadFiles to filter tests after loading
228
- const originalLoadFiles = mocha.loadFiles.bind(mocha)
229
- mocha.loadFiles = function() {
230
- const result = originalLoadFiles()
231
-
232
- // Filter the suite after files are loaded to ensure only exact matches run
233
- const filterSuite = (suite) => {
234
- // Filter direct tests in this suite
235
- suite.tests = suite.tests.filter(test => {
236
- const testFullTitle = test.fullTitle()
237
- return global.__EXACT_FAILED_TESTS__.some(failedTest =>
238
- failedTest.fullTitle === testFullTitle
239
- )
240
- })
241
-
242
- // Recursively filter child suites
243
- suite.suites.forEach(childSuite => filterSuite(childSuite))
244
-
245
- // Remove empty child suites
246
- suite.suites = suite.suites.filter(childSuite =>
247
- childSuite.tests.length > 0 || childSuite.suites.length > 0
248
- )
249
- }
250
-
251
- filterSuite(this.suite)
252
- return result
253
- }
254
-
255
- output.print(`Filtered to ${failedTestsData.tests.length} specific failed tests using exact matching`)
256
- }
257
-
258
- // Display information about what we're running
259
- if (options.verbose) {
260
- output.print('\nFailed tests to re-run:')
261
- failedTestsData.tests.forEach((test, index) => {
262
- output.print(` ${index + 1}. ${test.fullTitle || test.title} (${test.file || 'unknown file'})`)
263
- if (test.error && test.error.message) {
264
- output.print(` Error: ${test.error.message}`)
265
- }
266
- })
267
- output.print('')
268
- }
269
-
270
- await codecept.run()
271
- } catch (err) {
272
- printError(err)
273
- process.exitCode = 1
274
- } finally {
275
- await codecept.teardown()
276
- }
277
- }