Skip to content

Commit 2afb223

Browse files
authored
fix: polling usage in watchFiles option (#3366)
1 parent 63815b7 commit 2afb223

4 files changed

+242
-32
lines changed

lib/Server.js

+8-2
Original file line numberDiff line numberDiff line change
@@ -973,9 +973,15 @@ class Server {
973973
// https://github.com/webpack/watchpack/blob/master/lib/DirectoryWatcher.js#L49
974974
// this isn't an elegant solution, but we'll improve it in the future
975975
// eslint-disable-next-line no-undefined
976-
const usePolling = watchOptions.poll ? true : undefined;
976+
const usePolling =
977+
typeof watchOptions.usePolling !== 'undefined'
978+
? watchOptions.usePolling
979+
: Boolean(watchOptions.poll);
977980
const interval =
978-
typeof watchOptions.poll === 'number'
981+
// eslint-disable-next-line no-nested-ternary
982+
typeof watchOptions.interval !== 'undefined'
983+
? watchOptions.interval
984+
: typeof watchOptions.poll === 'number'
979985
? watchOptions.poll
980986
: // eslint-disable-next-line no-undefined
981987
undefined;
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
// Jest Snapshot v1, https://goo.gl/fbAQLP
2+
3+
exports[`'watchFiles' option should work with options {"poll":200} should pass correct options to chokidar config 1`] = `
4+
Object {
5+
"alwaysStat": true,
6+
"atomic": false,
7+
"followSymlinks": false,
8+
"ignoreInitial": true,
9+
"ignorePermissionErrors": true,
10+
"ignored": undefined,
11+
"interval": 200,
12+
"persistent": true,
13+
"usePolling": true,
14+
}
15+
`;
16+
17+
exports[`'watchFiles' option should work with options {"poll":true} should pass correct options to chokidar config 1`] = `
18+
Object {
19+
"alwaysStat": true,
20+
"atomic": false,
21+
"followSymlinks": false,
22+
"ignoreInitial": true,
23+
"ignorePermissionErrors": true,
24+
"ignored": undefined,
25+
"interval": undefined,
26+
"persistent": true,
27+
"usePolling": true,
28+
}
29+
`;
30+
31+
exports[`'watchFiles' option should work with options {"usePolling":false,"poll":true} should pass correct options to chokidar config 1`] = `
32+
Object {
33+
"alwaysStat": true,
34+
"atomic": false,
35+
"followSymlinks": false,
36+
"ignoreInitial": true,
37+
"ignorePermissionErrors": true,
38+
"ignored": undefined,
39+
"interval": undefined,
40+
"persistent": true,
41+
"usePolling": false,
42+
}
43+
`;
44+
45+
exports[`'watchFiles' option should work with options {"usePolling":false} should pass correct options to chokidar config 1`] = `
46+
Object {
47+
"alwaysStat": true,
48+
"atomic": false,
49+
"followSymlinks": false,
50+
"ignoreInitial": true,
51+
"ignorePermissionErrors": true,
52+
"ignored": undefined,
53+
"interval": undefined,
54+
"persistent": true,
55+
"usePolling": false,
56+
}
57+
`;
58+
59+
exports[`'watchFiles' option should work with options {"usePolling":true,"interval":200,"poll":400} should pass correct options to chokidar config 1`] = `
60+
Object {
61+
"alwaysStat": true,
62+
"atomic": false,
63+
"followSymlinks": false,
64+
"ignoreInitial": true,
65+
"ignorePermissionErrors": true,
66+
"ignored": undefined,
67+
"interval": 200,
68+
"persistent": true,
69+
"usePolling": true,
70+
}
71+
`;
72+
73+
exports[`'watchFiles' option should work with options {"usePolling":true} should pass correct options to chokidar config 1`] = `
74+
Object {
75+
"alwaysStat": true,
76+
"atomic": false,
77+
"followSymlinks": false,
78+
"ignoreInitial": true,
79+
"ignorePermissionErrors": true,
80+
"ignored": undefined,
81+
"interval": undefined,
82+
"persistent": true,
83+
"usePolling": true,
84+
}
85+
`;
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,85 @@
1+
// Jest Snapshot v1, https://goo.gl/fbAQLP
2+
3+
exports[`'watchFiles' option should work with options {"poll":200} should pass correct options to chokidar config 1`] = `
4+
Object {
5+
"alwaysStat": true,
6+
"atomic": false,
7+
"followSymlinks": false,
8+
"ignoreInitial": true,
9+
"ignorePermissionErrors": true,
10+
"ignored": undefined,
11+
"interval": 200,
12+
"persistent": true,
13+
"usePolling": true,
14+
}
15+
`;
16+
17+
exports[`'watchFiles' option should work with options {"poll":true} should pass correct options to chokidar config 1`] = `
18+
Object {
19+
"alwaysStat": true,
20+
"atomic": false,
21+
"followSymlinks": false,
22+
"ignoreInitial": true,
23+
"ignorePermissionErrors": true,
24+
"ignored": undefined,
25+
"interval": undefined,
26+
"persistent": true,
27+
"usePolling": true,
28+
}
29+
`;
30+
31+
exports[`'watchFiles' option should work with options {"usePolling":false,"poll":true} should pass correct options to chokidar config 1`] = `
32+
Object {
33+
"alwaysStat": true,
34+
"atomic": false,
35+
"followSymlinks": false,
36+
"ignoreInitial": true,
37+
"ignorePermissionErrors": true,
38+
"ignored": undefined,
39+
"interval": undefined,
40+
"persistent": true,
41+
"usePolling": false,
42+
}
43+
`;
44+
45+
exports[`'watchFiles' option should work with options {"usePolling":false} should pass correct options to chokidar config 1`] = `
46+
Object {
47+
"alwaysStat": true,
48+
"atomic": false,
49+
"followSymlinks": false,
50+
"ignoreInitial": true,
51+
"ignorePermissionErrors": true,
52+
"ignored": undefined,
53+
"interval": undefined,
54+
"persistent": true,
55+
"usePolling": false,
56+
}
57+
`;
58+
59+
exports[`'watchFiles' option should work with options {"usePolling":true,"interval":200,"poll":400} should pass correct options to chokidar config 1`] = `
60+
Object {
61+
"alwaysStat": true,
62+
"atomic": false,
63+
"followSymlinks": false,
64+
"ignoreInitial": true,
65+
"ignorePermissionErrors": true,
66+
"ignored": undefined,
67+
"interval": 200,
68+
"persistent": true,
69+
"usePolling": true,
70+
}
71+
`;
72+
73+
exports[`'watchFiles' option should work with options {"usePolling":true} should pass correct options to chokidar config 1`] = `
74+
Object {
75+
"alwaysStat": true,
76+
"atomic": false,
77+
"followSymlinks": false,
78+
"ignoreInitial": true,
79+
"ignorePermissionErrors": true,
80+
"ignored": undefined,
81+
"interval": undefined,
82+
"persistent": true,
83+
"usePolling": true,
84+
}
85+
`;

test/server/watchFiles-option.test.js

+64-30
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
const path = require('path');
44
const fs = require('graceful-fs');
5+
const chokidar = require('chokidar');
56
const testServer = require('../helpers/test-server');
67
const config = require('../fixtures/contentbase-config/webpack.config');
78
const port = require('../ports-map')['watchFiles-option'];
@@ -277,38 +278,71 @@ describe("'watchFiles' option", () => {
277278
describe('should work with options', () => {
278279
const file = path.join(watchDir, 'assets/example.txt');
279280

280-
beforeAll((done) => {
281-
server = testServer.start(
282-
config,
283-
{
284-
watchFiles: {
285-
paths: file,
286-
options: {
287-
usePolling: true,
281+
const chokidarMock = jest.spyOn(chokidar, 'watch');
282+
283+
const optionCases = [
284+
{
285+
poll: true,
286+
},
287+
{
288+
poll: 200,
289+
},
290+
{
291+
usePolling: true,
292+
},
293+
{
294+
usePolling: false,
295+
},
296+
{
297+
usePolling: false,
298+
poll: true,
299+
},
300+
{
301+
usePolling: true,
302+
interval: 200,
303+
poll: 400,
304+
},
305+
];
306+
307+
optionCases.forEach((optionCase) => {
308+
describe(JSON.stringify(optionCase), () => {
309+
beforeAll((done) => {
310+
chokidarMock.mockClear();
311+
server = testServer.start(
312+
config,
313+
{
314+
watchFiles: {
315+
paths: file,
316+
options: optionCase,
317+
},
318+
port,
288319
},
289-
},
290-
port,
291-
},
292-
done
293-
);
294-
});
295-
296-
afterAll((done) => {
297-
testServer.close(done);
298-
fs.truncateSync(file);
299-
});
300-
301-
it('should reload on file content changed', (done) => {
302-
server.staticWatchers[0].on('change', (changedPath) => {
303-
expect(changedPath).toBe(file);
304-
305-
done();
320+
done
321+
);
322+
});
323+
324+
afterAll((done) => {
325+
testServer.close(done);
326+
fs.truncateSync(file);
327+
});
328+
329+
it('should pass correct options to chokidar config', () => {
330+
expect(chokidarMock.mock.calls[0][1]).toMatchSnapshot();
331+
});
332+
333+
it('should reload on file content changed', (done) => {
334+
server.staticWatchers[0].on('change', (changedPath) => {
335+
expect(changedPath).toBe(file);
336+
337+
done();
338+
});
339+
340+
// change file content
341+
setTimeout(() => {
342+
fs.writeFileSync(file, 'Kurosaki Ichigo', 'utf8');
343+
}, 1000);
344+
});
306345
});
307-
308-
// change file content
309-
setTimeout(() => {
310-
fs.writeFileSync(file, 'Kurosaki Ichigo', 'utf8');
311-
}, 1000);
312346
});
313347
});
314348
});

0 commit comments

Comments
 (0)