• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1'use strict';
2const {
3  ArrayPrototypePush,
4  ArrayPrototypeShift,
5  Symbol,
6} = primordials;
7const Readable = require('internal/streams/readable');
8
9const kEmitMessage = Symbol('kEmitMessage');
10class TestsStream extends Readable {
11  #buffer;
12  #canPush;
13
14  constructor() {
15    super({ __proto__: null, objectMode: true });
16    this.#buffer = [];
17    this.#canPush = true;
18  }
19
20  _read() {
21    this.#canPush = true;
22
23    while (this.#buffer.length > 0) {
24      const obj = ArrayPrototypeShift(this.#buffer);
25
26      if (!this.#tryPush(obj)) {
27        return;
28      }
29    }
30  }
31
32  fail(nesting, loc, testNumber, name, details, directive) {
33    this[kEmitMessage]('test:fail', {
34      __proto__: null,
35      name,
36      nesting,
37      testNumber,
38      details,
39      ...loc,
40      ...directive,
41    });
42  }
43
44  ok(nesting, loc, testNumber, name, details, directive) {
45    this[kEmitMessage]('test:pass', {
46      __proto__: null,
47      name,
48      nesting,
49      testNumber,
50      details,
51      ...loc,
52      ...directive,
53    });
54  }
55
56  plan(nesting, loc, count) {
57    this[kEmitMessage]('test:plan', {
58      __proto__: null,
59      nesting,
60      count,
61      ...loc,
62    });
63  }
64
65  getSkip(reason = undefined) {
66    return { __proto__: null, skip: reason ?? true };
67  }
68
69  getTodo(reason = undefined) {
70    return { __proto__: null, todo: reason ?? true };
71  }
72
73  enqueue(nesting, loc, name) {
74    this[kEmitMessage]('test:enqueue', {
75      __proto__: null,
76      nesting,
77      name,
78      ...loc,
79    });
80  }
81
82  dequeue(nesting, loc, name) {
83    this[kEmitMessage]('test:dequeue', {
84      __proto__: null,
85      nesting,
86      name,
87      ...loc,
88    });
89  }
90
91  start(nesting, loc, name) {
92    this[kEmitMessage]('test:start', {
93      __proto__: null,
94      nesting,
95      name,
96      ...loc,
97    });
98  }
99
100  diagnostic(nesting, loc, message) {
101    this[kEmitMessage]('test:diagnostic', {
102      __proto__: null,
103      nesting,
104      message,
105      ...loc,
106    });
107  }
108
109  stderr(loc, message) {
110    this[kEmitMessage]('test:stderr', { __proto__: null, message, ...loc });
111  }
112
113  stdout(loc, message) {
114    this[kEmitMessage]('test:stdout', { __proto__: null, message, ...loc });
115  }
116
117  coverage(nesting, loc, summary) {
118    this[kEmitMessage]('test:coverage', {
119      __proto__: null,
120      nesting,
121      summary,
122      ...loc,
123    });
124  }
125
126  end() {
127    this.#tryPush(null);
128  }
129
130  [kEmitMessage](type, data) {
131    this.emit(type, data);
132    // Disabling as this going to the user-land
133    // eslint-disable-next-line node-core/set-proto-to-null-in-object
134    this.#tryPush({ type, data });
135  }
136
137  #tryPush(message) {
138    if (this.#canPush) {
139      this.#canPush = this.push(message);
140    } else {
141      ArrayPrototypePush(this.#buffer, message);
142    }
143
144    return this.#canPush;
145  }
146}
147
148module.exports = { TestsStream, kEmitMessage };
149