vitest 0.0.109 → 0.0.113

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,4 +1,4 @@
1
- import { c, g as getNames, s as slash$1, a as getTests, i as isAbsolute, r as relative, d as dirname, b as basename, f as getSuites, h as resolve, n as noop$1, t as toArray, j as hasFailed } from './utils-d97bd6d9.js';
1
+ import { i as isAbsolute, r as relative, d as dirname, b as basename, a as resolve } from './index-1488b423.js';
2
2
  import { createServer, mergeConfig } from 'vite';
3
3
  import path$a from 'path';
4
4
  import process$1 from 'process';
@@ -7,9 +7,11 @@ import require$$0 from 'os';
7
7
  import require$$0$1 from 'util';
8
8
  import require$$0$2 from 'stream';
9
9
  import require$$2 from 'events';
10
- import { d as defaultInclude, a as defaultExclude, b as defaultPort, c as distDir, e as configFiles } from './constants-e762cbc5.js';
10
+ import { c, s as slash$1, g as getFullName, h as hasFailed, a as getSuites, b as getTests, n as noop$1, t as toArray } from './index-041e627e.js';
11
+ import { d as defaultInclude, a as defaultExclude, b as defaultPort, c as distDir, e as configFiles } from './constants-900abe4a.js';
12
+ import MagicString from './magic-string.es-94000aea.js';
11
13
  import { performance } from 'perf_hooks';
12
- import { s as stringWidth, a as ansiStyles, b as stripAnsi, c as sliceAnsi, F as F_POINTER, d as F_DOWN, e as F_LONG_DASH, f as F_DOWN_RIGHT, g as F_DOT, h as F_CHECK, i as F_CROSS, j as cliTruncate, k as F_RIGHT, p as printError } from './diff-46ee5d7d.js';
14
+ import { F as F_POINTER, a as F_DOWN, s as stripAnsi, b as F_LONG_DASH, c as F_DOWN_RIGHT, d as F_DOT, e as F_CHECK, f as F_CROSS, g as F_RIGHT, p as printError, h as stringWidth, i as ansiStyles, j as sliceAnsi, k as cliTruncate } from './diff-9c43ab50.js';
13
15
  import { o as onetime, s as signalExit } from './index-61c8686f.js';
14
16
  import { MessageChannel } from 'worker_threads';
15
17
  import { pathToFileURL } from 'url';
@@ -411,7 +413,7 @@ var isExtglob$1 = function isExtglob(str) {
411
413
  */
412
414
 
413
415
  var isExtglob = isExtglob$1;
414
- var chars$1 = { '{': '}', '(': ')', '[': ']'};
416
+ var chars = { '{': '}', '(': ')', '[': ']'};
415
417
  var strictCheck = function(str) {
416
418
  if (str[0] === '!') {
417
419
  return true;
@@ -484,7 +486,7 @@ var strictCheck = function(str) {
484
486
  if (str[index] === '\\') {
485
487
  var open = str[index + 1];
486
488
  index += 2;
487
- var close = chars$1[open];
489
+ var close = chars[open];
488
490
 
489
491
  if (close) {
490
492
  var n = str.indexOf(close, index);
@@ -516,7 +518,7 @@ var relaxedCheck = function(str) {
516
518
  if (str[index] === '\\') {
517
519
  var open = str[index + 1];
518
520
  index += 2;
519
- var close = chars$1[open];
521
+ var close = chars[open];
520
522
 
521
523
  if (close) {
522
524
  var n = str.indexOf(close, index);
@@ -1055,7 +1057,7 @@ var toRegexRange_1 = toRegexRange$1;
1055
1057
  const util$1 = require$$0$1;
1056
1058
  const toRegexRange = toRegexRange_1;
1057
1059
 
1058
- const isObject$2 = val => val !== null && typeof val === 'object' && !Array.isArray(val);
1060
+ const isObject$1 = val => val !== null && typeof val === 'object' && !Array.isArray(val);
1059
1061
 
1060
1062
  const transform = toNumber => {
1061
1063
  return value => toNumber === true ? Number(value) : String(value);
@@ -1271,7 +1273,7 @@ const fill$2 = (start, end, step, options = {}) => {
1271
1273
  return fill$2(start, end, 1, { transform: step });
1272
1274
  }
1273
1275
 
1274
- if (isObject$2(step)) {
1276
+ if (isObject$1(step)) {
1275
1277
  return fill$2(start, end, 0, step);
1276
1278
  }
1277
1279
 
@@ -1280,7 +1282,7 @@ const fill$2 = (start, end, step, options = {}) => {
1280
1282
  step = step || opts.step || 1;
1281
1283
 
1282
1284
  if (!isNumber(step)) {
1283
- if (step != null && !isObject$2(step)) return invalidStep(step, opts);
1285
+ if (step != null && !isObject$1(step)) return invalidStep(step, opts);
1284
1286
  return fill$2(start, end, 1, step);
1285
1287
  }
1286
1288
 
@@ -3739,7 +3741,7 @@ const scan = scan_1;
3739
3741
  const parse = parse_1;
3740
3742
  const utils$c = utils$f;
3741
3743
  const constants$1 = constants$3;
3742
- const isObject$1 = val => val && typeof val === 'object' && !Array.isArray(val);
3744
+ const isObject = val => val && typeof val === 'object' && !Array.isArray(val);
3743
3745
 
3744
3746
  /**
3745
3747
  * Creates a matcher function from one or more glob patterns. The
@@ -3776,7 +3778,7 @@ const picomatch$2 = (glob, options, returnState = false) => {
3776
3778
  return arrayMatcher;
3777
3779
  }
3778
3780
 
3779
- const isState = isObject$1(glob) && glob.tokens && glob.input;
3781
+ const isState = isObject(glob) && glob.tokens && glob.input;
3780
3782
 
3781
3783
  if (glob === '' || (typeof glob !== 'string' && !isState)) {
3782
3784
  throw new TypeError('Expected pattern to be a non-empty string');
@@ -6750,515 +6752,124 @@ function addSnapshotResult(summary, result) {
6750
6752
  summary.total += result.added + result.matched + result.unmatched + result.updated;
6751
6753
  }
6752
6754
 
6753
- const ESC = '\u001B[';
6754
- const OSC = '\u001B]';
6755
- const BEL = '\u0007';
6756
- const SEP = ';';
6757
- const isTerminalApp = process.env.TERM_PROGRAM === 'Apple_Terminal';
6758
-
6759
- const ansiEscapes = {};
6760
-
6761
- ansiEscapes.cursorTo = (x, y) => {
6762
- if (typeof x !== 'number') {
6763
- throw new TypeError('The `x` argument is required');
6764
- }
6765
-
6766
- if (typeof y !== 'number') {
6767
- return ESC + (x + 1) + 'G';
6768
- }
6769
-
6770
- return ESC + (y + 1) + ';' + (x + 1) + 'H';
6771
- };
6772
-
6773
- ansiEscapes.cursorMove = (x, y) => {
6774
- if (typeof x !== 'number') {
6775
- throw new TypeError('The `x` argument is required');
6776
- }
6777
-
6778
- let returnValue = '';
6779
-
6780
- if (x < 0) {
6781
- returnValue += ESC + (-x) + 'D';
6782
- } else if (x > 0) {
6783
- returnValue += ESC + x + 'C';
6784
- }
6785
-
6786
- if (y < 0) {
6787
- returnValue += ESC + (-y) + 'A';
6788
- } else if (y > 0) {
6789
- returnValue += ESC + y + 'B';
6790
- }
6791
-
6792
- return returnValue;
6793
- };
6794
-
6795
- ansiEscapes.cursorUp = (count = 1) => ESC + count + 'A';
6796
- ansiEscapes.cursorDown = (count = 1) => ESC + count + 'B';
6797
- ansiEscapes.cursorForward = (count = 1) => ESC + count + 'C';
6798
- ansiEscapes.cursorBackward = (count = 1) => ESC + count + 'D';
6799
-
6800
- ansiEscapes.cursorLeft = ESC + 'G';
6801
- ansiEscapes.cursorSavePosition = isTerminalApp ? '\u001B7' : ESC + 's';
6802
- ansiEscapes.cursorRestorePosition = isTerminalApp ? '\u001B8' : ESC + 'u';
6803
- ansiEscapes.cursorGetPosition = ESC + '6n';
6804
- ansiEscapes.cursorNextLine = ESC + 'E';
6805
- ansiEscapes.cursorPrevLine = ESC + 'F';
6806
- ansiEscapes.cursorHide = ESC + '?25l';
6807
- ansiEscapes.cursorShow = ESC + '?25h';
6808
-
6809
- ansiEscapes.eraseLines = count => {
6810
- let clear = '';
6811
-
6812
- for (let i = 0; i < count; i++) {
6813
- clear += ansiEscapes.eraseLine + (i < count - 1 ? ansiEscapes.cursorUp() : '');
6814
- }
6815
-
6816
- if (count) {
6817
- clear += ansiEscapes.cursorLeft;
6818
- }
6819
-
6820
- return clear;
6821
- };
6822
-
6823
- ansiEscapes.eraseEndLine = ESC + 'K';
6824
- ansiEscapes.eraseStartLine = ESC + '1K';
6825
- ansiEscapes.eraseLine = ESC + '2K';
6826
- ansiEscapes.eraseDown = ESC + 'J';
6827
- ansiEscapes.eraseUp = ESC + '1J';
6828
- ansiEscapes.eraseScreen = ESC + '2J';
6829
- ansiEscapes.scrollUp = ESC + 'S';
6830
- ansiEscapes.scrollDown = ESC + 'T';
6831
-
6832
- ansiEscapes.clearScreen = '\u001Bc';
6833
-
6834
- ansiEscapes.clearTerminal = process.platform === 'win32' ?
6835
- `${ansiEscapes.eraseScreen}${ESC}0f` :
6836
- // 1. Erases the screen (Only done in case `2` is not supported)
6837
- // 2. Erases the whole screen including scrollback buffer
6838
- // 3. Moves cursor to the top-left position
6839
- // More info: https://www.real-world-systems.com/docs/ANSIcode.html
6840
- `${ansiEscapes.eraseScreen}${ESC}3J${ESC}H`;
6841
-
6842
- ansiEscapes.beep = BEL;
6843
-
6844
- ansiEscapes.link = (text, url) => {
6845
- return [
6846
- OSC,
6847
- '8',
6848
- SEP,
6849
- SEP,
6850
- url,
6851
- BEL,
6852
- text,
6853
- OSC,
6854
- '8',
6855
- SEP,
6856
- SEP,
6857
- BEL
6858
- ].join('');
6859
- };
6860
-
6861
- ansiEscapes.image = (buffer, options = {}) => {
6862
- let returnValue = `${OSC}1337;File=inline=1`;
6863
-
6864
- if (options.width) {
6865
- returnValue += `;width=${options.width}`;
6866
- }
6867
-
6868
- if (options.height) {
6869
- returnValue += `;height=${options.height}`;
6870
- }
6871
-
6872
- if (options.preserveAspectRatio === false) {
6873
- returnValue += ';preserveAspectRatio=0';
6874
- }
6875
-
6876
- return returnValue + ':' + buffer.toString('base64') + BEL;
6877
- };
6878
-
6879
- ansiEscapes.iTerm = {
6880
- setCwd: (cwd = process.cwd()) => `${OSC}50;CurrentDir=${cwd}${BEL}`,
6881
-
6882
- annotation: (message, options = {}) => {
6883
- let returnValue = `${OSC}1337;`;
6884
-
6885
- const hasX = typeof options.x !== 'undefined';
6886
- const hasY = typeof options.y !== 'undefined';
6887
- if ((hasX || hasY) && !(hasX && hasY && typeof options.length !== 'undefined')) {
6888
- throw new Error('`x`, `y` and `length` must be defined when `x` or `y` is defined');
6889
- }
6890
-
6891
- message = message.replace(/\|/g, '');
6892
-
6893
- returnValue += options.isHidden ? 'AddHiddenAnnotation=' : 'AddAnnotation=';
6894
-
6895
- if (options.length > 0) {
6896
- returnValue +=
6897
- (hasX ?
6898
- [message, options.length, options.x, options.y] :
6899
- [options.length, message]).join('|');
6900
- } else {
6901
- returnValue += message;
6902
- }
6903
-
6904
- return returnValue + BEL;
6905
- }
6906
- };
6907
-
6908
- const restoreCursor = onetime(() => {
6909
- signalExit(() => {
6910
- process$1.stderr.write('\u001B[?25h');
6911
- }, {alwaysLast: true});
6912
- });
6913
-
6914
- let isHidden = false;
6915
-
6916
- const cliCursor = {};
6917
-
6918
- cliCursor.show = (writableStream = process$1.stderr) => {
6919
- if (!writableStream.isTTY) {
6920
- return;
6921
- }
6922
-
6923
- isHidden = false;
6924
- writableStream.write('\u001B[?25h');
6925
- };
6926
-
6927
- cliCursor.hide = (writableStream = process$1.stderr) => {
6928
- if (!writableStream.isTTY) {
6929
- return;
6930
- }
6931
-
6932
- restoreCursor();
6933
- isHidden = true;
6934
- writableStream.write('\u001B[?25l');
6935
- };
6936
-
6937
- cliCursor.toggle = (force, writableStream) => {
6938
- if (force !== undefined) {
6939
- isHidden = force;
6940
- }
6941
-
6942
- if (isHidden) {
6943
- cliCursor.show(writableStream);
6944
- } else {
6945
- cliCursor.hide(writableStream);
6946
- }
6947
- };
6948
-
6949
- const ESCAPES = new Set([
6950
- '\u001B',
6951
- '\u009B',
6952
- ]);
6953
-
6954
- const END_CODE = 39;
6955
- const ANSI_ESCAPE_BELL = '\u0007';
6956
- const ANSI_CSI = '[';
6957
- const ANSI_OSC = ']';
6958
- const ANSI_SGR_TERMINATOR = 'm';
6959
- const ANSI_ESCAPE_LINK = `${ANSI_OSC}8;;`;
6960
-
6961
- const wrapAnsiCode = code => `${ESCAPES.values().next().value}${ANSI_CSI}${code}${ANSI_SGR_TERMINATOR}`;
6962
- const wrapAnsiHyperlink = uri => `${ESCAPES.values().next().value}${ANSI_ESCAPE_LINK}${uri}${ANSI_ESCAPE_BELL}`;
6963
-
6964
- // Calculate the length of words split on ' ', ignoring
6965
- // the extra characters added by ansi escape codes
6966
- const wordLengths = string => string.split(' ').map(character => stringWidth(character));
6967
-
6968
- // Wrap a long word across multiple rows
6969
- // Ansi escape codes do not count towards length
6970
- const wrapWord = (rows, word, columns) => {
6971
- const characters = [...word];
6972
-
6973
- let isInsideEscape = false;
6974
- let isInsideLinkEscape = false;
6975
- let visible = stringWidth(stripAnsi(rows[rows.length - 1]));
6976
-
6977
- for (const [index, character] of characters.entries()) {
6978
- const characterLength = stringWidth(character);
6979
-
6980
- if (visible + characterLength <= columns) {
6981
- rows[rows.length - 1] += character;
6982
- } else {
6983
- rows.push(character);
6984
- visible = 0;
6985
- }
6986
-
6987
- if (ESCAPES.has(character)) {
6988
- isInsideEscape = true;
6989
- isInsideLinkEscape = characters.slice(index + 1).join('').startsWith(ANSI_ESCAPE_LINK);
6990
- }
6991
-
6992
- if (isInsideEscape) {
6993
- if (isInsideLinkEscape) {
6994
- if (character === ANSI_ESCAPE_BELL) {
6995
- isInsideEscape = false;
6996
- isInsideLinkEscape = false;
6997
- }
6998
- } else if (character === ANSI_SGR_TERMINATOR) {
6999
- isInsideEscape = false;
7000
- }
7001
-
7002
- continue;
7003
- }
7004
-
7005
- visible += characterLength;
7006
-
7007
- if (visible === columns && index < characters.length - 1) {
7008
- rows.push('');
7009
- visible = 0;
7010
- }
7011
- }
7012
-
7013
- // It's possible that the last row we copy over is only
7014
- // ansi escape characters, handle this edge-case
7015
- if (!visible && rows[rows.length - 1].length > 0 && rows.length > 1) {
7016
- rows[rows.length - 2] += rows.pop();
7017
- }
7018
- };
7019
-
7020
- // Trims spaces from a string ignoring invisible sequences
7021
- const stringVisibleTrimSpacesRight = string => {
7022
- const words = string.split(' ');
7023
- let last = words.length;
7024
-
7025
- while (last > 0) {
7026
- if (stringWidth(words[last - 1]) > 0) {
7027
- break;
7028
- }
7029
-
7030
- last--;
7031
- }
7032
-
7033
- if (last === words.length) {
7034
- return string;
7035
- }
7036
-
7037
- return words.slice(0, last).join(' ') + words.slice(last).join('');
7038
- };
7039
-
7040
- // The wrap-ansi module can be invoked in either 'hard' or 'soft' wrap mode
7041
- //
7042
- // 'hard' will never allow a string to take up more than columns characters
7043
- //
7044
- // 'soft' allows long words to expand past the column length
7045
- const exec = (string, columns, options = {}) => {
7046
- if (options.trim !== false && string.trim() === '') {
7047
- return '';
7048
- }
7049
-
7050
- let returnValue = '';
7051
- let escapeCode;
7052
- let escapeUrl;
7053
-
7054
- const lengths = wordLengths(string);
7055
- let rows = [''];
7056
-
7057
- for (const [index, word] of string.split(' ').entries()) {
7058
- if (options.trim !== false) {
7059
- rows[rows.length - 1] = rows[rows.length - 1].trimStart();
7060
- }
7061
-
7062
- let rowLength = stringWidth(rows[rows.length - 1]);
7063
-
7064
- if (index !== 0) {
7065
- if (rowLength >= columns && (options.wordWrap === false || options.trim === false)) {
7066
- // If we start with a new word but the current row length equals the length of the columns, add a new row
7067
- rows.push('');
7068
- rowLength = 0;
7069
- }
7070
-
7071
- if (rowLength > 0 || options.trim === false) {
7072
- rows[rows.length - 1] += ' ';
7073
- rowLength++;
7074
- }
7075
- }
7076
-
7077
- // In 'hard' wrap mode, the length of a line is never allowed to extend past 'columns'
7078
- if (options.hard && lengths[index] > columns) {
7079
- const remainingColumns = (columns - rowLength);
7080
- const breaksStartingThisLine = 1 + Math.floor((lengths[index] - remainingColumns - 1) / columns);
7081
- const breaksStartingNextLine = Math.floor((lengths[index] - 1) / columns);
7082
- if (breaksStartingNextLine < breaksStartingThisLine) {
7083
- rows.push('');
7084
- }
7085
-
7086
- wrapWord(rows, word, columns);
7087
- continue;
7088
- }
7089
-
7090
- if (rowLength + lengths[index] > columns && rowLength > 0 && lengths[index] > 0) {
7091
- if (options.wordWrap === false && rowLength < columns) {
7092
- wrapWord(rows, word, columns);
7093
- continue;
7094
- }
7095
-
7096
- rows.push('');
7097
- }
7098
-
7099
- if (rowLength + lengths[index] > columns && options.wordWrap === false) {
7100
- wrapWord(rows, word, columns);
7101
- continue;
7102
- }
7103
-
7104
- rows[rows.length - 1] += word;
7105
- }
7106
-
7107
- if (options.trim !== false) {
7108
- rows = rows.map(row => stringVisibleTrimSpacesRight(row));
7109
- }
7110
-
7111
- const pre = [...rows.join('\n')];
7112
-
7113
- for (const [index, character] of pre.entries()) {
7114
- returnValue += character;
7115
-
7116
- if (ESCAPES.has(character)) {
7117
- const {groups} = new RegExp(`(?:\\${ANSI_CSI}(?<code>\\d+)m|\\${ANSI_ESCAPE_LINK}(?<uri>.*)${ANSI_ESCAPE_BELL})`).exec(pre.slice(index).join('')) || {groups: {}};
7118
- if (groups.code !== undefined) {
7119
- const code = Number.parseFloat(groups.code);
7120
- escapeCode = code === END_CODE ? undefined : code;
7121
- } else if (groups.uri !== undefined) {
7122
- escapeUrl = groups.uri.length === 0 ? undefined : groups.uri;
7123
- }
7124
- }
7125
-
7126
- const code = ansiStyles.codes.get(Number(escapeCode));
7127
-
7128
- if (pre[index + 1] === '\n') {
7129
- if (escapeUrl) {
7130
- returnValue += wrapAnsiHyperlink('');
7131
- }
7132
-
7133
- if (escapeCode && code) {
7134
- returnValue += wrapAnsiCode(code);
7135
- }
7136
- } else if (character === '\n') {
7137
- if (escapeCode && code) {
7138
- returnValue += wrapAnsiCode(escapeCode);
7139
- }
7140
-
7141
- if (escapeUrl) {
7142
- returnValue += wrapAnsiHyperlink(escapeUrl);
7143
- }
7144
- }
7145
- }
7146
-
7147
- return returnValue;
6755
+ const mockRegexp = /\b((?:vitest|vi)\s*.\s*mock\(["`'\s](.*[@\w_-]+)["`'\s])[),]{1}/;
6756
+ const pathRegexp = /\b(?:vitest|vi)\s*.\s*(unmock|importActual|importMock)\(["`'\s](.*[@\w_-]+)["`'\s]\);?/mg;
6757
+ const isComment = (line) => {
6758
+ const commentStarts = ["//", "/*", "*"];
6759
+ line = line.trim();
6760
+ return commentStarts.some((cmt) => line.startsWith(cmt));
6761
+ };
6762
+ const parseMocks = (code) => {
6763
+ const splitted = code.split("\n");
6764
+ const mockCalls = {};
6765
+ let mockCall = 0;
6766
+ let lineIndex = -1;
6767
+ while (lineIndex < splitted.length) {
6768
+ lineIndex++;
6769
+ const line = splitted[lineIndex];
6770
+ if (!line)
6771
+ break;
6772
+ const mock = mockCalls[mockCall] || {
6773
+ code: "",
6774
+ declaraton: "",
6775
+ path: ""
6776
+ };
6777
+ if (!mock.code) {
6778
+ const started = mockRegexp.exec(line);
6779
+ if (!started || isComment(line))
6780
+ continue;
6781
+ mock.code += `${line}
6782
+ `;
6783
+ mock.declaraton = started[1];
6784
+ mock.path = started[2];
6785
+ mockCalls[mockCall] = mock;
6786
+ if (line.includes(");")) {
6787
+ mockCall++;
6788
+ continue;
6789
+ }
6790
+ continue;
6791
+ }
6792
+ mock.code += `${line}
6793
+ `;
6794
+ mockCalls[mockCall] = mock;
6795
+ const startNumber = (mock.code.match(/{/g) || []).length;
6796
+ const endNumber = (mock.code.match(/}/g) || []).length;
6797
+ if (line.includes(");")) {
6798
+ if (startNumber === endNumber || startNumber === 0 && endNumber === 0)
6799
+ mockCall++;
6800
+ }
6801
+ }
6802
+ return Object.values(mockCalls);
7148
6803
  };
7149
-
7150
- // For each newline, invoke the method separately
7151
- function wrapAnsi(string, columns, options) {
7152
- return String(string)
7153
- .normalize()
7154
- .replace(/\r\n/g, '\n')
7155
- .split('\n')
7156
- .map(line => exec(line, columns, options))
7157
- .join('\n');
7158
- }
7159
-
7160
- const defaultTerminalHeight = 24;
7161
-
7162
- const getWidth = stream => {
7163
- const {columns} = stream;
7164
-
7165
- if (!columns) {
7166
- return 80;
7167
- }
7168
-
7169
- return columns;
6804
+ const getMethodCall = (method, actualPath, importPath) => {
6805
+ let nodeModule = "null";
6806
+ if (actualPath.includes("/node_modules/"))
6807
+ nodeModule = `"${importPath}"`;
6808
+ return `__vitest__${method}__("${actualPath}", ${nodeModule}`;
7170
6809
  };
7171
-
7172
- const fitToTerminalHeight = (stream, text) => {
7173
- const terminalHeight = stream.rows || defaultTerminalHeight;
7174
- const lines = text.split('\n');
7175
-
7176
- const toRemove = lines.length - terminalHeight;
7177
- if (toRemove <= 0) {
7178
- return text;
7179
- }
7180
-
7181
- return sliceAnsi(
7182
- text,
7183
- lines.slice(0, toRemove).join('\n').length + 1,
7184
- text.length);
6810
+ const MocksPlugin = () => {
6811
+ return {
6812
+ name: "vitest:mock-plugin",
6813
+ enforce: "post",
6814
+ async transform(code, id) {
6815
+ let m;
6816
+ const matchAll = code.matchAll(pathRegexp);
6817
+ for (const match of matchAll) {
6818
+ const [line, method, modulePath] = match;
6819
+ const filepath = await this.resolve(modulePath, id);
6820
+ if (filepath) {
6821
+ m ?? (m = new MagicString(code));
6822
+ const start = match.index || 0;
6823
+ const end = start + line.length;
6824
+ const overwrite = `${getMethodCall(method, filepath.id, modulePath)});`;
6825
+ m.overwrite(start, end, overwrite);
6826
+ }
6827
+ }
6828
+ if (mockRegexp.exec(code)) {
6829
+ const mocks = parseMocks((m == null ? void 0 : m.toString()) || code);
6830
+ for (const mock of mocks) {
6831
+ const filepath = await this.resolve(mock.path, id);
6832
+ if (!filepath)
6833
+ continue;
6834
+ m ?? (m = new MagicString(code));
6835
+ const overwrite = getMethodCall("mock", filepath.id, mock.path);
6836
+ m.prepend(mock.code.replace(mock.declaraton, overwrite));
6837
+ }
6838
+ }
6839
+ if (m) {
6840
+ return {
6841
+ code: m.toString(),
6842
+ map: m.generateMap()
6843
+ };
6844
+ }
6845
+ }
6846
+ };
7185
6847
  };
7186
6848
 
7187
- function createLogUpdate(stream, {showCursor = false} = {}) {
7188
- let previousLineCount = 0;
7189
- let previousWidth = getWidth(stream);
7190
- let previousOutput = '';
7191
-
7192
- const render = (...arguments_) => {
7193
- if (!showCursor) {
7194
- cliCursor.hide();
7195
- }
7196
-
7197
- let output = arguments_.join(' ') + '\n';
7198
- output = fitToTerminalHeight(stream, output);
7199
- const width = getWidth(stream);
7200
- if (output === previousOutput && previousWidth === width) {
7201
- return;
7202
- }
7203
-
7204
- previousOutput = output;
7205
- previousWidth = width;
7206
- output = wrapAnsi(output, width, {
7207
- trim: false,
7208
- hard: true,
7209
- wordWrap: false,
7210
- });
7211
- stream.write(ansiEscapes.eraseLines(previousLineCount) + output);
7212
- previousLineCount = output.split('\n').length;
7213
- };
7214
-
7215
- render.clear = () => {
7216
- stream.write(ansiEscapes.eraseLines(previousLineCount));
7217
- previousOutput = '';
7218
- previousWidth = getWidth(stream);
7219
- previousLineCount = 0;
7220
- };
7221
-
7222
- render.done = () => {
7223
- previousOutput = '';
7224
- previousWidth = getWidth(stream);
7225
- previousLineCount = 0;
7226
-
7227
- if (!showCursor) {
7228
- cliCursor.show();
7229
- }
7230
- };
7231
-
7232
- return render;
7233
- }
7234
-
7235
- createLogUpdate(process$1.stdout);
7236
-
7237
- createLogUpdate(process$1.stderr);
7238
-
7239
- const DURATION_LONG = 300;
7240
- const MAX_HEIGHT = 20;
7241
6849
  const spinnerMap = /* @__PURE__ */ new WeakMap();
7242
- const outputMap = /* @__PURE__ */ new WeakMap();
7243
6850
  const pointer = c.yellow(F_POINTER);
7244
6851
  const skipped = c.yellow(F_DOWN);
7245
- function divider(text, left, right) {
6852
+ function getCols(delta = 0) {
7246
6853
  let length = process.stdout.columns;
7247
6854
  if (!length || isNaN(length))
7248
- length = 10;
6855
+ length = 30;
6856
+ return Math.max(length + delta, 0);
6857
+ }
6858
+ function divider(text, left, right) {
6859
+ const cols = getCols();
7249
6860
  if (text) {
7250
6861
  const textLength = stripAnsi(text).length;
7251
6862
  if (left == null && right != null) {
7252
- left = length - textLength - right;
6863
+ left = cols - textLength - right;
7253
6864
  } else {
7254
- left = left ?? Math.floor((length - textLength) / 2);
7255
- right = length - textLength - left;
6865
+ left = left ?? Math.floor((cols - textLength) / 2);
6866
+ right = cols - textLength - left;
7256
6867
  }
7257
6868
  left = Math.max(0, left);
7258
6869
  right = Math.max(0, right);
7259
6870
  return `${F_LONG_DASH.repeat(left)}${text}${F_LONG_DASH.repeat(right)}`;
7260
6871
  }
7261
- return F_LONG_DASH.repeat(length);
6872
+ return F_LONG_DASH.repeat(cols);
7262
6873
  }
7263
6874
  function formatTestPath(root, path) {
7264
6875
  var _a;
@@ -7324,96 +6935,25 @@ function getStateString(tasks, name = "tests") {
7324
6935
  }
7325
6936
  function getStateSymbol(task) {
7326
6937
  if (task.mode === "skip" || task.mode === "todo")
7327
- return skipped;
7328
- if (!task.result)
7329
- return c.gray("\xB7");
7330
- if (task.result.state === "run") {
7331
- if (task.type === "suite")
7332
- return pointer;
7333
- let spinner = spinnerMap.get(task);
7334
- if (!spinner) {
7335
- spinner = elegantSpinner();
7336
- spinnerMap.set(task, spinner);
7337
- }
7338
- return c.yellow(spinner());
7339
- }
7340
- if (task.result.state === "pass")
7341
- return c.green(F_CHECK);
7342
- if (task.result.state === "fail") {
7343
- return task.type === "suite" ? pointer : c.red(F_CROSS);
7344
- }
7345
- return " ";
7346
- }
7347
- function renderTree(tasks, level = 0) {
7348
- var _a, _b, _c, _d;
7349
- let output = [];
7350
- for (const task of tasks) {
7351
- let suffix = "";
7352
- const prefix = ` ${getStateSymbol(task)} `;
7353
- if (task.mode === "skip" || task.mode === "todo")
7354
- suffix += ` ${c.dim("[skipped]")}`;
7355
- if (task.type === "suite")
7356
- suffix += c.dim(` (${getTests(task).length})`);
7357
- if ((_a = task.result) == null ? void 0 : _a.end) {
7358
- const duration = task.result.end - task.result.start;
7359
- if (duration > DURATION_LONG)
7360
- suffix += c.yellow(` ${Math.round(duration)}${c.dim("ms")}`);
7361
- }
7362
- output.push(" ".repeat(level) + prefix + task.name + suffix);
7363
- if (((_b = task.result) == null ? void 0 : _b.state) !== "pass" && outputMap.get(task) != null) {
7364
- let data = outputMap.get(task);
7365
- if (typeof data === "string") {
7366
- data = stripAnsi(data.trim().split("\n").filter(Boolean).pop());
7367
- if (data === "")
7368
- data = void 0;
7369
- }
7370
- if (data != null) {
7371
- const out = `${" ".repeat(level)}${F_RIGHT} ${data}`;
7372
- output.push(` ${c.gray(cliTruncate(out, process.stdout.columns - 3))}`);
7373
- }
6938
+ return skipped;
6939
+ if (!task.result)
6940
+ return c.gray("\xB7");
6941
+ if (task.result.state === "run") {
6942
+ if (task.type === "suite")
6943
+ return pointer;
6944
+ let spinner = spinnerMap.get(task);
6945
+ if (!spinner) {
6946
+ spinner = elegantSpinner();
6947
+ spinnerMap.set(task, spinner);
7374
6948
  }
7375
- if ((((_c = task.result) == null ? void 0 : _c.state) === "fail" || ((_d = task.result) == null ? void 0 : _d.state) === "run") && task.type === "suite" && task.tasks.length > 0)
7376
- output = output.concat(renderTree(task.tasks, level + 1));
6949
+ return c.yellow(spinner());
7377
6950
  }
7378
- return output.slice(0, MAX_HEIGHT).join("\n");
7379
- }
7380
- const createRenderer = (_tasks) => {
7381
- let tasks = _tasks;
7382
- let timer;
7383
- const stdout = process.stdout;
7384
- const log = createLogUpdate(stdout);
7385
- function update() {
7386
- log(renderTree(tasks));
6951
+ if (task.result.state === "pass")
6952
+ return c.green(F_CHECK);
6953
+ if (task.result.state === "fail") {
6954
+ return task.type === "suite" ? pointer : c.red(F_CROSS);
7387
6955
  }
7388
- return {
7389
- start() {
7390
- if (timer)
7391
- return this;
7392
- timer = setInterval(update, 200);
7393
- return this;
7394
- },
7395
- update(_tasks2) {
7396
- tasks = _tasks2;
7397
- update();
7398
- return this;
7399
- },
7400
- async stop() {
7401
- if (timer) {
7402
- clearInterval(timer);
7403
- timer = void 0;
7404
- }
7405
- log.clear();
7406
- stdout.write(`${renderTree(tasks)}
7407
- `);
7408
- return this;
7409
- },
7410
- clear() {
7411
- log.clear();
7412
- }
7413
- };
7414
- };
7415
- function getFullName(task) {
7416
- return getNames(task).join(c.dim(" > "));
6956
+ return " ";
7417
6957
  }
7418
6958
  const spinnerFrames = process.platform === "win32" ? ["-", "\\", "|", "/"] : ["\u280B", "\u2819", "\u2839", "\u2838", "\u283C", "\u2834", "\u2826", "\u2827", "\u2807", "\u280F"];
7419
6959
  function elegantSpinner() {
@@ -7424,14 +6964,14 @@ function elegantSpinner() {
7424
6964
  };
7425
6965
  }
7426
6966
 
7427
- const isTTY = process.stdout.isTTY && !process.env.CI;
7428
- class ConsoleReporter {
6967
+ class BaseReporter {
7429
6968
  constructor(ctx) {
7430
6969
  this.ctx = ctx;
7431
6970
  this.start = 0;
7432
6971
  this.end = 0;
6972
+ this.isTTY = process.stdout.isTTY && !process.env.CI;
7433
6973
  this.isFirstWatchRun = true;
7434
- const mode = ctx.config.watch ? c.yellow(" DEV ") : c.cyan(" RUN ");
6974
+ const mode = ctx.config.watch ? c.blue(" WATCH ") : c.cyan(" RUN ");
7435
6975
  this.ctx.log(`
7436
6976
  ${c.inverse(c.bold(mode))} ${c.gray(this.ctx.config.root)}
7437
6977
  `);
@@ -7440,1249 +6980,846 @@ ${c.inverse(c.bold(mode))} ${c.gray(this.ctx.config.root)}
7440
6980
  relative(path) {
7441
6981
  return relative(this.ctx.config.root, path);
7442
6982
  }
7443
- onStart() {
7444
- if (isTTY) {
7445
- const files = this.ctx.state.getFiles(this.watchFilters);
7446
- if (!this.renderer)
7447
- this.renderer = createRenderer(files).start();
7448
- else
7449
- this.renderer.update(files);
7450
- }
6983
+ async onFinished(files = this.ctx.state.getFiles()) {
6984
+ this.end = performance.now();
6985
+ await this.reportSummary(files);
7451
6986
  }
7452
6987
  onTaskUpdate(pack) {
7453
6988
  var _a, _b, _c;
7454
- if (isTTY)
6989
+ if (this.isTTY)
7455
6990
  return;
7456
6991
  const task = this.ctx.state.idMap[pack[0]];
7457
- if (task.type === "test" && ((_a = task.result) == null ? void 0 : _a.state) && ((_b = task.result) == null ? void 0 : _b.state) !== "run") {
7458
- this.ctx.log(` ${getStateSymbol(task)} ${getFullName(task)}`);
7459
- if (task.result.state === "fail")
7460
- this.ctx.log(c.red(` ${F_RIGHT} ${(_c = task.result.error) == null ? void 0 : _c.message}`));
7461
- }
7462
- }
7463
- async onFinished(files = this.ctx.state.getFiles()) {
7464
- var _a, _b;
7465
- this.end = performance.now();
7466
- await this.stopListRender();
7467
- this.ctx.log();
7468
- const suites = getSuites(files);
7469
- const tests = getTests(files);
7470
- const failedSuites = suites.filter((i) => {
7471
- var _a2;
7472
- return (_a2 = i.result) == null ? void 0 : _a2.error;
7473
- });
7474
- const failedTests = tests.filter((i) => {
7475
- var _a2;
7476
- return ((_a2 = i.result) == null ? void 0 : _a2.state) === "fail";
7477
- });
7478
- const failedTotal = failedSuites.length + failedTests.length;
7479
- let current = 1;
7480
- const errorDivider = () => this.ctx.error(`${c.red(c.dim(divider(`[${current++}/${failedTotal}]`, void 0, 1)))}
7481
- `);
7482
- if (failedSuites.length) {
7483
- this.ctx.error(c.red(divider(c.bold(c.inverse(` Failed Suites ${failedSuites.length} `)))));
7484
- this.ctx.error();
7485
- for (const suite of failedSuites) {
7486
- const filepath = (suite == null ? void 0 : suite.filepath) || "";
7487
- this.ctx.error(c.red(`
7488
- - ${getFullName(suite)} ${c.dim(`[ ${this.relative(filepath)} ]`)}`));
7489
- await printError((_a = suite.result) == null ? void 0 : _a.error, this.ctx);
7490
- errorDivider();
7491
- }
7492
- }
7493
- if (failedTests.length) {
7494
- this.ctx.error(c.red(divider(c.bold(c.inverse(` Failed Tests ${failedTests.length} `)))));
7495
- this.ctx.error();
7496
- for (const test of failedTests) {
7497
- this.ctx.error(`${c.red(c.bold(c.inverse(" FAIL ")))} ${getFullName(test)}`);
7498
- await printError((_b = test.result) == null ? void 0 : _b.error, this.ctx);
7499
- errorDivider();
7500
- }
7501
- }
7502
- const executionTime = this.end - this.start;
7503
- const threadTime = tests.reduce((acc, test) => {
7504
- var _a2;
7505
- return acc + (((_a2 = test.result) == null ? void 0 : _a2.end) ? test.result.end - test.result.start : 0);
7506
- }, 0);
7507
- const padTitle = (str) => c.dim(`${str.padStart(10)} `);
7508
- const time = (time2) => {
7509
- if (time2 > 1e3)
7510
- return `${(time2 / 1e3).toFixed(2)}s`;
7511
- return `${Math.round(time2)}ms`;
7512
- };
7513
- const snapshotOutput = renderSnapshotSummary(this.ctx.config.root, this.ctx.snapshot.summary);
7514
- if (snapshotOutput.length) {
7515
- this.ctx.log(snapshotOutput.map((t, i) => i === 0 ? `${padTitle("Snapshots")} ${t}` : `${padTitle("")} ${t}`).join("\n"));
7516
- if (snapshotOutput.length > 1)
7517
- this.ctx.log();
7518
- }
7519
- this.ctx.log(padTitle("Test Files"), getStateString(files));
7520
- this.ctx.log(padTitle("Tests"), getStateString(tests));
7521
- if (this.watchFilters)
7522
- this.ctx.log(padTitle("Time"), time(threadTime));
7523
- else
7524
- this.ctx.log(padTitle("Time"), time(executionTime) + c.gray(` (in thread ${time(threadTime)}, ${(executionTime / threadTime * 100).toFixed(2)}%)`));
7525
- this.ctx.log();
7526
- }
7527
- async onWatcherStart() {
7528
- await this.stopListRender();
7529
- const failed = getTests(this.ctx.state.getFiles()).filter((i) => {
7530
- var _a;
7531
- return ((_a = i.result) == null ? void 0 : _a.state) === "fail";
7532
- });
7533
- if (failed.length)
7534
- this.ctx.log(`
7535
- ${c.bold(c.inverse(c.red(" FAIL ")))}${c.red(` ${failed.length} tests failed. Watching for file changes...`)}`);
7536
- else
7537
- this.ctx.log(`
7538
- ${c.bold(c.inverse(c.green(" PASS ")))}${c.green(" Waiting for file changes...")}`);
7539
- if (this.isFirstWatchRun) {
7540
- this.isFirstWatchRun = false;
7541
- this.ctx.log(c.gray("press any key to exit..."));
7542
- }
7543
- }
7544
- async onWatcherRerun(files, trigger) {
7545
- await this.stopListRender();
7546
- this.watchFilters = files;
7547
- if (!this.ctx.config.silent) {
7548
- this.ctx.console.clear();
7549
- this.ctx.log(c.blue("Re-running tests...") + c.dim(` [ ${this.relative(trigger)} ]
7550
- `));
7551
- }
7552
- }
7553
- async stopListRender() {
7554
- var _a;
7555
- (_a = this.renderer) == null ? void 0 : _a.stop();
7556
- this.renderer = void 0;
7557
- await new Promise((resolve) => setTimeout(resolve, 10));
7558
- }
7559
- onUserConsoleLog(log) {
7560
- var _a;
7561
- (_a = this.renderer) == null ? void 0 : _a.clear();
7562
- const task = log.taskId ? this.ctx.state.idMap[log.taskId] : void 0;
7563
- this.ctx.log(c.gray(log.type + c.dim(` | ${task ? getFullName(task) : "unknown test"}`)));
7564
- process[log.type].write(`${log.content}
7565
- `);
7566
- }
7567
- onServerRestart() {
7568
- this.ctx.log(c.cyan("Restarted due to config changes..."));
7569
- }
7570
- }
7571
-
7572
- var charToInteger = {};
7573
- var chars = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=';
7574
- for (var i = 0; i < chars.length; i++) {
7575
- charToInteger[chars.charCodeAt(i)] = i;
7576
- }
7577
- function encode(decoded) {
7578
- var sourceFileIndex = 0; // second field
7579
- var sourceCodeLine = 0; // third field
7580
- var sourceCodeColumn = 0; // fourth field
7581
- var nameIndex = 0; // fifth field
7582
- var mappings = '';
7583
- for (var i = 0; i < decoded.length; i++) {
7584
- var line = decoded[i];
7585
- if (i > 0)
7586
- mappings += ';';
7587
- if (line.length === 0)
7588
- continue;
7589
- var generatedCodeColumn = 0; // first field
7590
- var lineMappings = [];
7591
- for (var _i = 0, line_1 = line; _i < line_1.length; _i++) {
7592
- var segment = line_1[_i];
7593
- var segmentMappings = encodeInteger(segment[0] - generatedCodeColumn);
7594
- generatedCodeColumn = segment[0];
7595
- if (segment.length > 1) {
7596
- segmentMappings +=
7597
- encodeInteger(segment[1] - sourceFileIndex) +
7598
- encodeInteger(segment[2] - sourceCodeLine) +
7599
- encodeInteger(segment[3] - sourceCodeColumn);
7600
- sourceFileIndex = segment[1];
7601
- sourceCodeLine = segment[2];
7602
- sourceCodeColumn = segment[3];
7603
- }
7604
- if (segment.length === 5) {
7605
- segmentMappings += encodeInteger(segment[4] - nameIndex);
7606
- nameIndex = segment[4];
7607
- }
7608
- lineMappings.push(segmentMappings);
7609
- }
7610
- mappings += lineMappings.join(',');
7611
- }
7612
- return mappings;
7613
- }
7614
- function encodeInteger(num) {
7615
- var result = '';
7616
- num = num < 0 ? (-num << 1) | 1 : num << 1;
7617
- do {
7618
- var clamped = num & 31;
7619
- num >>>= 5;
7620
- if (num > 0) {
7621
- clamped |= 32;
7622
- }
7623
- result += chars[clamped];
7624
- } while (num > 0);
7625
- return result;
7626
- }
7627
-
7628
- var BitSet = function BitSet(arg) {
7629
- this.bits = arg instanceof BitSet ? arg.bits.slice() : [];
7630
- };
7631
-
7632
- BitSet.prototype.add = function add (n) {
7633
- this.bits[n >> 5] |= 1 << (n & 31);
7634
- };
7635
-
7636
- BitSet.prototype.has = function has (n) {
7637
- return !!(this.bits[n >> 5] & (1 << (n & 31)));
7638
- };
7639
-
7640
- var Chunk = function Chunk(start, end, content) {
7641
- this.start = start;
7642
- this.end = end;
7643
- this.original = content;
7644
-
7645
- this.intro = '';
7646
- this.outro = '';
7647
-
7648
- this.content = content;
7649
- this.storeName = false;
7650
- this.edited = false;
7651
-
7652
- // we make these non-enumerable, for sanity while debugging
7653
- Object.defineProperties(this, {
7654
- previous: { writable: true, value: null },
7655
- next: { writable: true, value: null }
7656
- });
7657
- };
7658
-
7659
- Chunk.prototype.appendLeft = function appendLeft (content) {
7660
- this.outro += content;
7661
- };
7662
-
7663
- Chunk.prototype.appendRight = function appendRight (content) {
7664
- this.intro = this.intro + content;
7665
- };
7666
-
7667
- Chunk.prototype.clone = function clone () {
7668
- var chunk = new Chunk(this.start, this.end, this.original);
7669
-
7670
- chunk.intro = this.intro;
7671
- chunk.outro = this.outro;
7672
- chunk.content = this.content;
7673
- chunk.storeName = this.storeName;
7674
- chunk.edited = this.edited;
7675
-
7676
- return chunk;
7677
- };
7678
-
7679
- Chunk.prototype.contains = function contains (index) {
7680
- return this.start < index && index < this.end;
7681
- };
7682
-
7683
- Chunk.prototype.eachNext = function eachNext (fn) {
7684
- var chunk = this;
7685
- while (chunk) {
7686
- fn(chunk);
7687
- chunk = chunk.next;
7688
- }
7689
- };
7690
-
7691
- Chunk.prototype.eachPrevious = function eachPrevious (fn) {
7692
- var chunk = this;
7693
- while (chunk) {
7694
- fn(chunk);
7695
- chunk = chunk.previous;
7696
- }
7697
- };
7698
-
7699
- Chunk.prototype.edit = function edit (content, storeName, contentOnly) {
7700
- this.content = content;
7701
- if (!contentOnly) {
7702
- this.intro = '';
7703
- this.outro = '';
7704
- }
7705
- this.storeName = storeName;
7706
-
7707
- this.edited = true;
7708
-
7709
- return this;
7710
- };
7711
-
7712
- Chunk.prototype.prependLeft = function prependLeft (content) {
7713
- this.outro = content + this.outro;
7714
- };
7715
-
7716
- Chunk.prototype.prependRight = function prependRight (content) {
7717
- this.intro = content + this.intro;
7718
- };
7719
-
7720
- Chunk.prototype.split = function split (index) {
7721
- var sliceIndex = index - this.start;
7722
-
7723
- var originalBefore = this.original.slice(0, sliceIndex);
7724
- var originalAfter = this.original.slice(sliceIndex);
7725
-
7726
- this.original = originalBefore;
7727
-
7728
- var newChunk = new Chunk(index, this.end, originalAfter);
7729
- newChunk.outro = this.outro;
7730
- this.outro = '';
7731
-
7732
- this.end = index;
7733
-
7734
- if (this.edited) {
7735
- // TODO is this block necessary?...
7736
- newChunk.edit('', false);
7737
- this.content = '';
7738
- } else {
7739
- this.content = originalBefore;
7740
- }
7741
-
7742
- newChunk.next = this.next;
7743
- if (newChunk.next) { newChunk.next.previous = newChunk; }
7744
- newChunk.previous = this;
7745
- this.next = newChunk;
7746
-
7747
- return newChunk;
7748
- };
7749
-
7750
- Chunk.prototype.toString = function toString () {
7751
- return this.intro + this.content + this.outro;
7752
- };
7753
-
7754
- Chunk.prototype.trimEnd = function trimEnd (rx) {
7755
- this.outro = this.outro.replace(rx, '');
7756
- if (this.outro.length) { return true; }
7757
-
7758
- var trimmed = this.content.replace(rx, '');
7759
-
7760
- if (trimmed.length) {
7761
- if (trimmed !== this.content) {
7762
- this.split(this.start + trimmed.length).edit('', undefined, true);
7763
- }
7764
- return true;
7765
-
7766
- } else {
7767
- this.edit('', undefined, true);
7768
-
7769
- this.intro = this.intro.replace(rx, '');
7770
- if (this.intro.length) { return true; }
7771
- }
7772
- };
7773
-
7774
- Chunk.prototype.trimStart = function trimStart (rx) {
7775
- this.intro = this.intro.replace(rx, '');
7776
- if (this.intro.length) { return true; }
7777
-
7778
- var trimmed = this.content.replace(rx, '');
7779
-
7780
- if (trimmed.length) {
7781
- if (trimmed !== this.content) {
7782
- this.split(this.end - trimmed.length);
7783
- this.edit('', undefined, true);
7784
- }
7785
- return true;
7786
-
7787
- } else {
7788
- this.edit('', undefined, true);
7789
-
7790
- this.outro = this.outro.replace(rx, '');
7791
- if (this.outro.length) { return true; }
7792
- }
7793
- };
7794
-
7795
- var btoa = function () {
7796
- throw new Error('Unsupported environment: `window.btoa` or `Buffer` should be supported.');
7797
- };
7798
- if (typeof window !== 'undefined' && typeof window.btoa === 'function') {
7799
- btoa = function (str) { return window.btoa(unescape(encodeURIComponent(str))); };
7800
- } else if (typeof Buffer === 'function') {
7801
- btoa = function (str) { return Buffer.from(str, 'utf-8').toString('base64'); };
7802
- }
7803
-
7804
- var SourceMap = function SourceMap(properties) {
7805
- this.version = 3;
7806
- this.file = properties.file;
7807
- this.sources = properties.sources;
7808
- this.sourcesContent = properties.sourcesContent;
7809
- this.names = properties.names;
7810
- this.mappings = encode(properties.mappings);
7811
- };
7812
-
7813
- SourceMap.prototype.toString = function toString () {
7814
- return JSON.stringify(this);
7815
- };
7816
-
7817
- SourceMap.prototype.toUrl = function toUrl () {
7818
- return 'data:application/json;charset=utf-8;base64,' + btoa(this.toString());
7819
- };
7820
-
7821
- function guessIndent(code) {
7822
- var lines = code.split('\n');
7823
-
7824
- var tabbed = lines.filter(function (line) { return /^\t+/.test(line); });
7825
- var spaced = lines.filter(function (line) { return /^ {2,}/.test(line); });
7826
-
7827
- if (tabbed.length === 0 && spaced.length === 0) {
7828
- return null;
7829
- }
7830
-
7831
- // More lines tabbed than spaced? Assume tabs, and
7832
- // default to tabs in the case of a tie (or nothing
7833
- // to go on)
7834
- if (tabbed.length >= spaced.length) {
7835
- return '\t';
7836
- }
7837
-
7838
- // Otherwise, we need to guess the multiple
7839
- var min = spaced.reduce(function (previous, current) {
7840
- var numSpaces = /^ +/.exec(current)[0].length;
7841
- return Math.min(numSpaces, previous);
7842
- }, Infinity);
7843
-
7844
- return new Array(min + 1).join(' ');
7845
- }
7846
-
7847
- function getRelativePath(from, to) {
7848
- var fromParts = from.split(/[/\\]/);
7849
- var toParts = to.split(/[/\\]/);
7850
-
7851
- fromParts.pop(); // get dirname
7852
-
7853
- while (fromParts[0] === toParts[0]) {
7854
- fromParts.shift();
7855
- toParts.shift();
7856
- }
7857
-
7858
- if (fromParts.length) {
7859
- var i = fromParts.length;
7860
- while (i--) { fromParts[i] = '..'; }
7861
- }
7862
-
7863
- return fromParts.concat(toParts).join('/');
6992
+ if (task.type === "test" && ((_a = task.result) == null ? void 0 : _a.state) && ((_b = task.result) == null ? void 0 : _b.state) !== "run") {
6993
+ this.ctx.log(` ${getStateSymbol(task)} ${getFullName(task)}`);
6994
+ if (task.result.state === "fail")
6995
+ this.ctx.log(c.red(` ${F_RIGHT} ${(_c = task.result.error) == null ? void 0 : _c.message}`));
6996
+ }
6997
+ }
6998
+ async onWatcherStart() {
6999
+ const failed = hasFailed(this.ctx.state.getFiles());
7000
+ if (failed)
7001
+ this.ctx.log(`
7002
+ ${c.bold(c.inverse(c.red(" FAIL ")))}${c.red(" Tests failed. Watching for file changes...")}`);
7003
+ else
7004
+ this.ctx.log(`
7005
+ ${c.bold(c.inverse(c.green(" PASS ")))}${c.green(" Waiting for file changes...")}`);
7006
+ if (this.isFirstWatchRun) {
7007
+ this.isFirstWatchRun = false;
7008
+ this.ctx.log(c.gray("press any key to exit..."));
7009
+ }
7010
+ }
7011
+ async onWatcherRerun(files, trigger) {
7012
+ this.watchFilters = files;
7013
+ if (!this.ctx.config.silent) {
7014
+ this.ctx.console.clear();
7015
+ this.ctx.log(c.blue("Re-running tests...") + c.dim(` [ ${this.relative(trigger)} ]
7016
+ `));
7017
+ }
7018
+ }
7019
+ onUserConsoleLog(log) {
7020
+ const task = log.taskId ? this.ctx.state.idMap[log.taskId] : void 0;
7021
+ this.ctx.log(c.gray(log.type + c.dim(` | ${task ? getFullName(task) : "unknown test"}`)));
7022
+ process[log.type].write(`${log.content}
7023
+ `);
7024
+ }
7025
+ onServerRestart() {
7026
+ this.ctx.log(c.cyan("Restarted due to config changes..."));
7027
+ }
7028
+ async reportSummary(files) {
7029
+ const suites = getSuites(files);
7030
+ const tests = getTests(files);
7031
+ const failedSuites = suites.filter((i) => {
7032
+ var _a;
7033
+ return (_a = i.result) == null ? void 0 : _a.error;
7034
+ });
7035
+ const failedTests = tests.filter((i) => {
7036
+ var _a;
7037
+ return ((_a = i.result) == null ? void 0 : _a.state) === "fail";
7038
+ });
7039
+ const failedTotal = failedSuites.length + failedTests.length;
7040
+ let current = 1;
7041
+ const errorDivider = () => this.ctx.error(`${c.red(c.dim(divider(`[${current++}/${failedTotal}]`, void 0, 1)))}
7042
+ `);
7043
+ if (failedSuites.length) {
7044
+ this.ctx.error(c.red(divider(c.bold(c.inverse(` Failed Suites ${failedSuites.length} `)))));
7045
+ this.ctx.error();
7046
+ await this.printTaskErrors(failedSuites, errorDivider);
7047
+ }
7048
+ if (failedTests.length) {
7049
+ this.ctx.error(c.red(divider(c.bold(c.inverse(` Failed Tests ${failedTests.length} `)))));
7050
+ this.ctx.error();
7051
+ await this.printTaskErrors(failedTests, errorDivider);
7052
+ }
7053
+ const executionTime = this.end - this.start;
7054
+ const threadTime = tests.reduce((acc, test) => {
7055
+ var _a;
7056
+ return acc + (((_a = test.result) == null ? void 0 : _a.end) ? test.result.end - test.result.start : 0);
7057
+ }, 0);
7058
+ const padTitle = (str) => c.dim(`${str.padStart(10)} `);
7059
+ const time = (time2) => {
7060
+ if (time2 > 1e3)
7061
+ return `${(time2 / 1e3).toFixed(2)}s`;
7062
+ return `${Math.round(time2)}ms`;
7063
+ };
7064
+ const snapshotOutput = renderSnapshotSummary(this.ctx.config.root, this.ctx.snapshot.summary);
7065
+ if (snapshotOutput.length) {
7066
+ this.ctx.log(snapshotOutput.map((t, i) => i === 0 ? `${padTitle("Snapshots")} ${t}` : `${padTitle("")} ${t}`).join("\n"));
7067
+ if (snapshotOutput.length > 1)
7068
+ this.ctx.log();
7069
+ }
7070
+ this.ctx.log(padTitle("Test Files"), getStateString(files));
7071
+ this.ctx.log(padTitle("Tests"), getStateString(tests));
7072
+ if (this.watchFilters)
7073
+ this.ctx.log(padTitle("Time"), time(threadTime));
7074
+ else
7075
+ this.ctx.log(padTitle("Time"), time(executionTime) + c.gray(` (in thread ${time(threadTime)}, ${(executionTime / threadTime * 100).toFixed(2)}%)`));
7076
+ this.ctx.log();
7077
+ }
7078
+ async printTaskErrors(tasks, errorDivider) {
7079
+ var _a;
7080
+ const errorsQueue = [];
7081
+ for (const task of tasks) {
7082
+ const error = (_a = task.result) == null ? void 0 : _a.error;
7083
+ const errorItem = (error == null ? void 0 : error.stackStr) && errorsQueue.find((i) => {
7084
+ var _a2;
7085
+ return ((_a2 = i[0]) == null ? void 0 : _a2.stackStr) === error.stackStr;
7086
+ });
7087
+ if (errorItem)
7088
+ errorItem[1].push(task);
7089
+ else
7090
+ errorsQueue.push([error, [task]]);
7091
+ }
7092
+ for (const [error, tasks2] of errorsQueue) {
7093
+ for (const task of tasks2) {
7094
+ const filepath = (task == null ? void 0 : task.filepath) || "";
7095
+ let name = getFullName(task);
7096
+ if (filepath)
7097
+ name = `${name} ${c.dim(`[ ${this.relative(filepath)} ]`)}`;
7098
+ this.ctx.error(`${c.red(c.bold(c.inverse(" FAIL ")))} ${name}`);
7099
+ }
7100
+ await printError(error, this.ctx);
7101
+ errorDivider();
7102
+ }
7103
+ }
7864
7104
  }
7865
7105
 
7866
- var toString = Object.prototype.toString;
7867
-
7868
- function isObject(thing) {
7869
- return toString.call(thing) === '[object Object]';
7870
- }
7106
+ const ESC = '\u001B[';
7107
+ const OSC = '\u001B]';
7108
+ const BEL = '\u0007';
7109
+ const SEP = ';';
7110
+ const isTerminalApp = process.env.TERM_PROGRAM === 'Apple_Terminal';
7871
7111
 
7872
- function getLocator(source) {
7873
- var originalLines = source.split('\n');
7874
- var lineOffsets = [];
7112
+ const ansiEscapes = {};
7875
7113
 
7876
- for (var i = 0, pos = 0; i < originalLines.length; i++) {
7877
- lineOffsets.push(pos);
7878
- pos += originalLines[i].length + 1;
7114
+ ansiEscapes.cursorTo = (x, y) => {
7115
+ if (typeof x !== 'number') {
7116
+ throw new TypeError('The `x` argument is required');
7879
7117
  }
7880
7118
 
7881
- return function locate(index) {
7882
- var i = 0;
7883
- var j = lineOffsets.length;
7884
- while (i < j) {
7885
- var m = (i + j) >> 1;
7886
- if (index < lineOffsets[m]) {
7887
- j = m;
7888
- } else {
7889
- i = m + 1;
7890
- }
7891
- }
7892
- var line = i - 1;
7893
- var column = index - lineOffsets[line];
7894
- return { line: line, column: column };
7895
- };
7896
- }
7897
-
7898
- var Mappings = function Mappings(hires) {
7899
- this.hires = hires;
7900
- this.generatedCodeLine = 0;
7901
- this.generatedCodeColumn = 0;
7902
- this.raw = [];
7903
- this.rawSegments = this.raw[this.generatedCodeLine] = [];
7904
- this.pending = null;
7905
- };
7906
-
7907
- Mappings.prototype.addEdit = function addEdit (sourceIndex, content, loc, nameIndex) {
7908
- if (content.length) {
7909
- var segment = [this.generatedCodeColumn, sourceIndex, loc.line, loc.column];
7910
- if (nameIndex >= 0) {
7911
- segment.push(nameIndex);
7912
- }
7913
- this.rawSegments.push(segment);
7914
- } else if (this.pending) {
7915
- this.rawSegments.push(this.pending);
7119
+ if (typeof y !== 'number') {
7120
+ return ESC + (x + 1) + 'G';
7916
7121
  }
7917
7122
 
7918
- this.advance(content);
7919
- this.pending = null;
7123
+ return ESC + (y + 1) + ';' + (x + 1) + 'H';
7920
7124
  };
7921
7125
 
7922
- Mappings.prototype.addUneditedChunk = function addUneditedChunk (sourceIndex, chunk, original, loc, sourcemapLocations) {
7923
- var originalCharIndex = chunk.start;
7924
- var first = true;
7925
-
7926
- while (originalCharIndex < chunk.end) {
7927
- if (this.hires || first || sourcemapLocations.has(originalCharIndex)) {
7928
- this.rawSegments.push([this.generatedCodeColumn, sourceIndex, loc.line, loc.column]);
7929
- }
7930
-
7931
- if (original[originalCharIndex] === '\n') {
7932
- loc.line += 1;
7933
- loc.column = 0;
7934
- this.generatedCodeLine += 1;
7935
- this.raw[this.generatedCodeLine] = this.rawSegments = [];
7936
- this.generatedCodeColumn = 0;
7937
- first = true;
7938
- } else {
7939
- loc.column += 1;
7940
- this.generatedCodeColumn += 1;
7941
- first = false;
7942
- }
7943
-
7944
- originalCharIndex += 1;
7126
+ ansiEscapes.cursorMove = (x, y) => {
7127
+ if (typeof x !== 'number') {
7128
+ throw new TypeError('The `x` argument is required');
7945
7129
  }
7946
7130
 
7947
- this.pending = null;
7948
- };
7949
-
7950
- Mappings.prototype.advance = function advance (str) {
7951
- if (!str) { return; }
7952
-
7953
- var lines = str.split('\n');
7131
+ let returnValue = '';
7954
7132
 
7955
- if (lines.length > 1) {
7956
- for (var i = 0; i < lines.length - 1; i++) {
7957
- this.generatedCodeLine++;
7958
- this.raw[this.generatedCodeLine] = this.rawSegments = [];
7959
- }
7960
- this.generatedCodeColumn = 0;
7133
+ if (x < 0) {
7134
+ returnValue += ESC + (-x) + 'D';
7135
+ } else if (x > 0) {
7136
+ returnValue += ESC + x + 'C';
7961
7137
  }
7962
7138
 
7963
- this.generatedCodeColumn += lines[lines.length - 1].length;
7964
- };
7965
-
7966
- var n = '\n';
7967
-
7968
- var warned = {
7969
- insertLeft: false,
7970
- insertRight: false,
7971
- storeName: false
7972
- };
7973
-
7974
- var MagicString = function MagicString(string, options) {
7975
- if ( options === void 0 ) options = {};
7976
-
7977
- var chunk = new Chunk(0, string.length, string);
7978
-
7979
- Object.defineProperties(this, {
7980
- original: { writable: true, value: string },
7981
- outro: { writable: true, value: '' },
7982
- intro: { writable: true, value: '' },
7983
- firstChunk: { writable: true, value: chunk },
7984
- lastChunk: { writable: true, value: chunk },
7985
- lastSearchedChunk: { writable: true, value: chunk },
7986
- byStart: { writable: true, value: {} },
7987
- byEnd: { writable: true, value: {} },
7988
- filename: { writable: true, value: options.filename },
7989
- indentExclusionRanges: { writable: true, value: options.indentExclusionRanges },
7990
- sourcemapLocations: { writable: true, value: new BitSet() },
7991
- storedNames: { writable: true, value: {} },
7992
- indentStr: { writable: true, value: guessIndent(string) }
7993
- });
7994
-
7995
- this.byStart[0] = chunk;
7996
- this.byEnd[string.length] = chunk;
7997
- };
7998
-
7999
- MagicString.prototype.addSourcemapLocation = function addSourcemapLocation (char) {
8000
- this.sourcemapLocations.add(char);
8001
- };
8002
-
8003
- MagicString.prototype.append = function append (content) {
8004
- if (typeof content !== 'string') { throw new TypeError('outro content must be a string'); }
8005
-
8006
- this.outro += content;
8007
- return this;
8008
- };
8009
-
8010
- MagicString.prototype.appendLeft = function appendLeft (index, content) {
8011
- if (typeof content !== 'string') { throw new TypeError('inserted content must be a string'); }
8012
-
8013
- this._split(index);
8014
-
8015
- var chunk = this.byEnd[index];
8016
-
8017
- if (chunk) {
8018
- chunk.appendLeft(content);
8019
- } else {
8020
- this.intro += content;
7139
+ if (y < 0) {
7140
+ returnValue += ESC + (-y) + 'A';
7141
+ } else if (y > 0) {
7142
+ returnValue += ESC + y + 'B';
8021
7143
  }
8022
- return this;
8023
- };
8024
7144
 
8025
- MagicString.prototype.appendRight = function appendRight (index, content) {
8026
- if (typeof content !== 'string') { throw new TypeError('inserted content must be a string'); }
8027
-
8028
- this._split(index);
8029
-
8030
- var chunk = this.byStart[index];
8031
-
8032
- if (chunk) {
8033
- chunk.appendRight(content);
8034
- } else {
8035
- this.outro += content;
8036
- }
8037
- return this;
7145
+ return returnValue;
8038
7146
  };
8039
7147
 
8040
- MagicString.prototype.clone = function clone () {
8041
- var cloned = new MagicString(this.original, { filename: this.filename });
8042
-
8043
- var originalChunk = this.firstChunk;
8044
- var clonedChunk = (cloned.firstChunk = cloned.lastSearchedChunk = originalChunk.clone());
8045
-
8046
- while (originalChunk) {
8047
- cloned.byStart[clonedChunk.start] = clonedChunk;
8048
- cloned.byEnd[clonedChunk.end] = clonedChunk;
8049
-
8050
- var nextOriginalChunk = originalChunk.next;
8051
- var nextClonedChunk = nextOriginalChunk && nextOriginalChunk.clone();
8052
-
8053
- if (nextClonedChunk) {
8054
- clonedChunk.next = nextClonedChunk;
8055
- nextClonedChunk.previous = clonedChunk;
8056
-
8057
- clonedChunk = nextClonedChunk;
8058
- }
7148
+ ansiEscapes.cursorUp = (count = 1) => ESC + count + 'A';
7149
+ ansiEscapes.cursorDown = (count = 1) => ESC + count + 'B';
7150
+ ansiEscapes.cursorForward = (count = 1) => ESC + count + 'C';
7151
+ ansiEscapes.cursorBackward = (count = 1) => ESC + count + 'D';
8059
7152
 
8060
- originalChunk = nextOriginalChunk;
8061
- }
7153
+ ansiEscapes.cursorLeft = ESC + 'G';
7154
+ ansiEscapes.cursorSavePosition = isTerminalApp ? '\u001B7' : ESC + 's';
7155
+ ansiEscapes.cursorRestorePosition = isTerminalApp ? '\u001B8' : ESC + 'u';
7156
+ ansiEscapes.cursorGetPosition = ESC + '6n';
7157
+ ansiEscapes.cursorNextLine = ESC + 'E';
7158
+ ansiEscapes.cursorPrevLine = ESC + 'F';
7159
+ ansiEscapes.cursorHide = ESC + '?25l';
7160
+ ansiEscapes.cursorShow = ESC + '?25h';
8062
7161
 
8063
- cloned.lastChunk = clonedChunk;
7162
+ ansiEscapes.eraseLines = count => {
7163
+ let clear = '';
8064
7164
 
8065
- if (this.indentExclusionRanges) {
8066
- cloned.indentExclusionRanges = this.indentExclusionRanges.slice();
7165
+ for (let i = 0; i < count; i++) {
7166
+ clear += ansiEscapes.eraseLine + (i < count - 1 ? ansiEscapes.cursorUp() : '');
8067
7167
  }
8068
7168
 
8069
- cloned.sourcemapLocations = new BitSet(this.sourcemapLocations);
8070
-
8071
- cloned.intro = this.intro;
8072
- cloned.outro = this.outro;
8073
-
8074
- return cloned;
8075
- };
8076
-
8077
- MagicString.prototype.generateDecodedMap = function generateDecodedMap (options) {
8078
- var this$1$1 = this;
8079
-
8080
- options = options || {};
8081
-
8082
- var sourceIndex = 0;
8083
- var names = Object.keys(this.storedNames);
8084
- var mappings = new Mappings(options.hires);
8085
-
8086
- var locate = getLocator(this.original);
8087
-
8088
- if (this.intro) {
8089
- mappings.advance(this.intro);
7169
+ if (count) {
7170
+ clear += ansiEscapes.cursorLeft;
8090
7171
  }
8091
7172
 
8092
- this.firstChunk.eachNext(function (chunk) {
8093
- var loc = locate(chunk.start);
8094
-
8095
- if (chunk.intro.length) { mappings.advance(chunk.intro); }
8096
-
8097
- if (chunk.edited) {
8098
- mappings.addEdit(
8099
- sourceIndex,
8100
- chunk.content,
8101
- loc,
8102
- chunk.storeName ? names.indexOf(chunk.original) : -1
8103
- );
8104
- } else {
8105
- mappings.addUneditedChunk(sourceIndex, chunk, this$1$1.original, loc, this$1$1.sourcemapLocations);
8106
- }
8107
-
8108
- if (chunk.outro.length) { mappings.advance(chunk.outro); }
8109
- });
8110
-
8111
- return {
8112
- file: options.file ? options.file.split(/[/\\]/).pop() : null,
8113
- sources: [options.source ? getRelativePath(options.file || '', options.source) : null],
8114
- sourcesContent: options.includeContent ? [this.original] : [null],
8115
- names: names,
8116
- mappings: mappings.raw
8117
- };
8118
- };
8119
-
8120
- MagicString.prototype.generateMap = function generateMap (options) {
8121
- return new SourceMap(this.generateDecodedMap(options));
8122
- };
8123
-
8124
- MagicString.prototype.getIndentString = function getIndentString () {
8125
- return this.indentStr === null ? '\t' : this.indentStr;
7173
+ return clear;
8126
7174
  };
8127
7175
 
8128
- MagicString.prototype.indent = function indent (indentStr, options) {
8129
- var pattern = /^[^\r\n]/gm;
8130
-
8131
- if (isObject(indentStr)) {
8132
- options = indentStr;
8133
- indentStr = undefined;
8134
- }
8135
-
8136
- indentStr = indentStr !== undefined ? indentStr : this.indentStr || '\t';
8137
-
8138
- if (indentStr === '') { return this; } // noop
8139
-
8140
- options = options || {};
8141
-
8142
- // Process exclusion ranges
8143
- var isExcluded = {};
8144
-
8145
- if (options.exclude) {
8146
- var exclusions =
8147
- typeof options.exclude[0] === 'number' ? [options.exclude] : options.exclude;
8148
- exclusions.forEach(function (exclusion) {
8149
- for (var i = exclusion[0]; i < exclusion[1]; i += 1) {
8150
- isExcluded[i] = true;
8151
- }
8152
- });
8153
- }
8154
-
8155
- var shouldIndentNextCharacter = options.indentStart !== false;
8156
- var replacer = function (match) {
8157
- if (shouldIndentNextCharacter) { return ("" + indentStr + match); }
8158
- shouldIndentNextCharacter = true;
8159
- return match;
8160
- };
8161
-
8162
- this.intro = this.intro.replace(pattern, replacer);
8163
-
8164
- var charIndex = 0;
8165
- var chunk = this.firstChunk;
8166
-
8167
- while (chunk) {
8168
- var end = chunk.end;
8169
-
8170
- if (chunk.edited) {
8171
- if (!isExcluded[charIndex]) {
8172
- chunk.content = chunk.content.replace(pattern, replacer);
8173
-
8174
- if (chunk.content.length) {
8175
- shouldIndentNextCharacter = chunk.content[chunk.content.length - 1] === '\n';
8176
- }
8177
- }
8178
- } else {
8179
- charIndex = chunk.start;
8180
-
8181
- while (charIndex < end) {
8182
- if (!isExcluded[charIndex]) {
8183
- var char = this.original[charIndex];
8184
-
8185
- if (char === '\n') {
8186
- shouldIndentNextCharacter = true;
8187
- } else if (char !== '\r' && shouldIndentNextCharacter) {
8188
- shouldIndentNextCharacter = false;
8189
-
8190
- if (charIndex === chunk.start) {
8191
- chunk.prependRight(indentStr);
8192
- } else {
8193
- this._splitChunk(chunk, charIndex);
8194
- chunk = chunk.next;
8195
- chunk.prependRight(indentStr);
8196
- }
8197
- }
8198
- }
7176
+ ansiEscapes.eraseEndLine = ESC + 'K';
7177
+ ansiEscapes.eraseStartLine = ESC + '1K';
7178
+ ansiEscapes.eraseLine = ESC + '2K';
7179
+ ansiEscapes.eraseDown = ESC + 'J';
7180
+ ansiEscapes.eraseUp = ESC + '1J';
7181
+ ansiEscapes.eraseScreen = ESC + '2J';
7182
+ ansiEscapes.scrollUp = ESC + 'S';
7183
+ ansiEscapes.scrollDown = ESC + 'T';
8199
7184
 
8200
- charIndex += 1;
8201
- }
8202
- }
7185
+ ansiEscapes.clearScreen = '\u001Bc';
8203
7186
 
8204
- charIndex = chunk.end;
8205
- chunk = chunk.next;
8206
- }
7187
+ ansiEscapes.clearTerminal = process.platform === 'win32' ?
7188
+ `${ansiEscapes.eraseScreen}${ESC}0f` :
7189
+ // 1. Erases the screen (Only done in case `2` is not supported)
7190
+ // 2. Erases the whole screen including scrollback buffer
7191
+ // 3. Moves cursor to the top-left position
7192
+ // More info: https://www.real-world-systems.com/docs/ANSIcode.html
7193
+ `${ansiEscapes.eraseScreen}${ESC}3J${ESC}H`;
8207
7194
 
8208
- this.outro = this.outro.replace(pattern, replacer);
7195
+ ansiEscapes.beep = BEL;
8209
7196
 
8210
- return this;
7197
+ ansiEscapes.link = (text, url) => {
7198
+ return [
7199
+ OSC,
7200
+ '8',
7201
+ SEP,
7202
+ SEP,
7203
+ url,
7204
+ BEL,
7205
+ text,
7206
+ OSC,
7207
+ '8',
7208
+ SEP,
7209
+ SEP,
7210
+ BEL
7211
+ ].join('');
8211
7212
  };
8212
7213
 
8213
- MagicString.prototype.insert = function insert () {
8214
- throw new Error('magicString.insert(...) is deprecated. Use prependRight(...) or appendLeft(...)');
8215
- };
7214
+ ansiEscapes.image = (buffer, options = {}) => {
7215
+ let returnValue = `${OSC}1337;File=inline=1`;
8216
7216
 
8217
- MagicString.prototype.insertLeft = function insertLeft (index, content) {
8218
- if (!warned.insertLeft) {
8219
- console.warn('magicString.insertLeft(...) is deprecated. Use magicString.appendLeft(...) instead'); // eslint-disable-line no-console
8220
- warned.insertLeft = true;
7217
+ if (options.width) {
7218
+ returnValue += `;width=${options.width}`;
8221
7219
  }
8222
7220
 
8223
- return this.appendLeft(index, content);
8224
- };
7221
+ if (options.height) {
7222
+ returnValue += `;height=${options.height}`;
7223
+ }
8225
7224
 
8226
- MagicString.prototype.insertRight = function insertRight (index, content) {
8227
- if (!warned.insertRight) {
8228
- console.warn('magicString.insertRight(...) is deprecated. Use magicString.prependRight(...) instead'); // eslint-disable-line no-console
8229
- warned.insertRight = true;
7225
+ if (options.preserveAspectRatio === false) {
7226
+ returnValue += ';preserveAspectRatio=0';
8230
7227
  }
8231
7228
 
8232
- return this.prependRight(index, content);
7229
+ return returnValue + ':' + buffer.toString('base64') + BEL;
8233
7230
  };
8234
7231
 
8235
- MagicString.prototype.move = function move (start, end, index) {
8236
- if (index >= start && index <= end) { throw new Error('Cannot move a selection inside itself'); }
8237
-
8238
- this._split(start);
8239
- this._split(end);
8240
- this._split(index);
7232
+ ansiEscapes.iTerm = {
7233
+ setCwd: (cwd = process.cwd()) => `${OSC}50;CurrentDir=${cwd}${BEL}`,
8241
7234
 
8242
- var first = this.byStart[start];
8243
- var last = this.byEnd[end];
7235
+ annotation: (message, options = {}) => {
7236
+ let returnValue = `${OSC}1337;`;
8244
7237
 
8245
- var oldLeft = first.previous;
8246
- var oldRight = last.next;
7238
+ const hasX = typeof options.x !== 'undefined';
7239
+ const hasY = typeof options.y !== 'undefined';
7240
+ if ((hasX || hasY) && !(hasX && hasY && typeof options.length !== 'undefined')) {
7241
+ throw new Error('`x`, `y` and `length` must be defined when `x` or `y` is defined');
7242
+ }
8247
7243
 
8248
- var newRight = this.byStart[index];
8249
- if (!newRight && last === this.lastChunk) { return this; }
8250
- var newLeft = newRight ? newRight.previous : this.lastChunk;
7244
+ message = message.replace(/\|/g, '');
8251
7245
 
8252
- if (oldLeft) { oldLeft.next = oldRight; }
8253
- if (oldRight) { oldRight.previous = oldLeft; }
7246
+ returnValue += options.isHidden ? 'AddHiddenAnnotation=' : 'AddAnnotation=';
8254
7247
 
8255
- if (newLeft) { newLeft.next = first; }
8256
- if (newRight) { newRight.previous = last; }
7248
+ if (options.length > 0) {
7249
+ returnValue +=
7250
+ (hasX ?
7251
+ [message, options.length, options.x, options.y] :
7252
+ [options.length, message]).join('|');
7253
+ } else {
7254
+ returnValue += message;
7255
+ }
8257
7256
 
8258
- if (!first.previous) { this.firstChunk = last.next; }
8259
- if (!last.next) {
8260
- this.lastChunk = first.previous;
8261
- this.lastChunk.next = null;
7257
+ return returnValue + BEL;
8262
7258
  }
8263
-
8264
- first.previous = newLeft;
8265
- last.next = newRight || null;
8266
-
8267
- if (!newLeft) { this.firstChunk = first; }
8268
- if (!newRight) { this.lastChunk = last; }
8269
- return this;
8270
7259
  };
8271
7260
 
8272
- MagicString.prototype.overwrite = function overwrite (start, end, content, options) {
8273
- if (typeof content !== 'string') { throw new TypeError('replacement content must be a string'); }
8274
-
8275
- while (start < 0) { start += this.original.length; }
8276
- while (end < 0) { end += this.original.length; }
8277
-
8278
- if (end > this.original.length) { throw new Error('end is out of bounds'); }
8279
- if (start === end)
8280
- { throw new Error('Cannot overwrite a zero-length range – use appendLeft or prependRight instead'); }
8281
-
8282
- this._split(start);
8283
- this._split(end);
7261
+ const restoreCursor = onetime(() => {
7262
+ signalExit(() => {
7263
+ process$1.stderr.write('\u001B[?25h');
7264
+ }, {alwaysLast: true});
7265
+ });
8284
7266
 
8285
- if (options === true) {
8286
- if (!warned.storeName) {
8287
- console.warn('The final argument to magicString.overwrite(...) should be an options object. See https://github.com/rich-harris/magic-string'); // eslint-disable-line no-console
8288
- warned.storeName = true;
8289
- }
7267
+ let isHidden = false;
8290
7268
 
8291
- options = { storeName: true };
8292
- }
8293
- var storeName = options !== undefined ? options.storeName : false;
8294
- var contentOnly = options !== undefined ? options.contentOnly : false;
7269
+ const cliCursor = {};
8295
7270
 
8296
- if (storeName) {
8297
- var original = this.original.slice(start, end);
8298
- this.storedNames[original] = true;
7271
+ cliCursor.show = (writableStream = process$1.stderr) => {
7272
+ if (!writableStream.isTTY) {
7273
+ return;
8299
7274
  }
8300
7275
 
8301
- var first = this.byStart[start];
8302
- var last = this.byEnd[end];
7276
+ isHidden = false;
7277
+ writableStream.write('\u001B[?25h');
7278
+ };
8303
7279
 
8304
- if (first) {
8305
- if (end > first.end && first.next !== this.byStart[first.end]) {
8306
- throw new Error('Cannot overwrite across a split point');
8307
- }
7280
+ cliCursor.hide = (writableStream = process$1.stderr) => {
7281
+ if (!writableStream.isTTY) {
7282
+ return;
7283
+ }
8308
7284
 
8309
- first.edit(content, storeName, contentOnly);
7285
+ restoreCursor();
7286
+ isHidden = true;
7287
+ writableStream.write('\u001B[?25l');
7288
+ };
8310
7289
 
8311
- if (first !== last) {
8312
- var chunk = first.next;
8313
- while (chunk !== last) {
8314
- chunk.edit('', false);
8315
- chunk = chunk.next;
8316
- }
7290
+ cliCursor.toggle = (force, writableStream) => {
7291
+ if (force !== undefined) {
7292
+ isHidden = force;
7293
+ }
8317
7294
 
8318
- chunk.edit('', false);
8319
- }
7295
+ if (isHidden) {
7296
+ cliCursor.show(writableStream);
8320
7297
  } else {
8321
- // must be inserting at the end
8322
- var newChunk = new Chunk(start, end, '').edit(content, storeName);
8323
-
8324
- // TODO last chunk in the array may not be the last chunk, if it's moved...
8325
- last.next = newChunk;
8326
- newChunk.previous = last;
7298
+ cliCursor.hide(writableStream);
8327
7299
  }
8328
- return this;
8329
7300
  };
8330
7301
 
8331
- MagicString.prototype.prepend = function prepend (content) {
8332
- if (typeof content !== 'string') { throw new TypeError('outro content must be a string'); }
8333
-
8334
- this.intro = content + this.intro;
8335
- return this;
8336
- };
8337
-
8338
- MagicString.prototype.prependLeft = function prependLeft (index, content) {
8339
- if (typeof content !== 'string') { throw new TypeError('inserted content must be a string'); }
8340
-
8341
- this._split(index);
7302
+ const ESCAPES = new Set([
7303
+ '\u001B',
7304
+ '\u009B',
7305
+ ]);
8342
7306
 
8343
- var chunk = this.byEnd[index];
7307
+ const END_CODE = 39;
7308
+ const ANSI_ESCAPE_BELL = '\u0007';
7309
+ const ANSI_CSI = '[';
7310
+ const ANSI_OSC = ']';
7311
+ const ANSI_SGR_TERMINATOR = 'm';
7312
+ const ANSI_ESCAPE_LINK = `${ANSI_OSC}8;;`;
8344
7313
 
8345
- if (chunk) {
8346
- chunk.prependLeft(content);
8347
- } else {
8348
- this.intro = content + this.intro;
8349
- }
8350
- return this;
8351
- };
7314
+ const wrapAnsiCode = code => `${ESCAPES.values().next().value}${ANSI_CSI}${code}${ANSI_SGR_TERMINATOR}`;
7315
+ const wrapAnsiHyperlink = uri => `${ESCAPES.values().next().value}${ANSI_ESCAPE_LINK}${uri}${ANSI_ESCAPE_BELL}`;
8352
7316
 
8353
- MagicString.prototype.prependRight = function prependRight (index, content) {
8354
- if (typeof content !== 'string') { throw new TypeError('inserted content must be a string'); }
7317
+ // Calculate the length of words split on ' ', ignoring
7318
+ // the extra characters added by ansi escape codes
7319
+ const wordLengths = string => string.split(' ').map(character => stringWidth(character));
8355
7320
 
8356
- this._split(index);
7321
+ // Wrap a long word across multiple rows
7322
+ // Ansi escape codes do not count towards length
7323
+ const wrapWord = (rows, word, columns) => {
7324
+ const characters = [...word];
8357
7325
 
8358
- var chunk = this.byStart[index];
7326
+ let isInsideEscape = false;
7327
+ let isInsideLinkEscape = false;
7328
+ let visible = stringWidth(stripAnsi(rows[rows.length - 1]));
8359
7329
 
8360
- if (chunk) {
8361
- chunk.prependRight(content);
8362
- } else {
8363
- this.outro = content + this.outro;
8364
- }
8365
- return this;
8366
- };
7330
+ for (const [index, character] of characters.entries()) {
7331
+ const characterLength = stringWidth(character);
8367
7332
 
8368
- MagicString.prototype.remove = function remove (start, end) {
8369
- while (start < 0) { start += this.original.length; }
8370
- while (end < 0) { end += this.original.length; }
7333
+ if (visible + characterLength <= columns) {
7334
+ rows[rows.length - 1] += character;
7335
+ } else {
7336
+ rows.push(character);
7337
+ visible = 0;
7338
+ }
8371
7339
 
8372
- if (start === end) { return this; }
7340
+ if (ESCAPES.has(character)) {
7341
+ isInsideEscape = true;
7342
+ isInsideLinkEscape = characters.slice(index + 1).join('').startsWith(ANSI_ESCAPE_LINK);
7343
+ }
8373
7344
 
8374
- if (start < 0 || end > this.original.length) { throw new Error('Character is out of bounds'); }
8375
- if (start > end) { throw new Error('end must be greater than start'); }
7345
+ if (isInsideEscape) {
7346
+ if (isInsideLinkEscape) {
7347
+ if (character === ANSI_ESCAPE_BELL) {
7348
+ isInsideEscape = false;
7349
+ isInsideLinkEscape = false;
7350
+ }
7351
+ } else if (character === ANSI_SGR_TERMINATOR) {
7352
+ isInsideEscape = false;
7353
+ }
8376
7354
 
8377
- this._split(start);
8378
- this._split(end);
7355
+ continue;
7356
+ }
8379
7357
 
8380
- var chunk = this.byStart[start];
7358
+ visible += characterLength;
8381
7359
 
8382
- while (chunk) {
8383
- chunk.intro = '';
8384
- chunk.outro = '';
8385
- chunk.edit('');
7360
+ if (visible === columns && index < characters.length - 1) {
7361
+ rows.push('');
7362
+ visible = 0;
7363
+ }
7364
+ }
8386
7365
 
8387
- chunk = end > chunk.end ? this.byStart[chunk.end] : null;
7366
+ // It's possible that the last row we copy over is only
7367
+ // ansi escape characters, handle this edge-case
7368
+ if (!visible && rows[rows.length - 1].length > 0 && rows.length > 1) {
7369
+ rows[rows.length - 2] += rows.pop();
8388
7370
  }
8389
- return this;
8390
7371
  };
8391
7372
 
8392
- MagicString.prototype.lastChar = function lastChar () {
8393
- if (this.outro.length)
8394
- { return this.outro[this.outro.length - 1]; }
8395
- var chunk = this.lastChunk;
8396
- do {
8397
- if (chunk.outro.length)
8398
- { return chunk.outro[chunk.outro.length - 1]; }
8399
- if (chunk.content.length)
8400
- { return chunk.content[chunk.content.length - 1]; }
8401
- if (chunk.intro.length)
8402
- { return chunk.intro[chunk.intro.length - 1]; }
8403
- } while (chunk = chunk.previous);
8404
- if (this.intro.length)
8405
- { return this.intro[this.intro.length - 1]; }
8406
- return '';
8407
- };
7373
+ // Trims spaces from a string ignoring invisible sequences
7374
+ const stringVisibleTrimSpacesRight = string => {
7375
+ const words = string.split(' ');
7376
+ let last = words.length;
8408
7377
 
8409
- MagicString.prototype.lastLine = function lastLine () {
8410
- var lineIndex = this.outro.lastIndexOf(n);
8411
- if (lineIndex !== -1)
8412
- { return this.outro.substr(lineIndex + 1); }
8413
- var lineStr = this.outro;
8414
- var chunk = this.lastChunk;
8415
- do {
8416
- if (chunk.outro.length > 0) {
8417
- lineIndex = chunk.outro.lastIndexOf(n);
8418
- if (lineIndex !== -1)
8419
- { return chunk.outro.substr(lineIndex + 1) + lineStr; }
8420
- lineStr = chunk.outro + lineStr;
7378
+ while (last > 0) {
7379
+ if (stringWidth(words[last - 1]) > 0) {
7380
+ break;
8421
7381
  }
8422
7382
 
8423
- if (chunk.content.length > 0) {
8424
- lineIndex = chunk.content.lastIndexOf(n);
8425
- if (lineIndex !== -1)
8426
- { return chunk.content.substr(lineIndex + 1) + lineStr; }
8427
- lineStr = chunk.content + lineStr;
8428
- }
7383
+ last--;
7384
+ }
8429
7385
 
8430
- if (chunk.intro.length > 0) {
8431
- lineIndex = chunk.intro.lastIndexOf(n);
8432
- if (lineIndex !== -1)
8433
- { return chunk.intro.substr(lineIndex + 1) + lineStr; }
8434
- lineStr = chunk.intro + lineStr;
8435
- }
8436
- } while (chunk = chunk.previous);
8437
- lineIndex = this.intro.lastIndexOf(n);
8438
- if (lineIndex !== -1)
8439
- { return this.intro.substr(lineIndex + 1) + lineStr; }
8440
- return this.intro + lineStr;
7386
+ if (last === words.length) {
7387
+ return string;
7388
+ }
7389
+
7390
+ return words.slice(0, last).join(' ') + words.slice(last).join('');
8441
7391
  };
8442
7392
 
8443
- MagicString.prototype.slice = function slice (start, end) {
8444
- if ( start === void 0 ) start = 0;
8445
- if ( end === void 0 ) end = this.original.length;
7393
+ // The wrap-ansi module can be invoked in either 'hard' or 'soft' wrap mode
7394
+ //
7395
+ // 'hard' will never allow a string to take up more than columns characters
7396
+ //
7397
+ // 'soft' allows long words to expand past the column length
7398
+ const exec = (string, columns, options = {}) => {
7399
+ if (options.trim !== false && string.trim() === '') {
7400
+ return '';
7401
+ }
8446
7402
 
8447
- while (start < 0) { start += this.original.length; }
8448
- while (end < 0) { end += this.original.length; }
7403
+ let returnValue = '';
7404
+ let escapeCode;
7405
+ let escapeUrl;
8449
7406
 
8450
- var result = '';
7407
+ const lengths = wordLengths(string);
7408
+ let rows = [''];
8451
7409
 
8452
- // find start chunk
8453
- var chunk = this.firstChunk;
8454
- while (chunk && (chunk.start > start || chunk.end <= start)) {
8455
- // found end chunk before start
8456
- if (chunk.start < end && chunk.end >= end) {
8457
- return result;
7410
+ for (const [index, word] of string.split(' ').entries()) {
7411
+ if (options.trim !== false) {
7412
+ rows[rows.length - 1] = rows[rows.length - 1].trimStart();
8458
7413
  }
8459
7414
 
8460
- chunk = chunk.next;
8461
- }
7415
+ let rowLength = stringWidth(rows[rows.length - 1]);
8462
7416
 
8463
- if (chunk && chunk.edited && chunk.start !== start)
8464
- { throw new Error(("Cannot use replaced character " + start + " as slice start anchor.")); }
7417
+ if (index !== 0) {
7418
+ if (rowLength >= columns && (options.wordWrap === false || options.trim === false)) {
7419
+ // If we start with a new word but the current row length equals the length of the columns, add a new row
7420
+ rows.push('');
7421
+ rowLength = 0;
7422
+ }
8465
7423
 
8466
- var startChunk = chunk;
8467
- while (chunk) {
8468
- if (chunk.intro && (startChunk !== chunk || chunk.start === start)) {
8469
- result += chunk.intro;
7424
+ if (rowLength > 0 || options.trim === false) {
7425
+ rows[rows.length - 1] += ' ';
7426
+ rowLength++;
7427
+ }
8470
7428
  }
8471
7429
 
8472
- var containsEnd = chunk.start < end && chunk.end >= end;
8473
- if (containsEnd && chunk.edited && chunk.end !== end)
8474
- { throw new Error(("Cannot use replaced character " + end + " as slice end anchor.")); }
7430
+ // In 'hard' wrap mode, the length of a line is never allowed to extend past 'columns'
7431
+ if (options.hard && lengths[index] > columns) {
7432
+ const remainingColumns = (columns - rowLength);
7433
+ const breaksStartingThisLine = 1 + Math.floor((lengths[index] - remainingColumns - 1) / columns);
7434
+ const breaksStartingNextLine = Math.floor((lengths[index] - 1) / columns);
7435
+ if (breaksStartingNextLine < breaksStartingThisLine) {
7436
+ rows.push('');
7437
+ }
8475
7438
 
8476
- var sliceStart = startChunk === chunk ? start - chunk.start : 0;
8477
- var sliceEnd = containsEnd ? chunk.content.length + end - chunk.end : chunk.content.length;
7439
+ wrapWord(rows, word, columns);
7440
+ continue;
7441
+ }
8478
7442
 
8479
- result += chunk.content.slice(sliceStart, sliceEnd);
7443
+ if (rowLength + lengths[index] > columns && rowLength > 0 && lengths[index] > 0) {
7444
+ if (options.wordWrap === false && rowLength < columns) {
7445
+ wrapWord(rows, word, columns);
7446
+ continue;
7447
+ }
8480
7448
 
8481
- if (chunk.outro && (!containsEnd || chunk.end === end)) {
8482
- result += chunk.outro;
7449
+ rows.push('');
8483
7450
  }
8484
7451
 
8485
- if (containsEnd) {
8486
- break;
7452
+ if (rowLength + lengths[index] > columns && options.wordWrap === false) {
7453
+ wrapWord(rows, word, columns);
7454
+ continue;
8487
7455
  }
8488
7456
 
8489
- chunk = chunk.next;
7457
+ rows[rows.length - 1] += word;
8490
7458
  }
8491
7459
 
8492
- return result;
8493
- };
7460
+ if (options.trim !== false) {
7461
+ rows = rows.map(row => stringVisibleTrimSpacesRight(row));
7462
+ }
8494
7463
 
8495
- // TODO deprecate this? not really very useful
8496
- MagicString.prototype.snip = function snip (start, end) {
8497
- var clone = this.clone();
8498
- clone.remove(0, start);
8499
- clone.remove(end, clone.original.length);
7464
+ const pre = [...rows.join('\n')];
8500
7465
 
8501
- return clone;
8502
- };
7466
+ for (const [index, character] of pre.entries()) {
7467
+ returnValue += character;
8503
7468
 
8504
- MagicString.prototype._split = function _split (index) {
8505
- if (this.byStart[index] || this.byEnd[index]) { return; }
7469
+ if (ESCAPES.has(character)) {
7470
+ const {groups} = new RegExp(`(?:\\${ANSI_CSI}(?<code>\\d+)m|\\${ANSI_ESCAPE_LINK}(?<uri>.*)${ANSI_ESCAPE_BELL})`).exec(pre.slice(index).join('')) || {groups: {}};
7471
+ if (groups.code !== undefined) {
7472
+ const code = Number.parseFloat(groups.code);
7473
+ escapeCode = code === END_CODE ? undefined : code;
7474
+ } else if (groups.uri !== undefined) {
7475
+ escapeUrl = groups.uri.length === 0 ? undefined : groups.uri;
7476
+ }
7477
+ }
8506
7478
 
8507
- var chunk = this.lastSearchedChunk;
8508
- var searchForward = index > chunk.end;
7479
+ const code = ansiStyles.codes.get(Number(escapeCode));
8509
7480
 
8510
- while (chunk) {
8511
- if (chunk.contains(index)) { return this._splitChunk(chunk, index); }
7481
+ if (pre[index + 1] === '\n') {
7482
+ if (escapeUrl) {
7483
+ returnValue += wrapAnsiHyperlink('');
7484
+ }
8512
7485
 
8513
- chunk = searchForward ? this.byStart[chunk.end] : this.byEnd[chunk.start];
8514
- }
8515
- };
7486
+ if (escapeCode && code) {
7487
+ returnValue += wrapAnsiCode(code);
7488
+ }
7489
+ } else if (character === '\n') {
7490
+ if (escapeCode && code) {
7491
+ returnValue += wrapAnsiCode(escapeCode);
7492
+ }
8516
7493
 
8517
- MagicString.prototype._splitChunk = function _splitChunk (chunk, index) {
8518
- if (chunk.edited && chunk.content.length) {
8519
- // zero-length edited chunks are a special case (overlapping replacements)
8520
- var loc = getLocator(this.original)(index);
8521
- throw new Error(
8522
- ("Cannot split a chunk that has already been edited (" + (loc.line) + ":" + (loc.column) + " – \"" + (chunk.original) + "\")")
8523
- );
7494
+ if (escapeUrl) {
7495
+ returnValue += wrapAnsiHyperlink(escapeUrl);
7496
+ }
7497
+ }
8524
7498
  }
8525
7499
 
8526
- var newChunk = chunk.split(index);
8527
-
8528
- this.byEnd[index] = chunk;
8529
- this.byStart[index] = newChunk;
8530
- this.byEnd[newChunk.end] = newChunk;
7500
+ return returnValue;
7501
+ };
8531
7502
 
8532
- if (chunk === this.lastChunk) { this.lastChunk = newChunk; }
7503
+ // For each newline, invoke the method separately
7504
+ function wrapAnsi(string, columns, options) {
7505
+ return String(string)
7506
+ .normalize()
7507
+ .replace(/\r\n/g, '\n')
7508
+ .split('\n')
7509
+ .map(line => exec(line, columns, options))
7510
+ .join('\n');
7511
+ }
8533
7512
 
8534
- this.lastSearchedChunk = chunk;
8535
- return true;
8536
- };
7513
+ const defaultTerminalHeight = 24;
8537
7514
 
8538
- MagicString.prototype.toString = function toString () {
8539
- var str = this.intro;
7515
+ const getWidth = stream => {
7516
+ const {columns} = stream;
8540
7517
 
8541
- var chunk = this.firstChunk;
8542
- while (chunk) {
8543
- str += chunk.toString();
8544
- chunk = chunk.next;
7518
+ if (!columns) {
7519
+ return 80;
8545
7520
  }
8546
7521
 
8547
- return str + this.outro;
8548
- };
8549
-
8550
- MagicString.prototype.isEmpty = function isEmpty () {
8551
- var chunk = this.firstChunk;
8552
- do {
8553
- if (chunk.intro.length && chunk.intro.trim() ||
8554
- chunk.content.length && chunk.content.trim() ||
8555
- chunk.outro.length && chunk.outro.trim())
8556
- { return false; }
8557
- } while (chunk = chunk.next);
8558
- return true;
7522
+ return columns;
8559
7523
  };
8560
7524
 
8561
- MagicString.prototype.length = function length () {
8562
- var chunk = this.firstChunk;
8563
- var length = 0;
8564
- do {
8565
- length += chunk.intro.length + chunk.content.length + chunk.outro.length;
8566
- } while (chunk = chunk.next);
8567
- return length;
8568
- };
7525
+ const fitToTerminalHeight = (stream, text) => {
7526
+ const terminalHeight = stream.rows || defaultTerminalHeight;
7527
+ const lines = text.split('\n');
8569
7528
 
8570
- MagicString.prototype.trimLines = function trimLines () {
8571
- return this.trim('[\\r\\n]');
8572
- };
7529
+ const toRemove = lines.length - terminalHeight;
7530
+ if (toRemove <= 0) {
7531
+ return text;
7532
+ }
8573
7533
 
8574
- MagicString.prototype.trim = function trim (charType) {
8575
- return this.trimStart(charType).trimEnd(charType);
7534
+ return sliceAnsi(
7535
+ text,
7536
+ lines.slice(0, toRemove).join('\n').length + 1,
7537
+ text.length);
8576
7538
  };
8577
7539
 
8578
- MagicString.prototype.trimEndAborted = function trimEndAborted (charType) {
8579
- var rx = new RegExp((charType || '\\s') + '+$');
8580
-
8581
- this.outro = this.outro.replace(rx, '');
8582
- if (this.outro.length) { return true; }
8583
-
8584
- var chunk = this.lastChunk;
8585
-
8586
- do {
8587
- var end = chunk.end;
8588
- var aborted = chunk.trimEnd(rx);
8589
-
8590
- // if chunk was trimmed, we have a new lastChunk
8591
- if (chunk.end !== end) {
8592
- if (this.lastChunk === chunk) {
8593
- this.lastChunk = chunk.next;
8594
- }
7540
+ function createLogUpdate(stream, {showCursor = false} = {}) {
7541
+ let previousLineCount = 0;
7542
+ let previousWidth = getWidth(stream);
7543
+ let previousOutput = '';
8595
7544
 
8596
- this.byEnd[chunk.end] = chunk;
8597
- this.byStart[chunk.next.start] = chunk.next;
8598
- this.byEnd[chunk.next.end] = chunk.next;
7545
+ const render = (...arguments_) => {
7546
+ if (!showCursor) {
7547
+ cliCursor.hide();
8599
7548
  }
8600
7549
 
8601
- if (aborted) { return true; }
8602
- chunk = chunk.previous;
8603
- } while (chunk);
8604
-
8605
- return false;
8606
- };
7550
+ let output = arguments_.join(' ') + '\n';
7551
+ output = fitToTerminalHeight(stream, output);
7552
+ const width = getWidth(stream);
7553
+ if (output === previousOutput && previousWidth === width) {
7554
+ return;
7555
+ }
8607
7556
 
8608
- MagicString.prototype.trimEnd = function trimEnd (charType) {
8609
- this.trimEndAborted(charType);
8610
- return this;
8611
- };
8612
- MagicString.prototype.trimStartAborted = function trimStartAborted (charType) {
8613
- var rx = new RegExp('^' + (charType || '\\s') + '+');
7557
+ previousOutput = output;
7558
+ previousWidth = width;
7559
+ output = wrapAnsi(output, width, {
7560
+ trim: false,
7561
+ hard: true,
7562
+ wordWrap: false,
7563
+ });
7564
+ stream.write(ansiEscapes.eraseLines(previousLineCount) + output);
7565
+ previousLineCount = output.split('\n').length;
7566
+ };
8614
7567
 
8615
- this.intro = this.intro.replace(rx, '');
8616
- if (this.intro.length) { return true; }
7568
+ render.clear = () => {
7569
+ stream.write(ansiEscapes.eraseLines(previousLineCount));
7570
+ previousOutput = '';
7571
+ previousWidth = getWidth(stream);
7572
+ previousLineCount = 0;
7573
+ };
8617
7574
 
8618
- var chunk = this.firstChunk;
7575
+ render.done = () => {
7576
+ previousOutput = '';
7577
+ previousWidth = getWidth(stream);
7578
+ previousLineCount = 0;
8619
7579
 
8620
- do {
8621
- var end = chunk.end;
8622
- var aborted = chunk.trimStart(rx);
7580
+ if (!showCursor) {
7581
+ cliCursor.show();
7582
+ }
7583
+ };
8623
7584
 
8624
- if (chunk.end !== end) {
8625
- // special case...
8626
- if (chunk === this.lastChunk) { this.lastChunk = chunk.next; }
7585
+ return render;
7586
+ }
8627
7587
 
8628
- this.byEnd[chunk.end] = chunk;
8629
- this.byStart[chunk.next.start] = chunk.next;
8630
- this.byEnd[chunk.next.end] = chunk.next;
8631
- }
7588
+ createLogUpdate(process$1.stdout);
8632
7589
 
8633
- if (aborted) { return true; }
8634
- chunk = chunk.next;
8635
- } while (chunk);
7590
+ createLogUpdate(process$1.stderr);
8636
7591
 
8637
- return false;
7592
+ const DURATION_LONG = 300;
7593
+ const MAX_HEIGHT = 20;
7594
+ const outputMap = /* @__PURE__ */ new WeakMap();
7595
+ function formatFilepath(path) {
7596
+ const lastSlash = Math.max(path.lastIndexOf("/") + 1, 0);
7597
+ const basename = path.slice(lastSlash);
7598
+ let firstDot = basename.indexOf(".");
7599
+ if (firstDot < 0)
7600
+ firstDot = basename.length;
7601
+ firstDot += lastSlash;
7602
+ return c.dim(path.slice(0, lastSlash)) + path.slice(lastSlash, firstDot) + c.dim(path.slice(firstDot));
7603
+ }
7604
+ function renderTree(tasks, options, level = 0) {
7605
+ var _a, _b, _c, _d;
7606
+ let output = [];
7607
+ for (const task of tasks) {
7608
+ let suffix = "";
7609
+ const prefix = ` ${getStateSymbol(task)} `;
7610
+ if (task.mode === "skip" || task.mode === "todo")
7611
+ suffix += ` ${c.dim("[skipped]")}`;
7612
+ if (task.type === "suite")
7613
+ suffix += c.dim(` (${getTests(task).length})`);
7614
+ if ((_a = task.result) == null ? void 0 : _a.end) {
7615
+ const duration = task.result.end - task.result.start;
7616
+ if (duration > DURATION_LONG)
7617
+ suffix += c.yellow(` ${Math.round(duration)}${c.dim("ms")}`);
7618
+ }
7619
+ let name = task.name;
7620
+ if (level === 0)
7621
+ name = formatFilepath(name);
7622
+ output.push(" ".repeat(level) + prefix + name + suffix);
7623
+ if (((_b = task.result) == null ? void 0 : _b.state) !== "pass" && outputMap.get(task) != null) {
7624
+ let data = outputMap.get(task);
7625
+ if (typeof data === "string") {
7626
+ data = stripAnsi(data.trim().split("\n").filter(Boolean).pop());
7627
+ if (data === "")
7628
+ data = void 0;
7629
+ }
7630
+ if (data != null) {
7631
+ const out = `${" ".repeat(level)}${F_RIGHT} ${data}`;
7632
+ output.push(` ${c.gray(cliTruncate(out, getCols(-3)))}`);
7633
+ }
7634
+ }
7635
+ if (task.type === "suite" && task.tasks.length > 0) {
7636
+ if (((_c = task.result) == null ? void 0 : _c.state) === "fail" || ((_d = task.result) == null ? void 0 : _d.state) === "run" || options.renderSucceed)
7637
+ output = output.concat(renderTree(task.tasks, options, level + 1));
7638
+ }
7639
+ }
7640
+ return output.slice(0, MAX_HEIGHT).join("\n");
7641
+ }
7642
+ const createListRenderer = (_tasks, options = {}) => {
7643
+ let tasks = _tasks;
7644
+ let timer;
7645
+ const stdout = process.stdout;
7646
+ const log = createLogUpdate(stdout);
7647
+ function update() {
7648
+ log(renderTree(tasks, options));
7649
+ }
7650
+ return {
7651
+ start() {
7652
+ if (timer)
7653
+ return this;
7654
+ timer = setInterval(update, 200);
7655
+ return this;
7656
+ },
7657
+ update(_tasks2) {
7658
+ tasks = _tasks2;
7659
+ update();
7660
+ return this;
7661
+ },
7662
+ async stop() {
7663
+ if (timer) {
7664
+ clearInterval(timer);
7665
+ timer = void 0;
7666
+ }
7667
+ log.clear();
7668
+ stdout.write(`${renderTree(tasks, options)}
7669
+ `);
7670
+ return this;
7671
+ },
7672
+ clear() {
7673
+ log.clear();
7674
+ }
7675
+ };
8638
7676
  };
8639
7677
 
8640
- MagicString.prototype.trimStart = function trimStart (charType) {
8641
- this.trimStartAborted(charType);
8642
- return this;
8643
- };
7678
+ class DefaultReporter extends BaseReporter {
7679
+ constructor() {
7680
+ super(...arguments);
7681
+ this.rendererOptions = {};
7682
+ }
7683
+ onStart() {
7684
+ if (this.isTTY) {
7685
+ const files = this.ctx.state.getFiles(this.watchFilters);
7686
+ if (!this.renderer)
7687
+ this.renderer = createListRenderer(files, this.rendererOptions).start();
7688
+ else
7689
+ this.renderer.update(files);
7690
+ }
7691
+ }
7692
+ async onFinished(files = this.ctx.state.getFiles()) {
7693
+ await this.stopListRender();
7694
+ this.ctx.log();
7695
+ await super.onFinished(files);
7696
+ }
7697
+ async onWatcherStart() {
7698
+ await this.stopListRender();
7699
+ super.onWatcherStart();
7700
+ }
7701
+ async stopListRender() {
7702
+ var _a;
7703
+ (_a = this.renderer) == null ? void 0 : _a.stop();
7704
+ this.renderer = void 0;
7705
+ await new Promise((resolve) => setTimeout(resolve, 10));
7706
+ }
7707
+ async onWatcherRerun(files, trigger) {
7708
+ await this.stopListRender();
7709
+ await super.onWatcherRerun(files, trigger);
7710
+ }
7711
+ onUserConsoleLog(log) {
7712
+ var _a;
7713
+ (_a = this.renderer) == null ? void 0 : _a.clear();
7714
+ super.onUserConsoleLog(log);
7715
+ }
7716
+ }
8644
7717
 
8645
- const mockRegexp = /\b(?:vitest|vi)\s*.\s*(mock|unmock|importActual|importMock)\(["`'\s](.*[@\w_-]+)["`'\s]\);?/mg;
8646
- const MocksPlugin = () => {
7718
+ const check = c.green("\xB7");
7719
+ const cross = c.red("x");
7720
+ const pending = c.yellow("*");
7721
+ const skip = c.dim(c.gray("-"));
7722
+ function render(tasks) {
7723
+ const all = getTests(tasks);
7724
+ return all.map((i) => {
7725
+ var _a;
7726
+ if (i.mode === "skip" || i.mode === "todo")
7727
+ return skip;
7728
+ switch ((_a = i.result) == null ? void 0 : _a.state) {
7729
+ case "pass":
7730
+ return check;
7731
+ case "fail":
7732
+ return cross;
7733
+ default:
7734
+ return pending;
7735
+ }
7736
+ }).join("");
7737
+ }
7738
+ const createDotRenderer = (_tasks) => {
7739
+ let tasks = _tasks;
7740
+ let timer;
7741
+ const stdout = process.stdout;
7742
+ const log = createLogUpdate(stdout);
7743
+ function update() {
7744
+ log(render(tasks));
7745
+ }
8647
7746
  return {
8648
- name: "vitest:mock-plugin",
8649
- enforce: "post",
8650
- async transform(code, id) {
8651
- let m;
8652
- const matchAll = Array.from(code.matchAll(mockRegexp));
8653
- if (!matchAll.length)
8654
- return;
8655
- for (const match of matchAll) {
8656
- const [line, method, modulePath] = match;
8657
- const filepath = await this.resolve(modulePath, id);
8658
- if (filepath) {
8659
- m ?? (m = new MagicString(code));
8660
- const start = match.index || 0;
8661
- const end = start + line.length;
8662
- let nodeModule = "null";
8663
- if (filepath.id.includes("/node_modules/"))
8664
- nodeModule = `"${modulePath}"`;
8665
- const overwrite = `__vitest__${method}__("${filepath.id}", ${nodeModule});`;
8666
- if (method === "mock") {
8667
- m.prepend(`${overwrite}
8668
-
8669
- `);
8670
- m.remove(start, end);
8671
- } else {
8672
- m.overwrite(start, end, overwrite);
8673
- }
8674
- }
8675
- }
8676
- if (m) {
8677
- return {
8678
- code: m.toString(),
8679
- map: m.generateMap()
8680
- };
7747
+ start() {
7748
+ if (timer)
7749
+ return this;
7750
+ timer = setInterval(update, 200);
7751
+ return this;
7752
+ },
7753
+ update(_tasks2) {
7754
+ tasks = _tasks2;
7755
+ update();
7756
+ return this;
7757
+ },
7758
+ async stop() {
7759
+ if (timer) {
7760
+ clearInterval(timer);
7761
+ timer = void 0;
8681
7762
  }
7763
+ log.clear();
7764
+ stdout.write(`${render(tasks)}
7765
+ `);
7766
+ return this;
7767
+ },
7768
+ clear() {
7769
+ log.clear();
8682
7770
  }
8683
7771
  };
8684
7772
  };
8685
7773
 
7774
+ class DotReporter extends BaseReporter {
7775
+ onStart() {
7776
+ if (this.isTTY) {
7777
+ const files = this.ctx.state.getFiles(this.watchFilters);
7778
+ if (!this.renderer)
7779
+ this.renderer = createDotRenderer(files).start();
7780
+ else
7781
+ this.renderer.update(files);
7782
+ }
7783
+ }
7784
+ async onFinished(files = this.ctx.state.getFiles()) {
7785
+ await this.stopListRender();
7786
+ this.ctx.log();
7787
+ await super.onFinished(files);
7788
+ }
7789
+ async onWatcherStart() {
7790
+ await this.stopListRender();
7791
+ super.onWatcherStart();
7792
+ }
7793
+ async stopListRender() {
7794
+ var _a;
7795
+ (_a = this.renderer) == null ? void 0 : _a.stop();
7796
+ this.renderer = void 0;
7797
+ await new Promise((resolve) => setTimeout(resolve, 10));
7798
+ }
7799
+ async onWatcherRerun(files, trigger) {
7800
+ await this.stopListRender();
7801
+ await super.onWatcherRerun(files, trigger);
7802
+ }
7803
+ onUserConsoleLog(log) {
7804
+ var _a;
7805
+ (_a = this.renderer) == null ? void 0 : _a.clear();
7806
+ super.onUserConsoleLog(log);
7807
+ }
7808
+ }
7809
+
7810
+ class VerboseReporter extends DefaultReporter {
7811
+ constructor(ctx) {
7812
+ super(ctx);
7813
+ this.rendererOptions.renderSucceed = true;
7814
+ }
7815
+ }
7816
+
7817
+ const ReportersMap = {
7818
+ default: DefaultReporter,
7819
+ verbose: VerboseReporter,
7820
+ dot: DotReporter
7821
+ };
7822
+
8686
7823
  class StateManager {
8687
7824
  constructor() {
8688
7825
  this.filesMap = {};
@@ -8793,7 +7930,7 @@ async function _transformRequest(ctx, id) {
8793
7930
  }
8794
7931
  if (result && process.env.NODE_V8_COVERAGE)
8795
7932
  withInlineSourcemap(result);
8796
- return result == null ? void 0 : result.code;
7933
+ return result;
8797
7934
  }
8798
7935
  let SOURCEMAPPING_URL = "sourceMa";
8799
7936
  SOURCEMAPPING_URL += "ppingURL";
@@ -8890,8 +8027,18 @@ function createChannel(ctx) {
8890
8027
  return;
8891
8028
  case "snapshotSaved":
8892
8029
  return send(() => ctx.snapshot.add(args[0]));
8030
+ case "getSourceMap":
8031
+ return send(() => {
8032
+ const [id2, force] = args;
8033
+ if (force) {
8034
+ const mod = ctx.server.moduleGraph.getModuleById(id2);
8035
+ if (mod)
8036
+ ctx.server.moduleGraph.invalidateModule(mod);
8037
+ }
8038
+ return transformRequest(ctx, id2).then((r) => r == null ? void 0 : r.map);
8039
+ });
8893
8040
  case "fetch":
8894
- return send(() => transformRequest(ctx, ...args));
8041
+ return send(() => transformRequest(ctx, ...args).then((r) => r == null ? void 0 : r.code));
8895
8042
  case "onCollected":
8896
8043
  ctx.state.collectFiles(args[0]);
8897
8044
  ctx.reporters.forEach((r) => {
@@ -8946,9 +8093,17 @@ class Vitest {
8946
8093
  this.config = resolved;
8947
8094
  this.state = new StateManager();
8948
8095
  this.snapshot = new SnapshotManager(resolved);
8949
- this.reporters = toArray(resolved.reporters);
8096
+ this.reporters = toArray(resolved.reporters || resolved.reporter).map((i) => {
8097
+ if (typeof i === "string") {
8098
+ const Reporter = ReportersMap[i];
8099
+ if (!Reporter)
8100
+ throw new Error(`Unknown reporter: ${i}`);
8101
+ return new Reporter(this);
8102
+ }
8103
+ return i;
8104
+ });
8950
8105
  if (!this.reporters.length && !this.config.silent)
8951
- this.reporters.push(new ConsoleReporter(this));
8106
+ this.reporters.push(new DefaultReporter(this));
8952
8107
  if (this.config.watch)
8953
8108
  this.registerWatcher();
8954
8109
  this.runningPromise = void 0;
@@ -9114,7 +8269,7 @@ async function createVitest(options, viteOverrides = {}) {
9114
8269
  ctx.setServer(options, server2);
9115
8270
  haveStarted = true;
9116
8271
  if (options.api)
9117
- server2.middlewares.use((await import('./middleware-093a3bde.js')).default(ctx));
8272
+ server2.middlewares.use((await import('./middleware-0ebc5238.js')).default(ctx));
9118
8273
  }
9119
8274
  },
9120
8275
  MocksPlugin()