@reporters/testwatch 1.1.1 → 1.2.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +20 -0
- package/index.js +4 -5
- package/package.json +3 -2
- package/tests/fixtures/not-test.js +6 -0
- package/tests/index.test.js +53 -20
- /package/tests/fixtures/{j.test.js → j.spec.js} +0 -0
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,25 @@
|
|
|
1
1
|
# Changelog
|
|
2
2
|
|
|
3
|
+
## [1.2.1](https://github.com/MoLow/reporters/compare/testwatch-v1.2.0...testwatch-v1.2.1) (2023-07-02)
|
|
4
|
+
|
|
5
|
+
|
|
6
|
+
### Bug Fixes
|
|
7
|
+
|
|
8
|
+
* clear screen before tests ([3d3f67c](https://github.com/MoLow/reporters/commit/3d3f67cddd7047c857e001066021933eb1381ec3))
|
|
9
|
+
|
|
10
|
+
## [1.2.0](https://github.com/MoLow/reporters/compare/testwatch-v1.1.1...testwatch-v1.2.0) (2023-06-19)
|
|
11
|
+
|
|
12
|
+
|
|
13
|
+
### Features
|
|
14
|
+
|
|
15
|
+
* add test:watch script ([4357fbd](https://github.com/MoLow/reporters/commit/4357fbde5f337cfd39226497f8ce0f6760f8a62c))
|
|
16
|
+
* change default file filter ([5968235](https://github.com/MoLow/reporters/commit/596823529cd9a86e5eeada0523825fa215e49efe))
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
### Bug Fixes
|
|
20
|
+
|
|
21
|
+
* don't exit when no tests on initial run ([66bcc2b](https://github.com/MoLow/reporters/commit/66bcc2bc6436b544900cfbceb4bbfb0d93973490))
|
|
22
|
+
|
|
3
23
|
## [1.1.1](https://github.com/MoLow/reporters/compare/testwatch-v1.1.0...testwatch-v1.1.1) (2023-06-12)
|
|
4
24
|
|
|
5
25
|
|
package/index.js
CHANGED
|
@@ -39,7 +39,7 @@ process.stdin.setRawMode?.(true);
|
|
|
39
39
|
class REPL {
|
|
40
40
|
#controller = new AbortController();
|
|
41
41
|
|
|
42
|
-
#filesFilter = '';
|
|
42
|
+
#filesFilter = process.argv[2] || '';
|
|
43
43
|
|
|
44
44
|
#testsFilter = '';
|
|
45
45
|
|
|
@@ -57,13 +57,13 @@ class REPL {
|
|
|
57
57
|
#emitter = new EventEmitter();
|
|
58
58
|
|
|
59
59
|
async #runTests() {
|
|
60
|
+
this.#clear();
|
|
60
61
|
this.#controller.abort();
|
|
61
62
|
this.#controller = new AbortController();
|
|
62
|
-
const filter = this.#filesFilter ? `**/${this.#filesFilter}*.*` : '
|
|
63
|
+
const filter = this.#filesFilter ? `**/${this.#filesFilter}*.*` : '**/?(*.)+(spec|test).[jt]s';
|
|
63
64
|
const files = await glob(filter, { ignore: 'node_modules/**' });
|
|
64
65
|
|
|
65
66
|
if (!files.length) {
|
|
66
|
-
this.#clear();
|
|
67
67
|
process.stdout.write(chalk.red(`\nNo files found for pattern ${filter}\n`));
|
|
68
68
|
this.#emitter.emit('drained');
|
|
69
69
|
return;
|
|
@@ -220,8 +220,7 @@ ${Object.entries(this.#currentCommands)
|
|
|
220
220
|
}
|
|
221
221
|
|
|
222
222
|
async run() {
|
|
223
|
-
await this.#runTests();
|
|
224
|
-
await once(this.#emitter, 'drained');
|
|
223
|
+
await Promise.all([once(this.#emitter, 'drained'), this.#runTests()]);
|
|
225
224
|
this.#emitter.on('drained', () => this.#compactHelp());
|
|
226
225
|
this.#help();
|
|
227
226
|
for await (const data of on(process.stdin, 'data')) {
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@reporters/testwatch",
|
|
3
|
-
"version": "1.
|
|
3
|
+
"version": "1.2.1",
|
|
4
4
|
"description": "An interactive repl for `node:test`",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"node:test",
|
|
@@ -10,7 +10,8 @@
|
|
|
10
10
|
],
|
|
11
11
|
"bin": "./index.js",
|
|
12
12
|
"scripts": {
|
|
13
|
-
"test": "node --test-reporter=spec --test-reporter-destination=stdout --test-reporter=../github/index.js --test-reporter-destination=stdout --test tests/index.test.js"
|
|
13
|
+
"test": "node --test-reporter=spec --test-reporter-destination=stdout --test-reporter=../github/index.js --test-reporter-destination=stdout --test tests/index.test.js",
|
|
14
|
+
"test:watch": "testwatch tests/index"
|
|
14
15
|
},
|
|
15
16
|
"bugs": {
|
|
16
17
|
"url": "https://github.com/MoLow/reporters/issues"
|
package/tests/index.test.js
CHANGED
|
@@ -35,11 +35,11 @@ Filter Test
|
|
|
35
35
|
pattern › `;
|
|
36
36
|
const filterFilesPrompt = filterTestsPrompt.replace('test', 'file').replace('Test', 'File');
|
|
37
37
|
|
|
38
|
-
async function spawnInteractive(commandSequence = 'q') {
|
|
38
|
+
async function spawnInteractive(commandSequence = 'q', args = []) {
|
|
39
39
|
let stderr = '';
|
|
40
40
|
let stdout = '';
|
|
41
|
-
const child = spawn(process.execPath, ['../../index.js'], {
|
|
42
|
-
env: {
|
|
41
|
+
const child = spawn(process.execPath, ['../../index.js', ...args], {
|
|
42
|
+
env: {}, cwd: path.resolve(__dirname, 'fixtures'),
|
|
43
43
|
});
|
|
44
44
|
child.stdin.setEncoding('utf8');
|
|
45
45
|
let writing = false;
|
|
@@ -62,7 +62,7 @@ async function spawnInteractive(commandSequence = 'q') {
|
|
|
62
62
|
child.stdout.setEncoding('utf8');
|
|
63
63
|
child.stdout.on('data', (data) => {
|
|
64
64
|
stdout += data;
|
|
65
|
-
if (stdout.includes(mainMenu)) {
|
|
65
|
+
if (stdout.includes(mainMenu) || stdout.includes(mainMenuWithFilters)) {
|
|
66
66
|
writeInput();
|
|
67
67
|
}
|
|
68
68
|
});
|
|
@@ -89,21 +89,21 @@ describe('testwatch', { concurrency: true, skip: !isSupported ? 'unsupported nod
|
|
|
89
89
|
it('should run all tests on initialization', async () => {
|
|
90
90
|
const { outputs, stderr } = await spawnInteractive('q');
|
|
91
91
|
assert.strictEqual(stderr, '');
|
|
92
|
-
assert.deepStrictEqual(outputs, ['', `${tests}\n${mainMenu}\n`]);
|
|
92
|
+
assert.deepStrictEqual(outputs, ['', '', `${tests}\n${mainMenu}\n`]);
|
|
93
93
|
});
|
|
94
94
|
it('should handle CTR + C', async () => {
|
|
95
95
|
const { outputs, stderr } = await spawnInteractive('\x03');
|
|
96
96
|
assert.strictEqual(stderr, '');
|
|
97
|
-
assert.deepStrictEqual(outputs, ['', `${tests}\n${mainMenu}\n`]);
|
|
97
|
+
assert.deepStrictEqual(outputs, ['', '', `${tests}\n${mainMenu}\n`]);
|
|
98
98
|
});
|
|
99
99
|
it('should handle CTR + D', async () => {
|
|
100
100
|
const { outputs, stderr } = await spawnInteractive('\x04');
|
|
101
101
|
assert.strictEqual(stderr, '');
|
|
102
|
-
assert.deepStrictEqual(outputs, ['', `${tests}\n${mainMenu}\n`]);
|
|
102
|
+
assert.deepStrictEqual(outputs, ['', '', `${tests}\n${mainMenu}\n`]);
|
|
103
103
|
});
|
|
104
104
|
it('should exit on sigkill', async () => {
|
|
105
105
|
const child = spawn(process.execPath, ['../../index.js'], {
|
|
106
|
-
env: {
|
|
106
|
+
env: {}, cwd: path.resolve(__dirname, 'fixtures'),
|
|
107
107
|
});
|
|
108
108
|
let stderr = '';
|
|
109
109
|
let stdout = '';
|
|
@@ -121,19 +121,21 @@ describe('testwatch', { concurrency: true, skip: !isSupported ? 'unsupported nod
|
|
|
121
121
|
it('should run all tests on "a"', async () => {
|
|
122
122
|
const { outputs, stderr } = await spawnInteractive('aq');
|
|
123
123
|
assert.strictEqual(stderr, '');
|
|
124
|
-
assert.deepStrictEqual(outputs, ['', `${tests}\n${mainMenu}`, `${tests}\n${compactMenu}\n`]);
|
|
124
|
+
assert.deepStrictEqual(outputs, ['', '', `${tests}\n${mainMenu}`, '', `${tests}\n${compactMenu}\n`]);
|
|
125
125
|
});
|
|
126
126
|
it('should run all tests on Enter', async () => {
|
|
127
127
|
const { outputs, stderr } = await spawnInteractive('\rq');
|
|
128
128
|
assert.strictEqual(stderr, '');
|
|
129
|
-
assert.deepStrictEqual(outputs, ['', `${tests}\n${mainMenu}`, `${tests}\n${compactMenu}\n`]);
|
|
129
|
+
assert.deepStrictEqual(outputs, ['', '', `${tests}\n${mainMenu}`, '', `${tests}\n${compactMenu}\n`]);
|
|
130
130
|
});
|
|
131
131
|
it('should show full menu on "w" after running tests', async () => {
|
|
132
132
|
const { outputs, stderr } = await spawnInteractive('awq');
|
|
133
133
|
assert.strictEqual(stderr, '');
|
|
134
134
|
assert.deepStrictEqual(outputs, [
|
|
135
|
+
'',
|
|
135
136
|
'',
|
|
136
137
|
`${tests}\n${mainMenu}`,
|
|
138
|
+
'',
|
|
137
139
|
`${tests}\n${compactMenu}\n${clearLines}${mainMenu}\n`,
|
|
138
140
|
]);
|
|
139
141
|
});
|
|
@@ -144,10 +146,12 @@ describe('testwatch', { concurrency: true, skip: !isSupported ? 'unsupported nod
|
|
|
144
146
|
const activeFilters = '\nActive Filters: test name /sub/\n';
|
|
145
147
|
assert.strictEqual(stderr, '');
|
|
146
148
|
assert.deepStrictEqual(outputs, [
|
|
149
|
+
'',
|
|
147
150
|
'',
|
|
148
151
|
`${tests}\n${mainMenu}`,
|
|
149
152
|
`${filterTestsPrompt}sub`,
|
|
150
153
|
'',
|
|
154
|
+
'',
|
|
151
155
|
`${tests
|
|
152
156
|
.replace('✔ j - sum (*ms)', '﹣ j - sum (*ms) # SKIP')
|
|
153
157
|
.replace('✔ index - sum (*ms)', '﹣ index - sum (*ms) # SKIP')
|
|
@@ -156,15 +160,39 @@ describe('testwatch', { concurrency: true, skip: !isSupported ? 'unsupported nod
|
|
|
156
160
|
});
|
|
157
161
|
|
|
158
162
|
describe('files filter', () => {
|
|
163
|
+
it('should not exit if no test found on first run', async () => {
|
|
164
|
+
const { outputs, stderr } = await spawnInteractive('q', ['notexist']);
|
|
165
|
+
const activeFilters = '\nActive Filters: file name **/notexist*.*\n';
|
|
166
|
+
const notFound = '\nNo files found for pattern **/notexist*.*';
|
|
167
|
+
assert.strictEqual(stderr, '');
|
|
168
|
+
assert.deepStrictEqual(outputs, [
|
|
169
|
+
'',
|
|
170
|
+
`${notFound}\n${activeFilters}${mainMenuWithFilters}\n`,
|
|
171
|
+
]);
|
|
172
|
+
});
|
|
173
|
+
|
|
174
|
+
it('should set first argument as file filter', async () => {
|
|
175
|
+
const { outputs, stderr } = await spawnInteractive('q', ['ind']);
|
|
176
|
+
const activeFilters = '\nActive Filters: file name **/ind*.*\n';
|
|
177
|
+
assert.strictEqual(stderr, '');
|
|
178
|
+
assert.deepStrictEqual(outputs, [
|
|
179
|
+
'',
|
|
180
|
+
'',
|
|
181
|
+
`${testsRun[1]}\n${activeFilters}${mainMenuWithFilters}\n`,
|
|
182
|
+
]);
|
|
183
|
+
});
|
|
184
|
+
|
|
159
185
|
it('should filter files on "p"', async () => {
|
|
160
186
|
const { outputs, stderr } = await spawnInteractive(['p', 'index', '\r', 'w', 'q'].join(''));
|
|
161
187
|
const activeFilters = '\nActive Filters: file name **/index*.*\n';
|
|
162
188
|
assert.strictEqual(stderr, '');
|
|
163
189
|
assert.deepStrictEqual(outputs, [
|
|
190
|
+
'',
|
|
164
191
|
'',
|
|
165
192
|
`${tests}\n${mainMenu}`,
|
|
166
193
|
`${filterFilesPrompt}index`,
|
|
167
194
|
'',
|
|
195
|
+
'',
|
|
168
196
|
`${testsRun[1]}\n${compactMenu}\n${clearLines}${activeFilters}${mainMenuWithFilters}\n`,
|
|
169
197
|
]);
|
|
170
198
|
});
|
|
@@ -174,10 +202,12 @@ describe('testwatch', { concurrency: true, skip: !isSupported ? 'unsupported nod
|
|
|
174
202
|
const activeFilters = '\nActive Filters: file name **/ind*.*\n';
|
|
175
203
|
assert.strictEqual(stderr, '');
|
|
176
204
|
assert.deepStrictEqual(outputs, [
|
|
205
|
+
'',
|
|
177
206
|
'',
|
|
178
207
|
`${tests}\n${mainMenu}`,
|
|
179
208
|
`${filterFilesPrompt}ind`,
|
|
180
209
|
'',
|
|
210
|
+
'',
|
|
181
211
|
`${testsRun[1]}\n${compactMenu}\n${clearLines}${activeFilters}${mainMenuWithFilters}\n`,
|
|
182
212
|
]);
|
|
183
213
|
});
|
|
@@ -186,8 +216,8 @@ describe('testwatch', { concurrency: true, skip: !isSupported ? 'unsupported nod
|
|
|
186
216
|
const { outputs, stderr } = await spawnInteractive(['p', 'index', '\r', 't', 'sum', '\r', 'w', 'q'].join(''));
|
|
187
217
|
const activeFilters = '\nActive Filters: file name **/index*.*, test name /sum/\n';
|
|
188
218
|
assert.strictEqual(stderr, '');
|
|
189
|
-
assert.strictEqual(outputs.length,
|
|
190
|
-
assert.strictEqual(outputs[
|
|
219
|
+
assert.strictEqual(outputs.length, 11);
|
|
220
|
+
assert.strictEqual(outputs[10], `${testsRun[1].replace('✔ index - subtraction (*ms)', '﹣ index - subtraction (*ms) # SKIP')}\n${compactMenu}\n${clearLines}${activeFilters}${mainMenuWithFilters}\n`);
|
|
191
221
|
});
|
|
192
222
|
|
|
193
223
|
it('should mention when no files found', async () => {
|
|
@@ -196,6 +226,7 @@ describe('testwatch', { concurrency: true, skip: !isSupported ? 'unsupported nod
|
|
|
196
226
|
const notFound = '\nNo files found for pattern **/nothing*.*';
|
|
197
227
|
assert.strictEqual(stderr, '');
|
|
198
228
|
assert.deepStrictEqual(outputs, [
|
|
229
|
+
'',
|
|
199
230
|
'',
|
|
200
231
|
`${tests}\n${mainMenu}`,
|
|
201
232
|
`${filterFilesPrompt}nothing`,
|
|
@@ -207,12 +238,12 @@ describe('testwatch', { concurrency: true, skip: !isSupported ? 'unsupported nod
|
|
|
207
238
|
it('should clear filters on "c"', async () => {
|
|
208
239
|
const { outputs, stderr } = await spawnInteractive(['p', 'index', '\r', 'w', 't', 'sum', '\r', 'w', 'c', 'w', 'q'].join(''));
|
|
209
240
|
assert.strictEqual(stderr, '');
|
|
210
|
-
assert.strictEqual(outputs.length,
|
|
241
|
+
assert.strictEqual(outputs.length, 13);
|
|
211
242
|
|
|
212
|
-
assert.match(outputs[
|
|
213
|
-
assert.match(outputs[
|
|
214
|
-
assert.match(outputs[
|
|
215
|
-
assert.strictEqual(outputs[
|
|
243
|
+
assert.match(outputs[6], /Active Filters: file name \*\*\/index\*\.\*/);
|
|
244
|
+
assert.match(outputs[7], /Active Filters: file name \*\*\/index\*\.\*/);
|
|
245
|
+
assert.match(outputs[10], /Active Filters: file name \*\*\/index\*\.\*, test name \/sum\//);
|
|
246
|
+
assert.strictEqual(outputs[12], `${tests}\n${compactMenu}\n${clearLines}${mainMenu}\n`);
|
|
216
247
|
});
|
|
217
248
|
|
|
218
249
|
it('prompt ESC should preserve previous state', async () => {
|
|
@@ -220,10 +251,12 @@ describe('testwatch', { concurrency: true, skip: !isSupported ? 'unsupported nod
|
|
|
220
251
|
const notFound = '\nNo files found for pattern **/filter*.*';
|
|
221
252
|
const activeFilters = '\nActive Filters: file name **/filter*.*\n';
|
|
222
253
|
assert.deepStrictEqual(outputs, [
|
|
254
|
+
'',
|
|
223
255
|
'',
|
|
224
256
|
`${tests}\n${mainMenu}`,
|
|
225
257
|
`${filterFilesPrompt}`,
|
|
226
258
|
'',
|
|
259
|
+
'',
|
|
227
260
|
`${tests}\n${compactMenu}`,
|
|
228
261
|
`${filterFilesPrompt}filter`,
|
|
229
262
|
'',
|
|
@@ -234,12 +267,12 @@ describe('testwatch', { concurrency: true, skip: !isSupported ? 'unsupported nod
|
|
|
234
267
|
]);
|
|
235
268
|
});
|
|
236
269
|
|
|
237
|
-
it('backspace
|
|
270
|
+
it('backspace should remove last character', async () => {
|
|
238
271
|
const backspace = '\x7f';
|
|
239
272
|
const { outputs, stderr } = await spawnInteractive(['p', `noth123${backspace}${backspace}ing`, '\r', 'w', 'q'].join(''));
|
|
240
273
|
assert.strictEqual(stderr, '');
|
|
241
|
-
assert.strictEqual(outputs.length,
|
|
242
|
-
assert.match(outputs[
|
|
274
|
+
assert.strictEqual(outputs.length, 6);
|
|
275
|
+
assert.match(outputs[5], /No files found for pattern \*\*\/noth1ing\*\.\*/);
|
|
243
276
|
});
|
|
244
277
|
});
|
|
245
278
|
});
|
|
File without changes
|