vitest 0.16.0 → 0.17.0

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.
@@ -1,5 +1,5 @@
1
1
  import { promises } from 'fs';
2
- import { c as createBirpc } from './chunk-vite-node-utils.7450fc0c.mjs';
2
+ import { c as createBirpc } from './chunk-vite-node-utils.4b58ae05.mjs';
3
3
  import require$$0$1 from 'stream';
4
4
  import require$$0 from 'zlib';
5
5
  import require$$3 from 'net';
@@ -9,8 +9,8 @@ import require$$2 from 'events';
9
9
  import require$$1 from 'https';
10
10
  import require$$2$1 from 'http';
11
11
  import url from 'url';
12
- import { A as API_PATH } from './chunk-constants.7b9cfc82.mjs';
13
- import { j as interpretSourcePos, b as parseStacktrace } from './chunk-utils-source-map.2556cba8.mjs';
12
+ import { A as API_PATH } from './chunk-constants.511c6e9b.mjs';
13
+ import { j as interpretSourcePos, b as parseStacktrace } from './chunk-utils-source-map.f52527bc.mjs';
14
14
  import 'module';
15
15
  import 'vm';
16
16
  import './chunk-utils-global.79a8b1cc.mjs';
@@ -6,11 +6,17 @@ const defaultPort = 51204;
6
6
  const API_PATH = "/__vitest_api__";
7
7
  const configFiles = [
8
8
  "vitest.config.ts",
9
+ "vitest.config.mts",
10
+ "vitest.config.cts",
9
11
  "vitest.config.js",
10
12
  "vitest.config.mjs",
13
+ "vitest.config.cjs",
11
14
  "vite.config.ts",
15
+ "vite.config.mts",
16
+ "vite.config.cts",
12
17
  "vite.config.js",
13
- "vite.config.mjs"
18
+ "vite.config.mjs",
19
+ "vite.config.cjs"
14
20
  ];
15
21
  const globalApis = [
16
22
  "suite",
@@ -0,0 +1,670 @@
1
+ import { importModule } from 'local-pkg';
2
+ import { existsSync, promises } from 'fs';
3
+ import { createRequire } from 'module';
4
+ import { pathToFileURL } from 'url';
5
+ import { C as toArray, m as resolve } from './chunk-utils-global.79a8b1cc.mjs';
6
+
7
+ var node = {
8
+ name: "node",
9
+ async setup() {
10
+ return {
11
+ teardown() {
12
+ }
13
+ };
14
+ }
15
+ };
16
+
17
+ const LIVING_KEYS = [
18
+ "DOMException",
19
+ "URL",
20
+ "URLSearchParams",
21
+ "EventTarget",
22
+ "NamedNodeMap",
23
+ "Node",
24
+ "Attr",
25
+ "Element",
26
+ "DocumentFragment",
27
+ "DOMImplementation",
28
+ "Document",
29
+ "XMLDocument",
30
+ "CharacterData",
31
+ "Text",
32
+ "CDATASection",
33
+ "ProcessingInstruction",
34
+ "Comment",
35
+ "DocumentType",
36
+ "NodeList",
37
+ "HTMLCollection",
38
+ "HTMLOptionsCollection",
39
+ "DOMStringMap",
40
+ "DOMTokenList",
41
+ "StyleSheetList",
42
+ "HTMLElement",
43
+ "HTMLHeadElement",
44
+ "HTMLTitleElement",
45
+ "HTMLBaseElement",
46
+ "HTMLLinkElement",
47
+ "HTMLMetaElement",
48
+ "HTMLStyleElement",
49
+ "HTMLBodyElement",
50
+ "HTMLHeadingElement",
51
+ "HTMLParagraphElement",
52
+ "HTMLHRElement",
53
+ "HTMLPreElement",
54
+ "HTMLUListElement",
55
+ "HTMLOListElement",
56
+ "HTMLLIElement",
57
+ "HTMLMenuElement",
58
+ "HTMLDListElement",
59
+ "HTMLDivElement",
60
+ "HTMLAnchorElement",
61
+ "HTMLAreaElement",
62
+ "HTMLBRElement",
63
+ "HTMLButtonElement",
64
+ "HTMLCanvasElement",
65
+ "HTMLDataElement",
66
+ "HTMLDataListElement",
67
+ "HTMLDetailsElement",
68
+ "HTMLDialogElement",
69
+ "HTMLDirectoryElement",
70
+ "HTMLFieldSetElement",
71
+ "HTMLFontElement",
72
+ "HTMLFormElement",
73
+ "HTMLHtmlElement",
74
+ "HTMLImageElement",
75
+ "HTMLInputElement",
76
+ "HTMLLabelElement",
77
+ "HTMLLegendElement",
78
+ "HTMLMapElement",
79
+ "HTMLMarqueeElement",
80
+ "HTMLMediaElement",
81
+ "HTMLMeterElement",
82
+ "HTMLModElement",
83
+ "HTMLOptGroupElement",
84
+ "HTMLOptionElement",
85
+ "HTMLOutputElement",
86
+ "HTMLPictureElement",
87
+ "HTMLProgressElement",
88
+ "HTMLQuoteElement",
89
+ "HTMLScriptElement",
90
+ "HTMLSelectElement",
91
+ "HTMLSlotElement",
92
+ "HTMLSourceElement",
93
+ "HTMLSpanElement",
94
+ "HTMLTableCaptionElement",
95
+ "HTMLTableCellElement",
96
+ "HTMLTableColElement",
97
+ "HTMLTableElement",
98
+ "HTMLTimeElement",
99
+ "HTMLTableRowElement",
100
+ "HTMLTableSectionElement",
101
+ "HTMLTemplateElement",
102
+ "HTMLTextAreaElement",
103
+ "HTMLUnknownElement",
104
+ "HTMLFrameElement",
105
+ "HTMLFrameSetElement",
106
+ "HTMLIFrameElement",
107
+ "HTMLEmbedElement",
108
+ "HTMLObjectElement",
109
+ "HTMLParamElement",
110
+ "HTMLVideoElement",
111
+ "HTMLAudioElement",
112
+ "HTMLTrackElement",
113
+ "SVGElement",
114
+ "SVGGraphicsElement",
115
+ "SVGSVGElement",
116
+ "SVGTitleElement",
117
+ "SVGAnimatedString",
118
+ "SVGNumber",
119
+ "SVGStringList",
120
+ "Event",
121
+ "CloseEvent",
122
+ "CustomEvent",
123
+ "MessageEvent",
124
+ "ErrorEvent",
125
+ "HashChangeEvent",
126
+ "PopStateEvent",
127
+ "StorageEvent",
128
+ "ProgressEvent",
129
+ "PageTransitionEvent",
130
+ "UIEvent",
131
+ "FocusEvent",
132
+ "InputEvent",
133
+ "MouseEvent",
134
+ "KeyboardEvent",
135
+ "TouchEvent",
136
+ "CompositionEvent",
137
+ "WheelEvent",
138
+ "BarProp",
139
+ "External",
140
+ "Location",
141
+ "History",
142
+ "Screen",
143
+ "Performance",
144
+ "Navigator",
145
+ "PluginArray",
146
+ "MimeTypeArray",
147
+ "Plugin",
148
+ "MimeType",
149
+ "FileReader",
150
+ "Blob",
151
+ "File",
152
+ "FileList",
153
+ "ValidityState",
154
+ "DOMParser",
155
+ "XMLSerializer",
156
+ "FormData",
157
+ "XMLHttpRequestEventTarget",
158
+ "XMLHttpRequestUpload",
159
+ "XMLHttpRequest",
160
+ "WebSocket",
161
+ "NodeFilter",
162
+ "NodeIterator",
163
+ "TreeWalker",
164
+ "AbstractRange",
165
+ "Range",
166
+ "StaticRange",
167
+ "Selection",
168
+ "Storage",
169
+ "CustomElementRegistry",
170
+ "ShadowRoot",
171
+ "MutationObserver",
172
+ "MutationRecord",
173
+ "Headers",
174
+ "AbortController",
175
+ "AbortSignal",
176
+ "Image",
177
+ "Audio",
178
+ "Option"
179
+ ];
180
+ const OTHER_KEYS = [
181
+ "addEventListener",
182
+ "alert",
183
+ "atob",
184
+ "blur",
185
+ "btoa",
186
+ "cancelAnimationFrame",
187
+ "close",
188
+ "confirm",
189
+ "createPopup",
190
+ "dispatchEvent",
191
+ "document",
192
+ "focus",
193
+ "frames",
194
+ "getComputedStyle",
195
+ "history",
196
+ "innerHeight",
197
+ "innerWidth",
198
+ "length",
199
+ "location",
200
+ "matchMedia",
201
+ "moveBy",
202
+ "moveTo",
203
+ "name",
204
+ "navigator",
205
+ "open",
206
+ "outerHeight",
207
+ "outerWidth",
208
+ "pageXOffset",
209
+ "pageYOffset",
210
+ "parent",
211
+ "postMessage",
212
+ "print",
213
+ "prompt",
214
+ "removeEventListener",
215
+ "requestAnimationFrame",
216
+ "resizeBy",
217
+ "resizeTo",
218
+ "screen",
219
+ "screenLeft",
220
+ "screenTop",
221
+ "screenX",
222
+ "screenY",
223
+ "scroll",
224
+ "scrollBy",
225
+ "scrollLeft",
226
+ "scrollTo",
227
+ "scrollTop",
228
+ "scrollX",
229
+ "scrollY",
230
+ "self",
231
+ "stop",
232
+ "top",
233
+ "Window",
234
+ "window"
235
+ ];
236
+ const KEYS = LIVING_KEYS.concat(OTHER_KEYS);
237
+
238
+ const allowRewrite = [
239
+ "Event",
240
+ "EventTarget"
241
+ ];
242
+ const skipKeys = [
243
+ "window",
244
+ "self",
245
+ "top",
246
+ "parent"
247
+ ];
248
+ function getWindowKeys(global, win) {
249
+ const keys = new Set(KEYS.concat(Object.getOwnPropertyNames(win)).filter((k) => {
250
+ if (skipKeys.includes(k))
251
+ return false;
252
+ if (k in global)
253
+ return allowRewrite.includes(k);
254
+ return true;
255
+ }));
256
+ return keys;
257
+ }
258
+ function isClassLikeName(name) {
259
+ return name[0] === name[0].toUpperCase();
260
+ }
261
+ function populateGlobal(global, win, options = {}) {
262
+ const { bindFunctions = false } = options;
263
+ const keys = getWindowKeys(global, win);
264
+ const originals = new Map(allowRewrite.map(([key]) => [key, global[key]]));
265
+ const overrideObject = /* @__PURE__ */ new Map();
266
+ for (const key of keys) {
267
+ const boundFunction = bindFunctions && typeof win[key] === "function" && !isClassLikeName(key) && win[key].bind(win);
268
+ Object.defineProperty(global, key, {
269
+ get() {
270
+ if (overrideObject.has(key))
271
+ return overrideObject.get(key);
272
+ if (boundFunction)
273
+ return boundFunction;
274
+ return win[key];
275
+ },
276
+ set(v) {
277
+ overrideObject.set(key, v);
278
+ },
279
+ configurable: true
280
+ });
281
+ }
282
+ global.window = global;
283
+ global.self = global;
284
+ global.top = global;
285
+ global.parent = global;
286
+ if (global.global)
287
+ global.global = global;
288
+ skipKeys.forEach((k) => keys.add(k));
289
+ return {
290
+ keys,
291
+ skipKeys,
292
+ originals
293
+ };
294
+ }
295
+
296
+ var jsdom = {
297
+ name: "jsdom",
298
+ async setup(global, { jsdom = {} }) {
299
+ const {
300
+ CookieJar,
301
+ JSDOM,
302
+ ResourceLoader,
303
+ VirtualConsole
304
+ } = await importModule("jsdom");
305
+ const {
306
+ html = "<!DOCTYPE html>",
307
+ userAgent,
308
+ url = "http://localhost:3000",
309
+ contentType = "text/html",
310
+ pretendToBeVisual = true,
311
+ includeNodeLocations = false,
312
+ runScripts = "dangerously",
313
+ resources,
314
+ console = false,
315
+ cookieJar = false,
316
+ ...restOptions
317
+ } = jsdom;
318
+ const dom = new JSDOM(html, {
319
+ pretendToBeVisual,
320
+ resources: resources ?? (userAgent ? new ResourceLoader({ userAgent }) : void 0),
321
+ runScripts,
322
+ url,
323
+ virtualConsole: console && global.console ? new VirtualConsole().sendTo(global.console) : void 0,
324
+ cookieJar: cookieJar ? new CookieJar() : void 0,
325
+ includeNodeLocations,
326
+ contentType,
327
+ userAgent,
328
+ ...restOptions
329
+ });
330
+ const { keys, originals } = populateGlobal(global, dom.window, { bindFunctions: true });
331
+ return {
332
+ teardown(global2) {
333
+ keys.forEach((key) => delete global2[key]);
334
+ originals.forEach((v, k) => global2[k] = v);
335
+ }
336
+ };
337
+ }
338
+ };
339
+
340
+ var happy = {
341
+ name: "happy-dom",
342
+ async setup(global) {
343
+ const { Window, GlobalWindow } = await importModule("happy-dom");
344
+ const win = new (GlobalWindow || Window)();
345
+ const { keys, originals } = populateGlobal(global, win, { bindFunctions: true });
346
+ return {
347
+ teardown(global2) {
348
+ win.happyDOM.cancelAsync();
349
+ keys.forEach((key) => delete global2[key]);
350
+ originals.forEach((v, k) => global2[k] = v);
351
+ }
352
+ };
353
+ }
354
+ };
355
+
356
+ var edge = {
357
+ name: "edge-runtime",
358
+ async setup(global) {
359
+ const { EdgeVM } = await importModule("@edge-runtime/vm");
360
+ const vm = new EdgeVM({
361
+ extend: (context) => {
362
+ context.global = context;
363
+ context.Buffer = Buffer;
364
+ return context;
365
+ }
366
+ });
367
+ const { keys, originals } = populateGlobal(global, vm.context, { bindFunctions: true });
368
+ return {
369
+ teardown(global2) {
370
+ keys.forEach((key) => delete global2[key]);
371
+ originals.forEach((v, k) => global2[k] = v);
372
+ }
373
+ };
374
+ }
375
+ };
376
+
377
+ const environments = {
378
+ node,
379
+ jsdom,
380
+ "happy-dom": happy,
381
+ "edge-runtime": edge
382
+ };
383
+ const envs = Object.keys(environments);
384
+ const envPackageNames = {
385
+ "jsdom": "jsdom",
386
+ "happy-dom": "happy-dom",
387
+ "edge-runtime": "@edge-runtime/vm"
388
+ };
389
+
390
+ /*
391
+ How it works:
392
+ `this.#head` is an instance of `Node` which keeps track of its current value and nests another instance of `Node` that keeps the value that comes after it. When a value is provided to `.enqueue()`, the code needs to iterate through `this.#head`, going deeper and deeper to find the last value. However, iterating through every single item is slow. This problem is solved by saving a reference to the last value as `this.#tail` so that it can reference it to add a new value.
393
+ */
394
+
395
+ class Node {
396
+ value;
397
+ next;
398
+
399
+ constructor(value) {
400
+ this.value = value;
401
+ }
402
+ }
403
+
404
+ class Queue {
405
+ #head;
406
+ #tail;
407
+ #size;
408
+
409
+ constructor() {
410
+ this.clear();
411
+ }
412
+
413
+ enqueue(value) {
414
+ const node = new Node(value);
415
+
416
+ if (this.#head) {
417
+ this.#tail.next = node;
418
+ this.#tail = node;
419
+ } else {
420
+ this.#head = node;
421
+ this.#tail = node;
422
+ }
423
+
424
+ this.#size++;
425
+ }
426
+
427
+ dequeue() {
428
+ const current = this.#head;
429
+ if (!current) {
430
+ return;
431
+ }
432
+
433
+ this.#head = this.#head.next;
434
+ this.#size--;
435
+ return current.value;
436
+ }
437
+
438
+ clear() {
439
+ this.#head = undefined;
440
+ this.#tail = undefined;
441
+ this.#size = 0;
442
+ }
443
+
444
+ get size() {
445
+ return this.#size;
446
+ }
447
+
448
+ * [Symbol.iterator]() {
449
+ let current = this.#head;
450
+
451
+ while (current) {
452
+ yield current.value;
453
+ current = current.next;
454
+ }
455
+ }
456
+ }
457
+
458
+ function pLimit(concurrency) {
459
+ if (!((Number.isInteger(concurrency) || concurrency === Number.POSITIVE_INFINITY) && concurrency > 0)) {
460
+ throw new TypeError('Expected `concurrency` to be a number from 1 and up');
461
+ }
462
+
463
+ const queue = new Queue();
464
+ let activeCount = 0;
465
+
466
+ const next = () => {
467
+ activeCount--;
468
+
469
+ if (queue.size > 0) {
470
+ queue.dequeue()();
471
+ }
472
+ };
473
+
474
+ const run = async (fn, resolve, args) => {
475
+ activeCount++;
476
+
477
+ const result = (async () => fn(...args))();
478
+
479
+ resolve(result);
480
+
481
+ try {
482
+ await result;
483
+ } catch {}
484
+
485
+ next();
486
+ };
487
+
488
+ const enqueue = (fn, resolve, args) => {
489
+ queue.enqueue(run.bind(undefined, fn, resolve, args));
490
+
491
+ (async () => {
492
+ // This function needs to wait until the next microtask before comparing
493
+ // `activeCount` to `concurrency`, because `activeCount` is updated asynchronously
494
+ // when the run function is dequeued and called. The comparison in the if-statement
495
+ // needs to happen asynchronously as well to get an up-to-date value for `activeCount`.
496
+ await Promise.resolve();
497
+
498
+ if (activeCount < concurrency && queue.size > 0) {
499
+ queue.dequeue()();
500
+ }
501
+ })();
502
+ };
503
+
504
+ const generator = (fn, ...args) => new Promise(resolve => {
505
+ enqueue(fn, resolve, args);
506
+ });
507
+
508
+ Object.defineProperties(generator, {
509
+ activeCount: {
510
+ get: () => activeCount,
511
+ },
512
+ pendingCount: {
513
+ get: () => queue.size,
514
+ },
515
+ clearQueue: {
516
+ value: () => {
517
+ queue.clear();
518
+ },
519
+ },
520
+ });
521
+
522
+ return generator;
523
+ }
524
+
525
+ const defaultInclude = ["**/*.{test,spec}.{js,mjs,cjs,ts,mts,cts,jsx,tsx}"];
526
+ const defaultExclude = ["**/node_modules/**", "**/dist/**", "**/cypress/**", "**/.{idea,git,cache,output,temp}/**"];
527
+ const defaultCoverageExcludes = [
528
+ "coverage/**",
529
+ "packages/*/test{,s}/**",
530
+ "**/*.d.ts",
531
+ "cypress/**",
532
+ "test{,s}/**",
533
+ "test{,-*}.{js,cjs,mjs,ts,tsx,jsx}",
534
+ "**/*{.,-}test.{js,cjs,mjs,ts,tsx,jsx}",
535
+ "**/__tests__/**",
536
+ "**/{karma,rollup,webpack,vite,vitest,jest,ava,babel,nyc}.config.{js,cjs,mjs,ts}",
537
+ "**/.{eslint,mocha,prettier}rc.{js,cjs,yml}"
538
+ ];
539
+ const coverageConfigDefaults = {
540
+ enabled: false,
541
+ clean: true,
542
+ cleanOnRerun: false,
543
+ reportsDirectory: "./coverage",
544
+ excludeNodeModules: true,
545
+ exclude: defaultCoverageExcludes,
546
+ reporter: ["text", "html"],
547
+ allowExternal: false,
548
+ extension: [".js", ".cjs", ".mjs", ".ts", ".tsx", ".jsx", ".vue", ".svelte"]
549
+ };
550
+ const fakeTimersDefaults = {
551
+ loopLimit: 1e4,
552
+ shouldClearNativeTimers: true,
553
+ toFake: [
554
+ "setTimeout",
555
+ "clearTimeout",
556
+ "setInterval",
557
+ "clearInterval",
558
+ "setImmediate",
559
+ "clearImmediate",
560
+ "Date"
561
+ ]
562
+ };
563
+ const config = {
564
+ allowOnly: !process.env.CI,
565
+ watch: !process.env.CI,
566
+ globals: false,
567
+ environment: "node",
568
+ threads: true,
569
+ clearMocks: false,
570
+ restoreMocks: false,
571
+ mockReset: false,
572
+ include: defaultInclude,
573
+ exclude: defaultExclude,
574
+ testTimeout: 5e3,
575
+ hookTimeout: 1e4,
576
+ isolate: true,
577
+ watchExclude: ["**/node_modules/**", "**/dist/**"],
578
+ forceRerunTriggers: [],
579
+ update: false,
580
+ reporters: [],
581
+ silent: false,
582
+ api: false,
583
+ ui: false,
584
+ uiBase: "/__vitest__/",
585
+ open: true,
586
+ css: {
587
+ include: [/\.module\./]
588
+ },
589
+ coverage: coverageConfigDefaults,
590
+ fakeTimers: fakeTimersDefaults,
591
+ maxConcurrency: 5
592
+ };
593
+ const configDefaults = Object.freeze(config);
594
+
595
+ function resolveC8Options(options, root) {
596
+ const resolved = {
597
+ ...configDefaults.coverage,
598
+ ...options
599
+ };
600
+ resolved.reporter = toArray(resolved.reporter);
601
+ resolved.reportsDirectory = resolve(root, resolved.reportsDirectory);
602
+ resolved.tempDirectory = process.env.NODE_V8_COVERAGE || resolve(resolved.reportsDirectory, "tmp");
603
+ return resolved;
604
+ }
605
+ async function cleanCoverage(options, clean = true) {
606
+ if (clean && existsSync(options.reportsDirectory))
607
+ await promises.rm(options.reportsDirectory, { recursive: true, force: true });
608
+ if (!existsSync(options.tempDirectory))
609
+ await promises.mkdir(options.tempDirectory, { recursive: true });
610
+ }
611
+ const require = createRequire(import.meta.url);
612
+ function takeCoverage() {
613
+ const v8 = require("v8");
614
+ if (v8.takeCoverage == null)
615
+ console.warn("[Vitest] takeCoverage is not available in this NodeJs version.\nCoverage could be incomplete. Update to NodeJs 14.18.");
616
+ else
617
+ v8.takeCoverage();
618
+ }
619
+ async function reportCoverage(ctx) {
620
+ takeCoverage();
621
+ const createReport = require("c8/lib/report");
622
+ const report = createReport(ctx.config.coverage);
623
+ const sourceMapMeta = {};
624
+ await Promise.all(Array.from(ctx.vitenode.fetchCache.entries()).filter((i) => !i[0].includes("/node_modules/")).map(async ([file, { result }]) => {
625
+ const map = result.map;
626
+ if (!map)
627
+ return;
628
+ const url = pathToFileURL(file).href;
629
+ let code;
630
+ try {
631
+ code = (await promises.readFile(file)).toString();
632
+ } catch {
633
+ }
634
+ const sources = [url];
635
+ sourceMapMeta[url] = {
636
+ source: result.code,
637
+ map: {
638
+ sourcesContent: code ? [code] : void 0,
639
+ ...map,
640
+ sources
641
+ }
642
+ };
643
+ }));
644
+ const offset = 224;
645
+ report._getSourceMap = (coverage) => {
646
+ const path = pathToFileURL(coverage.url).href;
647
+ const data = sourceMapMeta[path];
648
+ if (!data)
649
+ return {};
650
+ return {
651
+ sourceMap: {
652
+ sourcemap: data.map
653
+ },
654
+ source: Array(offset).fill(".").join("") + data.source
655
+ };
656
+ };
657
+ await report.run();
658
+ if (ctx.config.coverage.enabled) {
659
+ if (ctx.config.coverage["100"]) {
660
+ ctx.config.coverage.lines = 100;
661
+ ctx.config.coverage.functions = 100;
662
+ ctx.config.coverage.branches = 100;
663
+ ctx.config.coverage.statements = 100;
664
+ }
665
+ const { checkCoverages } = require("c8/lib/commands/check-coverage");
666
+ await checkCoverages(ctx.config.coverage, report);
667
+ }
668
+ }
669
+
670
+ export { cleanCoverage as a, reportCoverage as b, configDefaults as c, environments as d, envPackageNames as e, envs as f, pLimit as p, resolveC8Options as r, takeCoverage as t };