1# Test runner 2 3<!--introduced_in=v18.0.0--> 4 5<!-- YAML 6added: 7 - v18.0.0 8 - v16.17.0 9--> 10 11> Stability: 1 - Experimental 12 13<!-- source_link=lib/test.js --> 14 15The `node:test` module facilitates the creation of JavaScript tests. 16To access it: 17 18```mjs 19import test from 'node:test'; 20``` 21 22```cjs 23const test = require('node:test'); 24``` 25 26This module is only available under the `node:` scheme. The following will not 27work: 28 29```mjs 30import test from 'test'; 31``` 32 33```cjs 34const test = require('test'); 35``` 36 37Tests created via the `test` module consist of a single function that is 38processed in one of three ways: 39 401. A synchronous function that is considered failing if it throws an exception, 41 and is considered passing otherwise. 422. A function that returns a `Promise` that is considered failing if the 43 `Promise` rejects, and is considered passing if the `Promise` resolves. 443. A function that receives a callback function. If the callback receives any 45 truthy value as its first argument, the test is considered failing. If a 46 falsy value is passed as the first argument to the callback, the test is 47 considered passing. If the test function receives a callback function and 48 also returns a `Promise`, the test will fail. 49 50The following example illustrates how tests are written using the 51`test` module. 52 53```js 54test('synchronous passing test', (t) => { 55 // This test passes because it does not throw an exception. 56 assert.strictEqual(1, 1); 57}); 58 59test('synchronous failing test', (t) => { 60 // This test fails because it throws an exception. 61 assert.strictEqual(1, 2); 62}); 63 64test('asynchronous passing test', async (t) => { 65 // This test passes because the Promise returned by the async 66 // function is not rejected. 67 assert.strictEqual(1, 1); 68}); 69 70test('asynchronous failing test', async (t) => { 71 // This test fails because the Promise returned by the async 72 // function is rejected. 73 assert.strictEqual(1, 2); 74}); 75 76test('failing test using Promises', (t) => { 77 // Promises can be used directly as well. 78 return new Promise((resolve, reject) => { 79 setImmediate(() => { 80 reject(new Error('this will cause the test to fail')); 81 }); 82 }); 83}); 84 85test('callback passing test', (t, done) => { 86 // done() is the callback function. When the setImmediate() runs, it invokes 87 // done() with no arguments. 88 setImmediate(done); 89}); 90 91test('callback failing test', (t, done) => { 92 // When the setImmediate() runs, done() is invoked with an Error object and 93 // the test fails. 94 setImmediate(() => { 95 done(new Error('callback failure')); 96 }); 97}); 98``` 99 100If any tests fail, the process exit code is set to `1`. 101 102## Subtests 103 104The test context's `test()` method allows subtests to be created. This method 105behaves identically to the top level `test()` function. The following example 106demonstrates the creation of a top level test with two subtests. 107 108```js 109test('top level test', async (t) => { 110 await t.test('subtest 1', (t) => { 111 assert.strictEqual(1, 1); 112 }); 113 114 await t.test('subtest 2', (t) => { 115 assert.strictEqual(2, 2); 116 }); 117}); 118``` 119 120In this example, `await` is used to ensure that both subtests have completed. 121This is necessary because parent tests do not wait for their subtests to 122complete. Any subtests that are still outstanding when their parent finishes 123are cancelled and treated as failures. Any subtest failures cause the parent 124test to fail. 125 126## Skipping tests 127 128Individual tests can be skipped by passing the `skip` option to the test, or by 129calling the test context's `skip()` method as shown in the 130following example. 131 132```js 133// The skip option is used, but no message is provided. 134test('skip option', { skip: true }, (t) => { 135 // This code is never executed. 136}); 137 138// The skip option is used, and a message is provided. 139test('skip option with message', { skip: 'this is skipped' }, (t) => { 140 // This code is never executed. 141}); 142 143test('skip() method', (t) => { 144 // Make sure to return here as well if the test contains additional logic. 145 t.skip(); 146}); 147 148test('skip() method with message', (t) => { 149 // Make sure to return here as well if the test contains additional logic. 150 t.skip('this is skipped'); 151}); 152``` 153 154## `describe`/`it` syntax 155 156Running tests can also be done using `describe` to declare a suite 157and `it` to declare a test. 158A suite is used to organize and group related tests together. 159`it` is a shorthand for [`test()`][]. 160 161```js 162describe('A thing', () => { 163 it('should work', () => { 164 assert.strictEqual(1, 1); 165 }); 166 167 it('should be ok', () => { 168 assert.strictEqual(2, 2); 169 }); 170 171 describe('a nested thing', () => { 172 it('should work', () => { 173 assert.strictEqual(3, 3); 174 }); 175 }); 176}); 177``` 178 179`describe` and `it` are imported from the `node:test` module. 180 181```mjs 182import { describe, it } from 'node:test'; 183``` 184 185```cjs 186const { describe, it } = require('node:test'); 187``` 188 189## `only` tests 190 191If Node.js is started with the [`--test-only`][] command-line option, it is 192possible to skip all top level tests except for a selected subset by passing 193the `only` option to the tests that should be run. When a test with the `only` 194option set is run, all subtests are also run. The test context's `runOnly()` 195method can be used to implement the same behavior at the subtest level. 196 197```js 198// Assume Node.js is run with the --test-only command-line option. 199// The 'only' option is set, so this test is run. 200test('this test is run', { only: true }, async (t) => { 201 // Within this test, all subtests are run by default. 202 await t.test('running subtest'); 203 204 // The test context can be updated to run subtests with the 'only' option. 205 t.runOnly(true); 206 await t.test('this subtest is now skipped'); 207 await t.test('this subtest is run', { only: true }); 208 209 // Switch the context back to execute all tests. 210 t.runOnly(false); 211 await t.test('this subtest is now run'); 212 213 // Explicitly do not run these tests. 214 await t.test('skipped subtest 3', { only: false }); 215 await t.test('skipped subtest 4', { skip: true }); 216}); 217 218// The 'only' option is not set, so this test is skipped. 219test('this test is not run', () => { 220 // This code is not run. 221 throw new Error('fail'); 222}); 223``` 224 225## Filtering tests by name 226 227The [`--test-name-pattern`][] command-line option can be used to only run tests 228whose name matches the provided pattern. Test name patterns are interpreted as 229JavaScript regular expressions. The `--test-name-pattern` option can be 230specified multiple times in order to run nested tests. For each test that is 231executed, any corresponding test hooks, such as `beforeEach()`, are also 232run. 233 234Given the following test file, starting Node.js with the 235`--test-name-pattern="test [1-3]"` option would cause the test runner to execute 236`test 1`, `test 2`, and `test 3`. If `test 1` did not match the test name 237pattern, then its subtests would not execute, despite matching the pattern. The 238same set of tests could also be executed by passing `--test-name-pattern` 239multiple times (e.g. `--test-name-pattern="test 1"`, 240`--test-name-pattern="test 2"`, etc.). 241 242```js 243test('test 1', async (t) => { 244 await t.test('test 2'); 245 await t.test('test 3'); 246}); 247 248test('Test 4', async (t) => { 249 await t.test('Test 5'); 250 await t.test('test 6'); 251}); 252``` 253 254Test name patterns can also be specified using regular expression literals. This 255allows regular expression flags to be used. In the previous example, starting 256Node.js with `--test-name-pattern="/test [4-5]/i"` would match `Test 4` and 257`Test 5` because the pattern is case-insensitive. 258 259Test name patterns do not change the set of files that the test runner executes. 260 261## Extraneous asynchronous activity 262 263Once a test function finishes executing, the results are reported as quickly 264as possible while maintaining the order of the tests. However, it is possible 265for the test function to generate asynchronous activity that outlives the test 266itself. The test runner handles this type of activity, but does not delay the 267reporting of test results in order to accommodate it. 268 269In the following example, a test completes with two `setImmediate()` 270operations still outstanding. The first `setImmediate()` attempts to create a 271new subtest. Because the parent test has already finished and output its 272results, the new subtest is immediately marked as failed, and reported later 273to the {TestsStream}. 274 275The second `setImmediate()` creates an `uncaughtException` event. 276`uncaughtException` and `unhandledRejection` events originating from a completed 277test are marked as failed by the `test` module and reported as diagnostic 278warnings at the top level by the {TestsStream}. 279 280```js 281test('a test that creates asynchronous activity', (t) => { 282 setImmediate(() => { 283 t.test('subtest that is created too late', (t) => { 284 throw new Error('error1'); 285 }); 286 }); 287 288 setImmediate(() => { 289 throw new Error('error2'); 290 }); 291 292 // The test finishes after this line. 293}); 294``` 295 296## Watch mode 297 298<!-- YAML 299added: v18.13.0 300--> 301 302> Stability: 1 - Experimental 303 304The Node.js test runner supports running in watch mode by passing the `--watch` flag: 305 306```bash 307node --test --watch 308``` 309 310In watch mode, the test runner will watch for changes to test files and 311their dependencies. When a change is detected, the test runner will 312rerun the tests affected by the change. 313The test runner will continue to run until the process is terminated. 314 315## Running tests from the command line 316 317The Node.js test runner can be invoked from the command line by passing the 318[`--test`][] flag: 319 320```bash 321node --test 322``` 323 324By default, Node.js will recursively search the current directory for 325JavaScript source files matching a specific naming convention. Matching files 326are executed as test files. More information on the expected test file naming 327convention and behavior can be found in the [test runner execution model][] 328section. 329 330Alternatively, one or more paths can be provided as the final argument(s) to 331the Node.js command, as shown below. 332 333```bash 334node --test test1.js test2.mjs custom_test_dir/ 335``` 336 337In this example, the test runner will execute the files `test1.js` and 338`test2.mjs`. The test runner will also recursively search the 339`custom_test_dir/` directory for test files to execute. 340 341### Test runner execution model 342 343When searching for test files to execute, the test runner behaves as follows: 344 345* Any files explicitly provided by the user are executed. 346* If the user did not explicitly specify any paths, the current working 347 directory is recursively searched for files as specified in the following 348 steps. 349* `node_modules` directories are skipped unless explicitly provided by the 350 user. 351* If a directory named `test` is encountered, the test runner will search it 352 recursively for all all `.js`, `.cjs`, and `.mjs` files. All of these files 353 are treated as test files, and do not need to match the specific naming 354 convention detailed below. This is to accommodate projects that place all of 355 their tests in a single `test` directory. 356* In all other directories, `.js`, `.cjs`, and `.mjs` files matching the 357 following patterns are treated as test files: 358 * `^test$` - Files whose basename is the string `'test'`. Examples: 359 `test.js`, `test.cjs`, `test.mjs`. 360 * `^test-.+` - Files whose basename starts with the string `'test-'` 361 followed by one or more characters. Examples: `test-example.js`, 362 `test-another-example.mjs`. 363 * `.+[\.\-\_]test$` - Files whose basename ends with `.test`, `-test`, or 364 `_test`, preceded by one or more characters. Examples: `example.test.js`, 365 `example-test.cjs`, `example_test.mjs`. 366 * Other file types understood by Node.js such as `.node` and `.json` are not 367 automatically executed by the test runner, but are supported if explicitly 368 provided on the command line. 369 370Each matching test file is executed in a separate child process. The maximum 371number of child processes running at any time is controlled by the 372[`--test-concurrency`][] flag. If the child process finishes with an exit code 373of 0, the test is considered passing. Otherwise, the test is considered to be a 374failure. Test files must be executable by Node.js, but are not required to use 375the `node:test` module internally. 376 377Each test file is executed as if it was a regular script. That is, if the test 378file itself uses `node:test` to define tests, all of those tests will be 379executed within a single application thread, regardless of the value of the 380`concurrency` option of [`test()`][]. 381 382## Collecting code coverage 383 384When Node.js is started with the [`--experimental-test-coverage`][] 385command-line flag, code coverage is collected and statistics are reported once 386all tests have completed. If the [`NODE_V8_COVERAGE`][] environment variable is 387used to specify a code coverage directory, the generated V8 coverage files are 388written to that directory. Node.js core modules and files within 389`node_modules/` directories are not included in the coverage report. If 390coverage is enabled, the coverage report is sent to any [test reporters][] via 391the `'test:coverage'` event. 392 393Coverage can be disabled on a series of lines using the following 394comment syntax: 395 396```js 397/* node:coverage disable */ 398if (anAlwaysFalseCondition) { 399 // Code in this branch will never be executed, but the lines are ignored for 400 // coverage purposes. All lines following the 'disable' comment are ignored 401 // until a corresponding 'enable' comment is encountered. 402 console.log('this is never executed'); 403} 404/* node:coverage enable */ 405``` 406 407Coverage can also be disabled for a specified number of lines. After the 408specified number of lines, coverage will be automatically reenabled. If the 409number of lines is not explicitly provided, a single line is ignored. 410 411```js 412/* node:coverage ignore next */ 413if (anAlwaysFalseCondition) { console.log('this is never executed'); } 414 415/* node:coverage ignore next 3 */ 416if (anAlwaysFalseCondition) { 417 console.log('this is never executed'); 418} 419``` 420 421The test runner's code coverage functionality has the following limitations, 422which will be addressed in a future Node.js release: 423 424* Source maps are not supported. 425* Excluding specific files or directories from the coverage report is not 426 supported. 427 428## Mocking 429 430The `node:test` module supports mocking during testing via a top-level `mock` 431object. The following example creates a spy on a function that adds two numbers 432together. The spy is then used to assert that the function was called as 433expected. 434 435```mjs 436import assert from 'node:assert'; 437import { mock, test } from 'node:test'; 438 439test('spies on a function', () => { 440 const sum = mock.fn((a, b) => { 441 return a + b; 442 }); 443 444 assert.strictEqual(sum.mock.calls.length, 0); 445 assert.strictEqual(sum(3, 4), 7); 446 assert.strictEqual(sum.mock.calls.length, 1); 447 448 const call = sum.mock.calls[0]; 449 assert.deepStrictEqual(call.arguments, [3, 4]); 450 assert.strictEqual(call.result, 7); 451 assert.strictEqual(call.error, undefined); 452 453 // Reset the globally tracked mocks. 454 mock.reset(); 455}); 456``` 457 458```cjs 459'use strict'; 460const assert = require('node:assert'); 461const { mock, test } = require('node:test'); 462 463test('spies on a function', () => { 464 const sum = mock.fn((a, b) => { 465 return a + b; 466 }); 467 468 assert.strictEqual(sum.mock.calls.length, 0); 469 assert.strictEqual(sum(3, 4), 7); 470 assert.strictEqual(sum.mock.calls.length, 1); 471 472 const call = sum.mock.calls[0]; 473 assert.deepStrictEqual(call.arguments, [3, 4]); 474 assert.strictEqual(call.result, 7); 475 assert.strictEqual(call.error, undefined); 476 477 // Reset the globally tracked mocks. 478 mock.reset(); 479}); 480``` 481 482The same mocking functionality is also exposed on the [`TestContext`][] object 483of each test. The following example creates a spy on an object method using the 484API exposed on the `TestContext`. The benefit of mocking via the test context is 485that the test runner will automatically restore all mocked functionality once 486the test finishes. 487 488```js 489test('spies on an object method', (t) => { 490 const number = { 491 value: 5, 492 add(a) { 493 return this.value + a; 494 }, 495 }; 496 497 t.mock.method(number, 'add'); 498 assert.strictEqual(number.add.mock.calls.length, 0); 499 assert.strictEqual(number.add(3), 8); 500 assert.strictEqual(number.add.mock.calls.length, 1); 501 502 const call = number.add.mock.calls[0]; 503 504 assert.deepStrictEqual(call.arguments, [3]); 505 assert.strictEqual(call.result, 8); 506 assert.strictEqual(call.target, undefined); 507 assert.strictEqual(call.this, number); 508}); 509``` 510 511### Timers 512 513Mocking timers is a technique commonly used in software testing to simulate and 514control the behavior of timers, such as `setInterval` and `setTimeout`, 515without actually waiting for the specified time intervals. 516 517Refer to the [`MockTimers`][] class for a full list of methods and features. 518 519This allows developers to write more reliable and 520predictable tests for time-dependent functionality. 521 522The example below shows how to mock `setTimeout`. 523Using `.enable(['setTimeout']);` 524it will mock the `setTimeout` functions in the [node:timers](./timers.md) and 525[node:timers/promises](./timers.md#timers-promises-api) modules, 526as well as from the Node.js global context. 527 528**Note:** Destructuring functions such as 529`import { setTimeout } from 'node:timers'` 530is currently not supported by this API. 531 532```mjs 533import assert from 'node:assert'; 534import { mock, test } from 'node:test'; 535 536test('mocks setTimeout to be executed synchronously without having to actually wait for it', () => { 537 const fn = mock.fn(); 538 539 // Optionally choose what to mock 540 mock.timers.enable(['setTimeout']); 541 setTimeout(fn, 9999); 542 assert.strictEqual(fn.mock.callCount(), 0); 543 544 // Advance in time 545 mock.timers.tick(9999); 546 assert.strictEqual(fn.mock.callCount(), 1); 547 548 // Reset the globally tracked mocks. 549 mock.timers.reset(); 550 551 // If you call reset mock instance, it will also reset timers instance 552 mock.reset(); 553}); 554``` 555 556```js 557const assert = require('node:assert'); 558const { mock, test } = require('node:test'); 559 560test('mocks setTimeout to be executed synchronously without having to actually wait for it', () => { 561 const fn = mock.fn(); 562 563 // Optionally choose what to mock 564 mock.timers.enable(['setTimeout']); 565 setTimeout(fn, 9999); 566 assert.strictEqual(fn.mock.callCount(), 0); 567 568 // Advance in time 569 mock.timers.tick(9999); 570 assert.strictEqual(fn.mock.callCount(), 1); 571 572 // Reset the globally tracked mocks. 573 mock.timers.reset(); 574 575 // If you call reset mock instance, it'll also reset timers instance 576 mock.reset(); 577}); 578``` 579 580The same mocking functionality is also exposed in the mock property on the [`TestContext`][] object 581of each test. The benefit of mocking via the test context is 582that the test runner will automatically restore all mocked timers 583functionality once the test finishes. 584 585```mjs 586import assert from 'node:assert'; 587import { test } from 'node:test'; 588 589test('mocks setTimeout to be executed synchronously without having to actually wait for it', (context) => { 590 const fn = context.mock.fn(); 591 592 // Optionally choose what to mock 593 context.mock.timers.enable(['setTimeout']); 594 setTimeout(fn, 9999); 595 assert.strictEqual(fn.mock.callCount(), 0); 596 597 // Advance in time 598 context.mock.timers.tick(9999); 599 assert.strictEqual(fn.mock.callCount(), 1); 600}); 601``` 602 603```js 604const assert = require('node:assert'); 605const { test } = require('node:test'); 606 607test('mocks setTimeout to be executed synchronously without having to actually wait for it', (context) => { 608 const fn = context.mock.fn(); 609 610 // Optionally choose what to mock 611 context.mock.timers.enable(['setTimeout']); 612 setTimeout(fn, 9999); 613 assert.strictEqual(fn.mock.callCount(), 0); 614 615 // Advance in time 616 context.mock.timers.tick(9999); 617 assert.strictEqual(fn.mock.callCount(), 1); 618}); 619``` 620 621## Test reporters 622 623<!-- YAML 624added: v18.15.0 625changes: 626 - version: v18.17.0 627 pr-url: https://github.com/nodejs/node/pull/47238 628 description: Reporters are now exposed at `node:test/reporters`. 629--> 630 631The `node:test` module supports passing [`--test-reporter`][] 632flags for the test runner to use a specific reporter. 633 634The following built-reporters are supported: 635 636* `tap` 637 The `tap` reporter outputs the test results in the [TAP][] format. 638 639* `spec` 640 The `spec` reporter outputs the test results in a human-readable format. 641 642* `dot` 643 The `dot` reporter outputs the test results in a compact format, 644 where each passing test is represented by a `.`, 645 and each failing test is represented by a `X`. 646 647* `junit` 648 The junit reporter outputs test results in a jUnit XML format 649 650When `stdout` is a [TTY][], the `spec` reporter is used by default. 651Otherwise, the `tap` reporter is used by default. 652 653The reporters are available via the `node:test/reporters` module: 654 655```mjs 656import { tap, spec, dot, junit } from 'node:test/reporters'; 657``` 658 659```cjs 660const { tap, spec, dot, junit } = require('node:test/reporters'); 661``` 662 663### Custom reporters 664 665[`--test-reporter`][] can be used to specify a path to custom reporter. 666A custom reporter is a module that exports a value 667accepted by [stream.compose][]. 668Reporters should transform events emitted by a {TestsStream} 669 670Example of a custom reporter using {stream.Transform}: 671 672```mjs 673import { Transform } from 'node:stream'; 674 675const customReporter = new Transform({ 676 writableObjectMode: true, 677 transform(event, encoding, callback) { 678 switch (event.type) { 679 case 'test:dequeue': 680 callback(null, `test ${event.data.name} dequeued`); 681 break; 682 case 'test:enqueue': 683 callback(null, `test ${event.data.name} enqueued`); 684 break; 685 case 'test:watch:drained': 686 callback(null, 'test watch queue drained'); 687 break; 688 case 'test:start': 689 callback(null, `test ${event.data.name} started`); 690 break; 691 case 'test:pass': 692 callback(null, `test ${event.data.name} passed`); 693 break; 694 case 'test:fail': 695 callback(null, `test ${event.data.name} failed`); 696 break; 697 case 'test:plan': 698 callback(null, 'test plan'); 699 break; 700 case 'test:diagnostic': 701 case 'test:stderr': 702 case 'test:stdout': 703 callback(null, event.data.message); 704 break; 705 case 'test:coverage': { 706 const { totalLineCount } = event.data.summary.totals; 707 callback(null, `total line count: ${totalLineCount}\n`); 708 break; 709 } 710 } 711 }, 712}); 713 714export default customReporter; 715``` 716 717```cjs 718const { Transform } = require('node:stream'); 719 720const customReporter = new Transform({ 721 writableObjectMode: true, 722 transform(event, encoding, callback) { 723 switch (event.type) { 724 case 'test:dequeue': 725 callback(null, `test ${event.data.name} dequeued`); 726 break; 727 case 'test:enqueue': 728 callback(null, `test ${event.data.name} enqueued`); 729 break; 730 case 'test:watch:drained': 731 callback(null, 'test watch queue drained'); 732 break; 733 case 'test:start': 734 callback(null, `test ${event.data.name} started`); 735 break; 736 case 'test:pass': 737 callback(null, `test ${event.data.name} passed`); 738 break; 739 case 'test:fail': 740 callback(null, `test ${event.data.name} failed`); 741 break; 742 case 'test:plan': 743 callback(null, 'test plan'); 744 break; 745 case 'test:diagnostic': 746 case 'test:stderr': 747 case 'test:stdout': 748 callback(null, event.data.message); 749 break; 750 case 'test:coverage': { 751 const { totalLineCount } = event.data.summary.totals; 752 callback(null, `total line count: ${totalLineCount}\n`); 753 break; 754 } 755 } 756 }, 757}); 758 759module.exports = customReporter; 760``` 761 762Example of a custom reporter using a generator function: 763 764```mjs 765export default async function * customReporter(source) { 766 for await (const event of source) { 767 switch (event.type) { 768 case 'test:dequeue': 769 yield `test ${event.data.name} dequeued`; 770 break; 771 case 'test:enqueue': 772 yield `test ${event.data.name} enqueued`; 773 break; 774 case 'test:watch:drained': 775 yield 'test watch queue drained'; 776 break; 777 case 'test:start': 778 yield `test ${event.data.name} started\n`; 779 break; 780 case 'test:pass': 781 yield `test ${event.data.name} passed\n`; 782 break; 783 case 'test:fail': 784 yield `test ${event.data.name} failed\n`; 785 break; 786 case 'test:plan': 787 yield 'test plan'; 788 break; 789 case 'test:diagnostic': 790 case 'test:stderr': 791 case 'test:stdout': 792 yield `${event.data.message}\n`; 793 break; 794 case 'test:coverage': { 795 const { totalLineCount } = event.data.summary.totals; 796 yield `total line count: ${totalLineCount}\n`; 797 break; 798 } 799 } 800 } 801} 802``` 803 804```cjs 805module.exports = async function * customReporter(source) { 806 for await (const event of source) { 807 switch (event.type) { 808 case 'test:dequeue': 809 yield `test ${event.data.name} dequeued`; 810 break; 811 case 'test:enqueue': 812 yield `test ${event.data.name} enqueued`; 813 break; 814 case 'test:watch:drained': 815 yield 'test watch queue drained'; 816 break; 817 case 'test:start': 818 yield `test ${event.data.name} started\n`; 819 break; 820 case 'test:pass': 821 yield `test ${event.data.name} passed\n`; 822 break; 823 case 'test:fail': 824 yield `test ${event.data.name} failed\n`; 825 break; 826 case 'test:plan': 827 yield 'test plan\n'; 828 break; 829 case 'test:diagnostic': 830 case 'test:stderr': 831 case 'test:stdout': 832 yield `${event.data.message}\n`; 833 break; 834 case 'test:coverage': { 835 const { totalLineCount } = event.data.summary.totals; 836 yield `total line count: ${totalLineCount}\n`; 837 break; 838 } 839 } 840 } 841}; 842``` 843 844The value provided to `--test-reporter` should be a string like one used in an 845`import()` in JavaScript code. 846 847### Multiple reporters 848 849The [`--test-reporter`][] flag can be specified multiple times to report test 850results in several formats. In this situation 851it is required to specify a destination for each reporter 852using [`--test-reporter-destination`][]. 853Destination can be `stdout`, `stderr`, or a file path. 854Reporters and destinations are paired according 855to the order they were specified. 856 857In the following example, the `spec` reporter will output to `stdout`, 858and the `dot` reporter will output to `file.txt`: 859 860```bash 861node --test-reporter=spec --test-reporter=dot --test-reporter-destination=stdout --test-reporter-destination=file.txt 862``` 863 864When a single reporter is specified, the destination will default to `stdout`, 865unless a destination is explicitly provided. 866 867## `run([options])` 868 869<!-- YAML 870added: v18.9.0 871changes: 872 - version: v18.17.0 873 pr-url: https://github.com/nodejs/node/pull/47628 874 description: Add a testNamePatterns option. 875--> 876 877* `options` {Object} Configuration options for running tests. The following 878 properties are supported: 879 * `concurrency` {number|boolean} If a number is provided, 880 then that many test processes would run in parallel, where each process 881 corresponds to one test file. 882 If `true`, it would run `os.availableParallelism() - 1` test files in 883 parallel. 884 If `false`, it would only run one test file at a time. 885 **Default:** `false`. 886 * `files`: {Array} An array containing the list of files to run. 887 **Default** matching files from [test runner execution model][]. 888 * `inspectPort` {number|Function} Sets inspector port of test child process. 889 This can be a number, or a function that takes no arguments and returns a 890 number. If a nullish value is provided, each process gets its own port, 891 incremented from the primary's `process.debugPort`. 892 **Default:** `undefined`. 893 * `only`: {boolean} If truthy, the test context will only run tests that 894 have the `only` option set 895 * `setup` {Function} A function that accepts the `TestsStream` instance 896 and can be used to setup listeners before any tests are run. 897 **Default:** `undefined`. 898 * `signal` {AbortSignal} Allows aborting an in-progress test execution. 899 * `testNamePatterns` {string|RegExp|Array} A String, RegExp or a RegExp Array, 900 that can be used to only run tests whose name matches the provided pattern. 901 Test name patterns are interpreted as JavaScript regular expressions. 902 For each test that is executed, any corresponding test hooks, such as 903 `beforeEach()`, are also run. 904 **Default:** `undefined`. 905 * `timeout` {number} A number of milliseconds the test execution will 906 fail after. 907 If unspecified, subtests inherit this value from their parent. 908 **Default:** `Infinity`. 909 * `watch` {boolean} Whether to run in watch mode or not. **Default:** `false`. 910 * `shard` {Object} Running tests in a specific shard. **Default:** `undefined`. 911 * `index` {number} is a positive integer between 1 and `<total>` 912 that specifies the index of the shard to run. This option is _required_. 913 * `total` {number} is a positive integer that specifies the total number 914 of shards to split the test files to. This option is _required_. 915* Returns: {TestsStream} 916 917```mjs 918import { tap } from 'node:test/reporters'; 919import process from 'node:process'; 920 921run({ files: [path.resolve('./tests/test.js')] }) 922 .compose(tap) 923 .pipe(process.stdout); 924``` 925 926```cjs 927const { tap } = require('node:test/reporters'); 928 929run({ files: [path.resolve('./tests/test.js')] }) 930 .compose(tap) 931 .pipe(process.stdout); 932``` 933 934## `test([name][, options][, fn])` 935 936<!-- YAML 937added: v18.0.0 938changes: 939 - version: v18.17.0 940 pr-url: https://github.com/nodejs/node/pull/47909 941 description: Added the `skip`, `todo`, and `only` shorthands. 942 - version: v18.8.0 943 pr-url: https://github.com/nodejs/node/pull/43554 944 description: Add a `signal` option. 945 - version: v18.7.0 946 pr-url: https://github.com/nodejs/node/pull/43505 947 description: Add a `timeout` option. 948--> 949 950* `name` {string} The name of the test, which is displayed when reporting test 951 results. **Default:** The `name` property of `fn`, or `'<anonymous>'` if `fn` 952 does not have a name. 953* `options` {Object} Configuration options for the test. The following 954 properties are supported: 955 * `concurrency` {number|boolean} If a number is provided, 956 then that many tests would run in parallel within the application thread. 957 If `true`, all scheduled asynchronous tests run concurrently within the 958 thread. If `false`, only one test runs at a time. 959 If unspecified, subtests inherit this value from their parent. 960 **Default:** `false`. 961 * `only` {boolean} If truthy, and the test context is configured to run 962 `only` tests, then this test will be run. Otherwise, the test is skipped. 963 **Default:** `false`. 964 * `signal` {AbortSignal} Allows aborting an in-progress test. 965 * `skip` {boolean|string} If truthy, the test is skipped. If a string is 966 provided, that string is displayed in the test results as the reason for 967 skipping the test. **Default:** `false`. 968 * `todo` {boolean|string} If truthy, the test marked as `TODO`. If a string 969 is provided, that string is displayed in the test results as the reason why 970 the test is `TODO`. **Default:** `false`. 971 * `timeout` {number} A number of milliseconds the test will fail after. 972 If unspecified, subtests inherit this value from their parent. 973 **Default:** `Infinity`. 974* `fn` {Function|AsyncFunction} The function under test. The first argument 975 to this function is a [`TestContext`][] object. If the test uses callbacks, 976 the callback function is passed as the second argument. **Default:** A no-op 977 function. 978* Returns: {Promise} Resolved with `undefined` once 979 the test completes, or immediately if the test runs within [`describe()`][]. 980 981The `test()` function is the value imported from the `test` module. Each 982invocation of this function results in reporting the test to the {TestsStream}. 983 984The `TestContext` object passed to the `fn` argument can be used to perform 985actions related to the current test. Examples include skipping the test, adding 986additional diagnostic information, or creating subtests. 987 988`test()` returns a `Promise` that resolves once the test completes. 989if `test()` is called within a `describe()` block, it resolve immediately. 990The return value can usually be discarded for top level tests. 991However, the return value from subtests should be used to prevent the parent 992test from finishing first and cancelling the subtest 993as shown in the following example. 994 995```js 996test('top level test', async (t) => { 997 // The setTimeout() in the following subtest would cause it to outlive its 998 // parent test if 'await' is removed on the next line. Once the parent test 999 // completes, it will cancel any outstanding subtests. 1000 await t.test('longer running subtest', async (t) => { 1001 return new Promise((resolve, reject) => { 1002 setTimeout(resolve, 1000); 1003 }); 1004 }); 1005}); 1006``` 1007 1008The `timeout` option can be used to fail the test if it takes longer than 1009`timeout` milliseconds to complete. However, it is not a reliable mechanism for 1010canceling tests because a running test might block the application thread and 1011thus prevent the scheduled cancellation. 1012 1013## `test.skip([name][, options][, fn])` 1014 1015Shorthand for skipping a test, 1016same as [`test([name], { skip: true }[, fn])`][it options]. 1017 1018## `test.todo([name][, options][, fn])` 1019 1020Shorthand for marking a test as `TODO`, 1021same as [`test([name], { todo: true }[, fn])`][it options]. 1022 1023## `test.only([name][, options][, fn])` 1024 1025Shorthand for marking a test as `only`, 1026same as [`test([name], { only: true }[, fn])`][it options]. 1027 1028## `describe([name][, options][, fn])` 1029 1030* `name` {string} The name of the suite, which is displayed when reporting test 1031 results. **Default:** The `name` property of `fn`, or `'<anonymous>'` if `fn` 1032 does not have a name. 1033* `options` {Object} Configuration options for the suite. 1034 supports the same options as `test([name][, options][, fn])`. 1035* `fn` {Function|AsyncFunction} The function under suite 1036 declaring all subtests and subsuites. 1037 The first argument to this function is a [`SuiteContext`][] object. 1038 **Default:** A no-op function. 1039* Returns: {Promise} Immediately fulfilled with `undefined`. 1040 1041The `describe()` function imported from the `node:test` module. Each 1042invocation of this function results in the creation of a Subtest. 1043After invocation of top level `describe` functions, 1044all top level tests and suites will execute. 1045 1046## `describe.skip([name][, options][, fn])` 1047 1048Shorthand for skipping a suite, same as [`describe([name], { skip: true }[, fn])`][describe options]. 1049 1050## `describe.todo([name][, options][, fn])` 1051 1052Shorthand for marking a suite as `TODO`, same as 1053[`describe([name], { todo: true }[, fn])`][describe options]. 1054 1055## `describe.only([name][, options][, fn])` 1056 1057<!-- YAML 1058added: v18.15.0 1059--> 1060 1061Shorthand for marking a suite as `only`, same as 1062[`describe([name], { only: true }[, fn])`][describe options]. 1063 1064## `it([name][, options][, fn])` 1065 1066<!-- YAML 1067added: 1068 - v18.6.0 1069 - v16.17.0 1070changes: 1071 - version: v18.16.0 1072 pr-url: https://github.com/nodejs/node/pull/46889 1073 description: Calling `it()` is now equivalent to calling `test()`. 1074--> 1075 1076Shorthand for [`test()`][]. 1077 1078The `it()` function is imported from the `node:test` module. 1079 1080## `it.skip([name][, options][, fn])` 1081 1082Shorthand for skipping a test, 1083same as [`it([name], { skip: true }[, fn])`][it options]. 1084 1085## `it.todo([name][, options][, fn])` 1086 1087Shorthand for marking a test as `TODO`, 1088same as [`it([name], { todo: true }[, fn])`][it options]. 1089 1090## `it.only([name][, options][, fn])` 1091 1092<!-- YAML 1093added: v18.15.0 1094--> 1095 1096Shorthand for marking a test as `only`, 1097same as [`it([name], { only: true }[, fn])`][it options]. 1098 1099## `before([fn][, options])` 1100 1101<!-- YAML 1102added: v18.8.0 1103--> 1104 1105* `fn` {Function|AsyncFunction} The hook function. 1106 If the hook uses callbacks, 1107 the callback function is passed as the second argument. **Default:** A no-op 1108 function. 1109* `options` {Object} Configuration options for the hook. The following 1110 properties are supported: 1111 * `signal` {AbortSignal} Allows aborting an in-progress hook. 1112 * `timeout` {number} A number of milliseconds the hook will fail after. 1113 If unspecified, subtests inherit this value from their parent. 1114 **Default:** `Infinity`. 1115 1116This function is used to create a hook running before running a suite. 1117 1118```js 1119describe('tests', async () => { 1120 before(() => console.log('about to run some test')); 1121 it('is a subtest', () => { 1122 assert.ok('some relevant assertion here'); 1123 }); 1124}); 1125``` 1126 1127## `after([fn][, options])` 1128 1129<!-- YAML 1130added: v18.8.0 1131--> 1132 1133* `fn` {Function|AsyncFunction} The hook function. 1134 If the hook uses callbacks, 1135 the callback function is passed as the second argument. **Default:** A no-op 1136 function. 1137* `options` {Object} Configuration options for the hook. The following 1138 properties are supported: 1139 * `signal` {AbortSignal} Allows aborting an in-progress hook. 1140 * `timeout` {number} A number of milliseconds the hook will fail after. 1141 If unspecified, subtests inherit this value from their parent. 1142 **Default:** `Infinity`. 1143 1144This function is used to create a hook running after running a suite. 1145 1146```js 1147describe('tests', async () => { 1148 after(() => console.log('finished running tests')); 1149 it('is a subtest', () => { 1150 assert.ok('some relevant assertion here'); 1151 }); 1152}); 1153``` 1154 1155## `beforeEach([fn][, options])` 1156 1157<!-- YAML 1158added: v18.8.0 1159--> 1160 1161* `fn` {Function|AsyncFunction} The hook function. 1162 If the hook uses callbacks, 1163 the callback function is passed as the second argument. **Default:** A no-op 1164 function. 1165* `options` {Object} Configuration options for the hook. The following 1166 properties are supported: 1167 * `signal` {AbortSignal} Allows aborting an in-progress hook. 1168 * `timeout` {number} A number of milliseconds the hook will fail after. 1169 If unspecified, subtests inherit this value from their parent. 1170 **Default:** `Infinity`. 1171 1172This function is used to create a hook running 1173before each subtest of the current suite. 1174 1175```js 1176describe('tests', async () => { 1177 beforeEach(() => console.log('about to run a test')); 1178 it('is a subtest', () => { 1179 assert.ok('some relevant assertion here'); 1180 }); 1181}); 1182``` 1183 1184## `afterEach([fn][, options])` 1185 1186<!-- YAML 1187added: v18.8.0 1188--> 1189 1190* `fn` {Function|AsyncFunction} The hook function. 1191 If the hook uses callbacks, 1192 the callback function is passed as the second argument. **Default:** A no-op 1193 function. 1194* `options` {Object} Configuration options for the hook. The following 1195 properties are supported: 1196 * `signal` {AbortSignal} Allows aborting an in-progress hook. 1197 * `timeout` {number} A number of milliseconds the hook will fail after. 1198 If unspecified, subtests inherit this value from their parent. 1199 **Default:** `Infinity`. 1200 1201This function is used to create a hook running 1202after each subtest of the current test. 1203 1204```js 1205describe('tests', async () => { 1206 afterEach(() => console.log('finished running a test')); 1207 it('is a subtest', () => { 1208 assert.ok('some relevant assertion here'); 1209 }); 1210}); 1211``` 1212 1213## Class: `MockFunctionContext` 1214 1215<!-- YAML 1216added: v18.13.0 1217--> 1218 1219The `MockFunctionContext` class is used to inspect or manipulate the behavior of 1220mocks created via the [`MockTracker`][] APIs. 1221 1222### `ctx.calls` 1223 1224<!-- YAML 1225added: v18.13.0 1226--> 1227 1228* {Array} 1229 1230A getter that returns a copy of the internal array used to track calls to the 1231mock. Each entry in the array is an object with the following properties. 1232 1233* `arguments` {Array} An array of the arguments passed to the mock function. 1234* `error` {any} If the mocked function threw then this property contains the 1235 thrown value. **Default:** `undefined`. 1236* `result` {any} The value returned by the mocked function. 1237* `stack` {Error} An `Error` object whose stack can be used to determine the 1238 callsite of the mocked function invocation. 1239* `target` {Function|undefined} If the mocked function is a constructor, this 1240 field contains the class being constructed. Otherwise this will be 1241 `undefined`. 1242* `this` {any} The mocked function's `this` value. 1243 1244### `ctx.callCount()` 1245 1246<!-- YAML 1247added: v18.13.0 1248--> 1249 1250* Returns: {integer} The number of times that this mock has been invoked. 1251 1252This function returns the number of times that this mock has been invoked. This 1253function is more efficient than checking `ctx.calls.length` because `ctx.calls` 1254is a getter that creates a copy of the internal call tracking array. 1255 1256### `ctx.mockImplementation(implementation)` 1257 1258<!-- YAML 1259added: v18.13.0 1260--> 1261 1262* `implementation` {Function|AsyncFunction} The function to be used as the 1263 mock's new implementation. 1264 1265This function is used to change the behavior of an existing mock. 1266 1267The following example creates a mock function using `t.mock.fn()`, calls the 1268mock function, and then changes the mock implementation to a different function. 1269 1270```js 1271test('changes a mock behavior', (t) => { 1272 let cnt = 0; 1273 1274 function addOne() { 1275 cnt++; 1276 return cnt; 1277 } 1278 1279 function addTwo() { 1280 cnt += 2; 1281 return cnt; 1282 } 1283 1284 const fn = t.mock.fn(addOne); 1285 1286 assert.strictEqual(fn(), 1); 1287 fn.mock.mockImplementation(addTwo); 1288 assert.strictEqual(fn(), 3); 1289 assert.strictEqual(fn(), 5); 1290}); 1291``` 1292 1293### `ctx.mockImplementationOnce(implementation[, onCall])` 1294 1295<!-- YAML 1296added: v18.13.0 1297--> 1298 1299* `implementation` {Function|AsyncFunction} The function to be used as the 1300 mock's implementation for the invocation number specified by `onCall`. 1301* `onCall` {integer} The invocation number that will use `implementation`. If 1302 the specified invocation has already occurred then an exception is thrown. 1303 **Default:** The number of the next invocation. 1304 1305This function is used to change the behavior of an existing mock for a single 1306invocation. Once invocation `onCall` has occurred, the mock will revert to 1307whatever behavior it would have used had `mockImplementationOnce()` not been 1308called. 1309 1310The following example creates a mock function using `t.mock.fn()`, calls the 1311mock function, changes the mock implementation to a different function for the 1312next invocation, and then resumes its previous behavior. 1313 1314```js 1315test('changes a mock behavior once', (t) => { 1316 let cnt = 0; 1317 1318 function addOne() { 1319 cnt++; 1320 return cnt; 1321 } 1322 1323 function addTwo() { 1324 cnt += 2; 1325 return cnt; 1326 } 1327 1328 const fn = t.mock.fn(addOne); 1329 1330 assert.strictEqual(fn(), 1); 1331 fn.mock.mockImplementationOnce(addTwo); 1332 assert.strictEqual(fn(), 3); 1333 assert.strictEqual(fn(), 4); 1334}); 1335``` 1336 1337### `ctx.resetCalls()` 1338 1339<!-- YAML 1340added: v18.13.0 1341--> 1342 1343Resets the call history of the mock function. 1344 1345### `ctx.restore()` 1346 1347<!-- YAML 1348added: v18.13.0 1349--> 1350 1351Resets the implementation of the mock function to its original behavior. The 1352mock can still be used after calling this function. 1353 1354## Class: `MockTracker` 1355 1356<!-- YAML 1357added: v18.13.0 1358--> 1359 1360The `MockTracker` class is used to manage mocking functionality. The test runner 1361module provides a top level `mock` export which is a `MockTracker` instance. 1362Each test also provides its own `MockTracker` instance via the test context's 1363`mock` property. 1364 1365### `mock.fn([original[, implementation]][, options])` 1366 1367<!-- YAML 1368added: v18.13.0 1369--> 1370 1371* `original` {Function|AsyncFunction} An optional function to create a mock on. 1372 **Default:** A no-op function. 1373* `implementation` {Function|AsyncFunction} An optional function used as the 1374 mock implementation for `original`. This is useful for creating mocks that 1375 exhibit one behavior for a specified number of calls and then restore the 1376 behavior of `original`. **Default:** The function specified by `original`. 1377* `options` {Object} Optional configuration options for the mock function. The 1378 following properties are supported: 1379 * `times` {integer} The number of times that the mock will use the behavior of 1380 `implementation`. Once the mock function has been called `times` times, it 1381 will automatically restore the behavior of `original`. This value must be an 1382 integer greater than zero. **Default:** `Infinity`. 1383* Returns: {Proxy} The mocked function. The mocked function contains a special 1384 `mock` property, which is an instance of [`MockFunctionContext`][], and can 1385 be used for inspecting and changing the behavior of the mocked function. 1386 1387This function is used to create a mock function. 1388 1389The following example creates a mock function that increments a counter by one 1390on each invocation. The `times` option is used to modify the mock behavior such 1391that the first two invocations add two to the counter instead of one. 1392 1393```js 1394test('mocks a counting function', (t) => { 1395 let cnt = 0; 1396 1397 function addOne() { 1398 cnt++; 1399 return cnt; 1400 } 1401 1402 function addTwo() { 1403 cnt += 2; 1404 return cnt; 1405 } 1406 1407 const fn = t.mock.fn(addOne, addTwo, { times: 2 }); 1408 1409 assert.strictEqual(fn(), 2); 1410 assert.strictEqual(fn(), 4); 1411 assert.strictEqual(fn(), 5); 1412 assert.strictEqual(fn(), 6); 1413}); 1414``` 1415 1416### `mock.getter(object, methodName[, implementation][, options])` 1417 1418<!-- YAML 1419added: v18.13.0 1420--> 1421 1422This function is syntax sugar for [`MockTracker.method`][] with `options.getter` 1423set to `true`. 1424 1425### `mock.method(object, methodName[, implementation][, options])` 1426 1427<!-- YAML 1428added: v18.13.0 1429--> 1430 1431* `object` {Object} The object whose method is being mocked. 1432* `methodName` {string|symbol} The identifier of the method on `object` to mock. 1433 If `object[methodName]` is not a function, an error is thrown. 1434* `implementation` {Function|AsyncFunction} An optional function used as the 1435 mock implementation for `object[methodName]`. **Default:** The original method 1436 specified by `object[methodName]`. 1437* `options` {Object} Optional configuration options for the mock method. The 1438 following properties are supported: 1439 * `getter` {boolean} If `true`, `object[methodName]` is treated as a getter. 1440 This option cannot be used with the `setter` option. **Default:** false. 1441 * `setter` {boolean} If `true`, `object[methodName]` is treated as a setter. 1442 This option cannot be used with the `getter` option. **Default:** false. 1443 * `times` {integer} The number of times that the mock will use the behavior of 1444 `implementation`. Once the mocked method has been called `times` times, it 1445 will automatically restore the original behavior. This value must be an 1446 integer greater than zero. **Default:** `Infinity`. 1447* Returns: {Proxy} The mocked method. The mocked method contains a special 1448 `mock` property, which is an instance of [`MockFunctionContext`][], and can 1449 be used for inspecting and changing the behavior of the mocked method. 1450 1451This function is used to create a mock on an existing object method. The 1452following example demonstrates how a mock is created on an existing object 1453method. 1454 1455```js 1456test('spies on an object method', (t) => { 1457 const number = { 1458 value: 5, 1459 subtract(a) { 1460 return this.value - a; 1461 }, 1462 }; 1463 1464 t.mock.method(number, 'subtract'); 1465 assert.strictEqual(number.subtract.mock.calls.length, 0); 1466 assert.strictEqual(number.subtract(3), 2); 1467 assert.strictEqual(number.subtract.mock.calls.length, 1); 1468 1469 const call = number.subtract.mock.calls[0]; 1470 1471 assert.deepStrictEqual(call.arguments, [3]); 1472 assert.strictEqual(call.result, 2); 1473 assert.strictEqual(call.error, undefined); 1474 assert.strictEqual(call.target, undefined); 1475 assert.strictEqual(call.this, number); 1476}); 1477``` 1478 1479### `mock.reset()` 1480 1481<!-- YAML 1482added: v18.13.0 1483--> 1484 1485This function restores the default behavior of all mocks that were previously 1486created by this `MockTracker` and disassociates the mocks from the 1487`MockTracker` instance. Once disassociated, the mocks can still be used, but the 1488`MockTracker` instance can no longer be used to reset their behavior or 1489otherwise interact with them. 1490 1491After each test completes, this function is called on the test context's 1492`MockTracker`. If the global `MockTracker` is used extensively, calling this 1493function manually is recommended. 1494 1495### `mock.restoreAll()` 1496 1497<!-- YAML 1498added: v18.13.0 1499--> 1500 1501This function restores the default behavior of all mocks that were previously 1502created by this `MockTracker`. Unlike `mock.reset()`, `mock.restoreAll()` does 1503not disassociate the mocks from the `MockTracker` instance. 1504 1505### `mock.setter(object, methodName[, implementation][, options])` 1506 1507<!-- YAML 1508added: v18.13.0 1509--> 1510 1511This function is syntax sugar for [`MockTracker.method`][] with `options.setter` 1512set to `true`. 1513 1514## Class: `MockTimers` 1515 1516<!-- YAML 1517added: 1518 - v18.19.0 1519--> 1520 1521> Stability: 1 - Experimental 1522 1523Mocking timers is a technique commonly used in software testing to simulate and 1524control the behavior of timers, such as `setInterval` and `setTimeout`, 1525without actually waiting for the specified time intervals. 1526 1527The [`MockTracker`][] provides a top-level `timers` export 1528which is a `MockTimers` instance. 1529 1530### `timers.enable([timers])` 1531 1532<!-- YAML 1533added: 1534 - v18.19.0 1535--> 1536 1537Enables timer mocking for the specified timers. 1538 1539* `timers` {Array} An optional array containing the timers to mock. 1540 The currently supported timer values are `'setInterval'`, `'setTimeout'`, 1541 and `'setImmediate'`. If no value is provided, all timers (`'setInterval'`, 1542 `'clearInterval'`, `'setTimeout'`, `'clearTimeout'`, `'setImmediate'`, 1543 and `'clearImmediate'`) will be mocked by default. 1544 1545**Note:** When you enable mocking for a specific timer, its associated 1546clear function will also be implicitly mocked. 1547 1548Example usage: 1549 1550```mjs 1551import { mock } from 'node:test'; 1552mock.timers.enable(['setInterval']); 1553``` 1554 1555```cjs 1556const { mock } = require('node:test'); 1557mock.timers.enable(['setInterval']); 1558``` 1559 1560The above example enables mocking for the `setInterval` timer and 1561implicitly mocks the `clearInterval` function. Only the `setInterval` 1562and `clearInterval` functions from [node:timers](./timers.md), 1563[node:timers/promises](./timers.md#timers-promises-api), and 1564`globalThis` will be mocked. 1565 1566Alternatively, if you call `mock.timers.enable()` without any parameters: 1567 1568All timers (`'setInterval'`, `'clearInterval'`, `'setTimeout'`, and `'clearTimeout'`) 1569will be mocked. The `setInterval`, `clearInterval`, `setTimeout`, and `clearTimeout` 1570functions from `node:timers`, `node:timers/promises`, 1571and `globalThis` will be mocked. 1572 1573### `timers.reset()` 1574 1575<!-- YAML 1576added: 1577 - v18.19.0 1578--> 1579 1580This function restores the default behavior of all mocks that were previously 1581created by this `MockTimers` instance and disassociates the mocks 1582from the `MockTracker` instance. 1583 1584**Note:** After each test completes, this function is called on 1585the test context's `MockTracker`. 1586 1587```mjs 1588import { mock } from 'node:test'; 1589mock.timers.reset(); 1590``` 1591 1592```cjs 1593const { mock } = require('node:test'); 1594mock.timers.reset(); 1595``` 1596 1597### `timers[Symbol.dispose]()` 1598 1599Calls `timers.reset()`. 1600 1601### `timers.tick(milliseconds)` 1602 1603<!-- YAML 1604added: 1605 - v18.19.0 1606--> 1607 1608Advances time for all mocked timers. 1609 1610* `milliseconds` {number} The amount of time, in milliseconds, 1611 to advance the timers. 1612 1613**Note:** This diverges from how `setTimeout` in Node.js behaves and accepts 1614only positive numbers. In Node.js, `setTimeout` with negative numbers is 1615only supported for web compatibility reasons. 1616 1617The following example mocks a `setTimeout` function and 1618by using `.tick` advances in 1619time triggering all pending timers. 1620 1621```mjs 1622import assert from 'node:assert'; 1623import { test } from 'node:test'; 1624 1625test('mocks setTimeout to be executed synchronously without having to actually wait for it', (context) => { 1626 const fn = context.mock.fn(); 1627 1628 context.mock.timers.enable(['setTimeout']); 1629 1630 setTimeout(fn, 9999); 1631 1632 assert.strictEqual(fn.mock.callCount(), 0); 1633 1634 // Advance in time 1635 context.mock.timers.tick(9999); 1636 1637 assert.strictEqual(fn.mock.callCount(), 1); 1638}); 1639``` 1640 1641```cjs 1642const assert = require('node:assert'); 1643const { test } = require('node:test'); 1644 1645test('mocks setTimeout to be executed synchronously without having to actually wait for it', (context) => { 1646 const fn = context.mock.fn(); 1647 context.mock.timers.enable(['setTimeout']); 1648 1649 setTimeout(fn, 9999); 1650 assert.strictEqual(fn.mock.callCount(), 0); 1651 1652 // Advance in time 1653 context.mock.timers.tick(9999); 1654 1655 assert.strictEqual(fn.mock.callCount(), 1); 1656}); 1657``` 1658 1659Alternativelly, the `.tick` function can be called many times 1660 1661```mjs 1662import assert from 'node:assert'; 1663import { test } from 'node:test'; 1664 1665test('mocks setTimeout to be executed synchronously without having to actually wait for it', (context) => { 1666 const fn = context.mock.fn(); 1667 context.mock.timers.enable(['setTimeout']); 1668 const nineSecs = 9000; 1669 setTimeout(fn, nineSecs); 1670 1671 const twoSeconds = 3000; 1672 context.mock.timers.tick(twoSeconds); 1673 context.mock.timers.tick(twoSeconds); 1674 context.mock.timers.tick(twoSeconds); 1675 1676 assert.strictEqual(fn.mock.callCount(), 1); 1677}); 1678``` 1679 1680```cjs 1681const assert = require('node:assert'); 1682const { test } = require('node:test'); 1683 1684test('mocks setTimeout to be executed synchronously without having to actually wait for it', (context) => { 1685 const fn = context.mock.fn(); 1686 context.mock.timers.enable(['setTimeout']); 1687 const nineSecs = 9000; 1688 setTimeout(fn, nineSecs); 1689 1690 const twoSeconds = 3000; 1691 context.mock.timers.tick(twoSeconds); 1692 context.mock.timers.tick(twoSeconds); 1693 context.mock.timers.tick(twoSeconds); 1694 1695 assert.strictEqual(fn.mock.callCount(), 1); 1696}); 1697``` 1698 1699#### Using clear functions 1700 1701As mentioned, all clear functions from timers (`clearTimeout` and `clearInterval`) 1702are implicity mocked. Take a look at this example using `setTimeout`: 1703 1704```mjs 1705import assert from 'node:assert'; 1706import { test } from 'node:test'; 1707 1708test('mocks setTimeout to be executed synchronously without having to actually wait for it', (context) => { 1709 const fn = context.mock.fn(); 1710 1711 // Optionally choose what to mock 1712 context.mock.timers.enable(['setTimeout']); 1713 const id = setTimeout(fn, 9999); 1714 1715 // Implicity mocked as well 1716 clearTimeout(id); 1717 context.mock.timers.tick(9999); 1718 1719 // As that setTimeout was cleared the mock function will never be called 1720 assert.strictEqual(fn.mock.callCount(), 0); 1721}); 1722``` 1723 1724```cjs 1725const assert = require('node:assert'); 1726const { test } = require('node:test'); 1727 1728test('mocks setTimeout to be executed synchronously without having to actually wait for it', (context) => { 1729 const fn = context.mock.fn(); 1730 1731 // Optionally choose what to mock 1732 context.mock.timers.enable(['setTimeout']); 1733 const id = setTimeout(fn, 9999); 1734 1735 // Implicity mocked as well 1736 clearTimeout(id); 1737 context.mock.timers.tick(9999); 1738 1739 // As that setTimeout was cleared the mock function will never be called 1740 assert.strictEqual(fn.mock.callCount(), 0); 1741}); 1742``` 1743 1744#### Working with Node.js timers modules 1745 1746Once you enable mocking timers, [node:timers](./timers.md), 1747[node:timers/promises](./timers.md#timers-promises-api) modules, 1748and timers from the Node.js global context are enabled: 1749 1750**Note:** Destructuring functions such as 1751`import { setTimeout } from 'node:timers'` is currently 1752not supported by this API. 1753 1754```mjs 1755import assert from 'node:assert'; 1756import { test } from 'node:test'; 1757import nodeTimers from 'node:timers'; 1758import nodeTimersPromises from 'node:timers/promises'; 1759 1760test('mocks setTimeout to be executed synchronously without having to actually wait for it', async (context) => { 1761 const globalTimeoutObjectSpy = context.mock.fn(); 1762 const nodeTimerSpy = context.mock.fn(); 1763 const nodeTimerPromiseSpy = context.mock.fn(); 1764 1765 // Optionally choose what to mock 1766 context.mock.timers.enable(['setTimeout']); 1767 setTimeout(globalTimeoutObjectSpy, 9999); 1768 nodeTimers.setTimeout(nodeTimerSpy, 9999); 1769 1770 const promise = nodeTimersPromises.setTimeout(9999).then(nodeTimerPromiseSpy); 1771 1772 // Advance in time 1773 context.mock.timers.tick(9999); 1774 assert.strictEqual(globalTimeoutObjectSpy.mock.callCount(), 1); 1775 assert.strictEqual(nodeTimerSpy.mock.callCount(), 1); 1776 await promise; 1777 assert.strictEqual(nodeTimerPromiseSpy.mock.callCount(), 1); 1778}); 1779``` 1780 1781```cjs 1782const assert = require('node:assert'); 1783const { test } = require('node:test'); 1784const nodeTimers = require('node:timers'); 1785const nodeTimersPromises = require('node:timers/promises'); 1786 1787test('mocks setTimeout to be executed synchronously without having to actually wait for it', async (context) => { 1788 const globalTimeoutObjectSpy = context.mock.fn(); 1789 const nodeTimerSpy = context.mock.fn(); 1790 const nodeTimerPromiseSpy = context.mock.fn(); 1791 1792 // Optionally choose what to mock 1793 context.mock.timers.enable(['setTimeout']); 1794 setTimeout(globalTimeoutObjectSpy, 9999); 1795 nodeTimers.setTimeout(nodeTimerSpy, 9999); 1796 1797 const promise = nodeTimersPromises.setTimeout(9999).then(nodeTimerPromiseSpy); 1798 1799 // Advance in time 1800 context.mock.timers.tick(9999); 1801 assert.strictEqual(globalTimeoutObjectSpy.mock.callCount(), 1); 1802 assert.strictEqual(nodeTimerSpy.mock.callCount(), 1); 1803 await promise; 1804 assert.strictEqual(nodeTimerPromiseSpy.mock.callCount(), 1); 1805}); 1806``` 1807 1808In Node.js, `setInterval` from [node:timers/promises](./timers.md#timers-promises-api) 1809is an `AsyncGenerator` and is also supported by this API: 1810 1811```mjs 1812import assert from 'node:assert'; 1813import { test } from 'node:test'; 1814import nodeTimersPromises from 'node:timers/promises'; 1815test('should tick five times testing a real use case', async (context) => { 1816 context.mock.timers.enable(['setInterval']); 1817 1818 const expectedIterations = 3; 1819 const interval = 1000; 1820 const startedAt = Date.now(); 1821 async function run() { 1822 const times = []; 1823 for await (const time of nodeTimersPromises.setInterval(interval, startedAt)) { 1824 times.push(time); 1825 if (times.length === expectedIterations) break; 1826 } 1827 return times; 1828 } 1829 1830 const r = run(); 1831 context.mock.timers.tick(interval); 1832 context.mock.timers.tick(interval); 1833 context.mock.timers.tick(interval); 1834 1835 const timeResults = await r; 1836 assert.strictEqual(timeResults.length, expectedIterations); 1837 for (let it = 1; it < expectedIterations; it++) { 1838 assert.strictEqual(timeResults[it - 1], startedAt + (interval * it)); 1839 } 1840}); 1841``` 1842 1843```cjs 1844const assert = require('node:assert'); 1845const { test } = require('node:test'); 1846const nodeTimersPromises = require('node:timers/promises'); 1847test('should tick five times testing a real use case', async (context) => { 1848 context.mock.timers.enable(['setInterval']); 1849 1850 const expectedIterations = 3; 1851 const interval = 1000; 1852 const startedAt = Date.now(); 1853 async function run() { 1854 const times = []; 1855 for await (const time of nodeTimersPromises.setInterval(interval, startedAt)) { 1856 times.push(time); 1857 if (times.length === expectedIterations) break; 1858 } 1859 return times; 1860 } 1861 1862 const r = run(); 1863 context.mock.timers.tick(interval); 1864 context.mock.timers.tick(interval); 1865 context.mock.timers.tick(interval); 1866 1867 const timeResults = await r; 1868 assert.strictEqual(timeResults.length, expectedIterations); 1869 for (let it = 1; it < expectedIterations; it++) { 1870 assert.strictEqual(timeResults[it - 1], startedAt + (interval * it)); 1871 } 1872}); 1873``` 1874 1875### `timers.runAll()` 1876 1877<!-- YAML 1878added: 1879 - v18.19.0 1880--> 1881 1882Triggers all pending mocked timers immediately. 1883 1884The example below triggers all pending timers immediately, 1885causing them to execute without any delay. 1886 1887```mjs 1888import assert from 'node:assert'; 1889import { test } from 'node:test'; 1890 1891test('runAll functions following the given order', (context) => { 1892 context.mock.timers.enable(['setTimeout']); 1893 const results = []; 1894 setTimeout(() => results.push(1), 9999); 1895 1896 // Notice that if both timers have the same timeout, 1897 // the order of execution is guaranteed 1898 setTimeout(() => results.push(3), 8888); 1899 setTimeout(() => results.push(2), 8888); 1900 1901 assert.deepStrictEqual(results, []); 1902 1903 context.mock.timers.runAll(); 1904 1905 assert.deepStrictEqual(results, [3, 2, 1]); 1906}); 1907``` 1908 1909```cjs 1910const assert = require('node:assert'); 1911const { test } = require('node:test'); 1912 1913test('runAll functions following the given order', (context) => { 1914 context.mock.timers.enable(['setTimeout']); 1915 const results = []; 1916 setTimeout(() => results.push(1), 9999); 1917 1918 // Notice that if both timers have the same timeout, 1919 // the order of execution is guaranteed 1920 setTimeout(() => results.push(3), 8888); 1921 setTimeout(() => results.push(2), 8888); 1922 1923 assert.deepStrictEqual(results, []); 1924 1925 context.mock.timers.runAll(); 1926 1927 assert.deepStrictEqual(results, [3, 2, 1]); 1928}); 1929``` 1930 1931**Note:** The `runAll()` function is specifically designed for 1932triggering timers in the context of timer mocking. 1933It does not have any effect on real-time system 1934clocks or actual timers outside of the mocking environment. 1935 1936## Class: `TestsStream` 1937 1938<!-- YAML 1939added: 1940 - v18.9.0 1941 - v16.19.0 1942changes: 1943 - version: v18.17.0 1944 pr-url: https://github.com/nodejs/node/pull/47094 1945 description: added type to test:pass and test:fail events for when the test is a suite. 1946--> 1947 1948* Extends {ReadableStream} 1949 1950A successful call to [`run()`][] method will return a new {TestsStream} 1951object, streaming a series of events representing the execution of the tests. 1952`TestsStream` will emit events, in the order of the tests definition 1953 1954### Event: `'test:coverage'` 1955 1956* `data` {Object} 1957 * `summary` {Object} An object containing the coverage report. 1958 * `files` {Array} An array of coverage reports for individual files. Each 1959 report is an object with the following schema: 1960 * `path` {string} The absolute path of the file. 1961 * `totalLineCount` {number} The total number of lines. 1962 * `totalBranchCount` {number} The total number of branches. 1963 * `totalFunctionCount` {number} The total number of functions. 1964 * `coveredLineCount` {number} The number of covered lines. 1965 * `coveredBranchCount` {number} The number of covered branches. 1966 * `coveredFunctionCount` {number} The number of covered functions. 1967 * `coveredLinePercent` {number} The percentage of lines covered. 1968 * `coveredBranchPercent` {number} The percentage of branches covered. 1969 * `coveredFunctionPercent` {number} The percentage of functions covered. 1970 * `uncoveredLineNumbers` {Array} An array of integers representing line 1971 numbers that are uncovered. 1972 * `totals` {Object} An object containing a summary of coverage for all 1973 files. 1974 * `totalLineCount` {number} The total number of lines. 1975 * `totalBranchCount` {number} The total number of branches. 1976 * `totalFunctionCount` {number} The total number of functions. 1977 * `coveredLineCount` {number} The number of covered lines. 1978 * `coveredBranchCount` {number} The number of covered branches. 1979 * `coveredFunctionCount` {number} The number of covered functions. 1980 * `coveredLinePercent` {number} The percentage of lines covered. 1981 * `coveredBranchPercent` {number} The percentage of branches covered. 1982 * `coveredFunctionPercent` {number} The percentage of functions covered. 1983 * `workingDirectory` {string} The working directory when code coverage 1984 began. This is useful for displaying relative path names in case the tests 1985 changed the working directory of the Node.js process. 1986 * `nesting` {number} The nesting level of the test. 1987 1988Emitted when code coverage is enabled and all tests have completed. 1989 1990### Event: `'test:dequeue'` 1991 1992* `data` {Object} 1993 * `column` {number|undefined} The column number where the test is defined, or 1994 `undefined` if the test was run through the REPL. 1995 * `file` {string|undefined} The path of the test file, 1996 `undefined` if test was run through the REPL. 1997 * `line` {number|undefined} The line number where the test is defined, or 1998 `undefined` if the test was run through the REPL. 1999 * `name` {string} The test name. 2000 * `nesting` {number} The nesting level of the test. 2001 2002Emitted when a test is dequeued, right before it is executed. 2003 2004### Event: `'test:diagnostic'` 2005 2006* `data` {Object} 2007 * `column` {number|undefined} The column number where the test is defined, or 2008 `undefined` if the test was run through the REPL. 2009 * `file` {string|undefined} The path of the test file, 2010 `undefined` if test was run through the REPL. 2011 * `line` {number|undefined} The line number where the test is defined, or 2012 `undefined` if the test was run through the REPL. 2013 * `message` {string} The diagnostic message. 2014 * `nesting` {number} The nesting level of the test. 2015 2016Emitted when [`context.diagnostic`][] is called. 2017 2018### Event: `'test:enqueue'` 2019 2020* `data` {Object} 2021 * `column` {number|undefined} The column number where the test is defined, or 2022 `undefined` if the test was run through the REPL. 2023 * `file` {string|undefined} The path of the test file, 2024 `undefined` if test was run through the REPL. 2025 * `line` {number|undefined} The line number where the test is defined, or 2026 `undefined` if the test was run through the REPL. 2027 * `name` {string} The test name. 2028 * `nesting` {number} The nesting level of the test. 2029 2030Emitted when a test is enqueued for execution. 2031 2032### Event: `'test:fail'` 2033 2034* `data` {Object} 2035 * `column` {number|undefined} The column number where the test is defined, or 2036 `undefined` if the test was run through the REPL. 2037 * `details` {Object} Additional execution metadata. 2038 * `duration_ms` {number} The duration of the test in milliseconds. 2039 * `error` {Error} An error wrapping the error thrown by the test. 2040 * `cause` {Error} The actual error thrown by the test. 2041 * `type` {string|undefined} The type of the test, used to denote whether 2042 this is a suite. 2043 * `file` {string|undefined} The path of the test file, 2044 `undefined` if test was run through the REPL. 2045 * `line` {number|undefined} The line number where the test is defined, or 2046 `undefined` if the test was run through the REPL. 2047 * `name` {string} The test name. 2048 * `nesting` {number} The nesting level of the test. 2049 * `testNumber` {number} The ordinal number of the test. 2050 * `todo` {string|boolean|undefined} Present if [`context.todo`][] is called 2051 * `skip` {string|boolean|undefined} Present if [`context.skip`][] is called 2052 2053Emitted when a test fails. 2054 2055### Event: `'test:pass'` 2056 2057* `data` {Object} 2058 * `column` {number|undefined} The column number where the test is defined, or 2059 `undefined` if the test was run through the REPL. 2060 * `details` {Object} Additional execution metadata. 2061 * `duration_ms` {number} The duration of the test in milliseconds. 2062 * `type` {string|undefined} The type of the test, used to denote whether 2063 this is a suite. 2064 * `file` {string|undefined} The path of the test file, 2065 `undefined` if test was run through the REPL. 2066 * `line` {number|undefined} The line number where the test is defined, or 2067 `undefined` if the test was run through the REPL. 2068 * `name` {string} The test name. 2069 * `nesting` {number} The nesting level of the test. 2070 * `testNumber` {number} The ordinal number of the test. 2071 * `todo` {string|boolean|undefined} Present if [`context.todo`][] is called 2072 * `skip` {string|boolean|undefined} Present if [`context.skip`][] is called 2073 2074Emitted when a test passes. 2075 2076### Event: `'test:plan'` 2077 2078* `data` {Object} 2079 * `column` {number|undefined} The column number where the test is defined, or 2080 `undefined` if the test was run through the REPL. 2081 * `file` {string|undefined} The path of the test file, 2082 `undefined` if test was run through the REPL. 2083 * `line` {number|undefined} The line number where the test is defined, or 2084 `undefined` if the test was run through the REPL. 2085 * `nesting` {number} The nesting level of the test. 2086 * `count` {number} The number of subtests that have ran. 2087 2088Emitted when all subtests have completed for a given test. 2089 2090### Event: `'test:start'` 2091 2092* `data` {Object} 2093 * `column` {number|undefined} The column number where the test is defined, or 2094 `undefined` if the test was run through the REPL. 2095 * `file` {string|undefined} The path of the test file, 2096 `undefined` if test was run through the REPL. 2097 * `line` {number|undefined} The line number where the test is defined, or 2098 `undefined` if the test was run through the REPL. 2099 * `name` {string} The test name. 2100 * `nesting` {number} The nesting level of the test. 2101 2102Emitted when a test starts reporting its own and its subtests status. 2103This event is guaranteed to be emitted in the same order as the tests are 2104defined. 2105 2106### Event: `'test:stderr'` 2107 2108* `data` {Object} 2109 * `column` {number|undefined} The column number where the test is defined, or 2110 `undefined` if the test was run through the REPL. 2111 * `file` {string} The path of the test file. 2112 * `line` {number|undefined} The line number where the test is defined, or 2113 `undefined` if the test was run through the REPL. 2114 * `message` {string} The message written to `stderr`. 2115 2116Emitted when a running test writes to `stderr`. 2117This event is only emitted if `--test` flag is passed. 2118 2119### Event: `'test:stdout'` 2120 2121* `data` {Object} 2122 * `column` {number|undefined} The column number where the test is defined, or 2123 `undefined` if the test was run through the REPL. 2124 * `file` {string} The path of the test file. 2125 * `line` {number|undefined} The line number where the test is defined, or 2126 `undefined` if the test was run through the REPL. 2127 * `message` {string} The message written to `stdout`. 2128 2129Emitted when a running test writes to `stdout`. 2130This event is only emitted if `--test` flag is passed. 2131 2132### Event: `'test:watch:drained'` 2133 2134Emitted when no more tests are queued for execution in watch mode. 2135 2136## Class: `TestContext` 2137 2138<!-- YAML 2139added: v18.0.0 2140changes: 2141 - version: v18.17.0 2142 pr-url: https://github.com/nodejs/node/pull/47586 2143 description: The `before` function was added to TestContext. 2144--> 2145 2146An instance of `TestContext` is passed to each test function in order to 2147interact with the test runner. However, the `TestContext` constructor is not 2148exposed as part of the API. 2149 2150### `context.before([fn][, options])` 2151 2152<!-- YAML 2153added: v18.17.0 2154--> 2155 2156* `fn` {Function|AsyncFunction} The hook function. The first argument 2157 to this function is a [`TestContext`][] object. If the hook uses callbacks, 2158 the callback function is passed as the second argument. **Default:** A no-op 2159 function. 2160* `options` {Object} Configuration options for the hook. The following 2161 properties are supported: 2162 * `signal` {AbortSignal} Allows aborting an in-progress hook. 2163 * `timeout` {number} A number of milliseconds the hook will fail after. 2164 If unspecified, subtests inherit this value from their parent. 2165 **Default:** `Infinity`. 2166 2167This function is used to create a hook running before 2168subtest of the current test. 2169 2170### `context.beforeEach([fn][, options])` 2171 2172<!-- YAML 2173added: v18.8.0 2174--> 2175 2176* `fn` {Function|AsyncFunction} The hook function. The first argument 2177 to this function is a [`TestContext`][] object. If the hook uses callbacks, 2178 the callback function is passed as the second argument. **Default:** A no-op 2179 function. 2180* `options` {Object} Configuration options for the hook. The following 2181 properties are supported: 2182 * `signal` {AbortSignal} Allows aborting an in-progress hook. 2183 * `timeout` {number} A number of milliseconds the hook will fail after. 2184 If unspecified, subtests inherit this value from their parent. 2185 **Default:** `Infinity`. 2186 2187This function is used to create a hook running 2188before each subtest of the current test. 2189 2190```js 2191test('top level test', async (t) => { 2192 t.beforeEach((t) => t.diagnostic(`about to run ${t.name}`)); 2193 await t.test( 2194 'This is a subtest', 2195 (t) => { 2196 assert.ok('some relevant assertion here'); 2197 }, 2198 ); 2199}); 2200``` 2201 2202### `context.after([fn][, options])` 2203 2204<!-- YAML 2205added: v18.13.0 2206--> 2207 2208* `fn` {Function|AsyncFunction} The hook function. The first argument 2209 to this function is a [`TestContext`][] object. If the hook uses callbacks, 2210 the callback function is passed as the second argument. **Default:** A no-op 2211 function. 2212* `options` {Object} Configuration options for the hook. The following 2213 properties are supported: 2214 * `signal` {AbortSignal} Allows aborting an in-progress hook. 2215 * `timeout` {number} A number of milliseconds the hook will fail after. 2216 If unspecified, subtests inherit this value from their parent. 2217 **Default:** `Infinity`. 2218 2219This function is used to create a hook that runs after the current test 2220finishes. 2221 2222```js 2223test('top level test', async (t) => { 2224 t.after((t) => t.diagnostic(`finished running ${t.name}`)); 2225 assert.ok('some relevant assertion here'); 2226}); 2227``` 2228 2229### `context.afterEach([fn][, options])` 2230 2231<!-- YAML 2232added: v18.8.0 2233--> 2234 2235* `fn` {Function|AsyncFunction} The hook function. The first argument 2236 to this function is a [`TestContext`][] object. If the hook uses callbacks, 2237 the callback function is passed as the second argument. **Default:** A no-op 2238 function. 2239* `options` {Object} Configuration options for the hook. The following 2240 properties are supported: 2241 * `signal` {AbortSignal} Allows aborting an in-progress hook. 2242 * `timeout` {number} A number of milliseconds the hook will fail after. 2243 If unspecified, subtests inherit this value from their parent. 2244 **Default:** `Infinity`. 2245 2246This function is used to create a hook running 2247after each subtest of the current test. 2248 2249```js 2250test('top level test', async (t) => { 2251 t.afterEach((t) => t.diagnostic(`finished running ${t.name}`)); 2252 await t.test( 2253 'This is a subtest', 2254 (t) => { 2255 assert.ok('some relevant assertion here'); 2256 }, 2257 ); 2258}); 2259``` 2260 2261### `context.diagnostic(message)` 2262 2263<!-- YAML 2264added: v18.0.0 2265--> 2266 2267* `message` {string} Message to be reported. 2268 2269This function is used to write diagnostics to the output. Any diagnostic 2270information is included at the end of the test's results. This function does 2271not return a value. 2272 2273```js 2274test('top level test', (t) => { 2275 t.diagnostic('A diagnostic message'); 2276}); 2277``` 2278 2279### `context.name` 2280 2281<!-- YAML 2282added: v18.8.0 2283--> 2284 2285The name of the test. 2286 2287### `context.runOnly(shouldRunOnlyTests)` 2288 2289<!-- YAML 2290added: v18.0.0 2291--> 2292 2293* `shouldRunOnlyTests` {boolean} Whether or not to run `only` tests. 2294 2295If `shouldRunOnlyTests` is truthy, the test context will only run tests that 2296have the `only` option set. Otherwise, all tests are run. If Node.js was not 2297started with the [`--test-only`][] command-line option, this function is a 2298no-op. 2299 2300```js 2301test('top level test', (t) => { 2302 // The test context can be set to run subtests with the 'only' option. 2303 t.runOnly(true); 2304 return Promise.all([ 2305 t.test('this subtest is now skipped'), 2306 t.test('this subtest is run', { only: true }), 2307 ]); 2308}); 2309``` 2310 2311### `context.signal` 2312 2313<!-- YAML 2314added: v18.7.0 2315--> 2316 2317* {AbortSignal} Can be used to abort test subtasks when the test has been 2318 aborted. 2319 2320```js 2321test('top level test', async (t) => { 2322 await fetch('some/uri', { signal: t.signal }); 2323}); 2324``` 2325 2326### `context.skip([message])` 2327 2328<!-- YAML 2329added: v18.0.0 2330--> 2331 2332* `message` {string} Optional skip message. 2333 2334This function causes the test's output to indicate the test as skipped. If 2335`message` is provided, it is included in the output. Calling `skip()` does 2336not terminate execution of the test function. This function does not return a 2337value. 2338 2339```js 2340test('top level test', (t) => { 2341 // Make sure to return here as well if the test contains additional logic. 2342 t.skip('this is skipped'); 2343}); 2344``` 2345 2346### `context.todo([message])` 2347 2348<!-- YAML 2349added: v18.0.0 2350--> 2351 2352* `message` {string} Optional `TODO` message. 2353 2354This function adds a `TODO` directive to the test's output. If `message` is 2355provided, it is included in the output. Calling `todo()` does not terminate 2356execution of the test function. This function does not return a value. 2357 2358```js 2359test('top level test', (t) => { 2360 // This test is marked as `TODO` 2361 t.todo('this is a todo'); 2362}); 2363``` 2364 2365### `context.test([name][, options][, fn])` 2366 2367<!-- YAML 2368added: v18.0.0 2369changes: 2370 - version: v18.8.0 2371 pr-url: https://github.com/nodejs/node/pull/43554 2372 description: Add a `signal` option. 2373 - version: v18.7.0 2374 pr-url: https://github.com/nodejs/node/pull/43505 2375 description: Add a `timeout` option. 2376--> 2377 2378* `name` {string} The name of the subtest, which is displayed when reporting 2379 test results. **Default:** The `name` property of `fn`, or `'<anonymous>'` if 2380 `fn` does not have a name. 2381* `options` {Object} Configuration options for the subtest. The following 2382 properties are supported: 2383 * `concurrency` {number|boolean|null} If a number is provided, 2384 then that many tests would run in parallel within the application thread. 2385 If `true`, it would run all subtests in parallel. 2386 If `false`, it would only run one test at a time. 2387 If unspecified, subtests inherit this value from their parent. 2388 **Default:** `null`. 2389 * `only` {boolean} If truthy, and the test context is configured to run 2390 `only` tests, then this test will be run. Otherwise, the test is skipped. 2391 **Default:** `false`. 2392 * `signal` {AbortSignal} Allows aborting an in-progress test. 2393 * `skip` {boolean|string} If truthy, the test is skipped. If a string is 2394 provided, that string is displayed in the test results as the reason for 2395 skipping the test. **Default:** `false`. 2396 * `todo` {boolean|string} If truthy, the test marked as `TODO`. If a string 2397 is provided, that string is displayed in the test results as the reason why 2398 the test is `TODO`. **Default:** `false`. 2399 * `timeout` {number} A number of milliseconds the test will fail after. 2400 If unspecified, subtests inherit this value from their parent. 2401 **Default:** `Infinity`. 2402* `fn` {Function|AsyncFunction} The function under test. The first argument 2403 to this function is a [`TestContext`][] object. If the test uses callbacks, 2404 the callback function is passed as the second argument. **Default:** A no-op 2405 function. 2406* Returns: {Promise} Resolved with `undefined` once the test completes. 2407 2408This function is used to create subtests under the current test. This function 2409behaves in the same fashion as the top level [`test()`][] function. 2410 2411```js 2412test('top level test', async (t) => { 2413 await t.test( 2414 'This is a subtest', 2415 { only: false, skip: false, concurrency: 1, todo: false }, 2416 (t) => { 2417 assert.ok('some relevant assertion here'); 2418 }, 2419 ); 2420}); 2421``` 2422 2423## Class: `SuiteContext` 2424 2425<!-- YAML 2426added: v18.7.0 2427--> 2428 2429An instance of `SuiteContext` is passed to each suite function in order to 2430interact with the test runner. However, the `SuiteContext` constructor is not 2431exposed as part of the API. 2432 2433### `context.name` 2434 2435<!-- YAML 2436added: v18.8.0 2437--> 2438 2439The name of the suite. 2440 2441### `context.signal` 2442 2443<!-- YAML 2444added: v18.7.0 2445--> 2446 2447* {AbortSignal} Can be used to abort test subtasks when the test has been 2448 aborted. 2449 2450[TAP]: https://testanything.org/ 2451[TTY]: tty.md 2452[`--experimental-test-coverage`]: cli.md#--experimental-test-coverage 2453[`--test-concurrency`]: cli.md#--test-concurrency 2454[`--test-name-pattern`]: cli.md#--test-name-pattern 2455[`--test-only`]: cli.md#--test-only 2456[`--test-reporter-destination`]: cli.md#--test-reporter-destination 2457[`--test-reporter`]: cli.md#--test-reporter 2458[`--test`]: cli.md#--test 2459[`MockFunctionContext`]: #class-mockfunctioncontext 2460[`MockTimers`]: #class-mocktimers 2461[`MockTracker.method`]: #mockmethodobject-methodname-implementation-options 2462[`MockTracker`]: #class-mocktracker 2463[`NODE_V8_COVERAGE`]: cli.md#node_v8_coveragedir 2464[`SuiteContext`]: #class-suitecontext 2465[`TestContext`]: #class-testcontext 2466[`context.diagnostic`]: #contextdiagnosticmessage 2467[`context.skip`]: #contextskipmessage 2468[`context.todo`]: #contexttodomessage 2469[`describe()`]: #describename-options-fn 2470[`run()`]: #runoptions 2471[`test()`]: #testname-options-fn 2472[describe options]: #describename-options-fn 2473[it options]: #testname-options-fn 2474[stream.compose]: stream.md#streamcomposestreams 2475[test reporters]: #test-reporters 2476[test runner execution model]: #test-runner-execution-model 2477