Skip to content

Commit 9307755

Browse files
feat: use ECMA modules in client (#3550)
1 parent 977a70d commit 9307755

33 files changed

+135
-105
lines changed

.eslintrc.js

+11
Original file line numberDiff line numberDiff line change
@@ -24,9 +24,20 @@ module.exports = {
2424
overrides: [
2525
{
2626
files: ["client-src/**/*.js"],
27+
excludedFiles: [
28+
"client-src/webpack.config.js",
29+
"client-src/modules/logger/SyncBailHookFake.js",
30+
],
31+
parserOptions: {
32+
sourceType: "module",
33+
allowImportExportEverywhere: true,
34+
},
2735
env: {
2836
browser: true,
2937
},
38+
rules: {
39+
"import/extensions": ["error", "always"],
40+
},
3041
},
3142
{
3243
files: ["test/**/*.js"],

babel.config.js

+12
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,9 @@ module.exports = (api) => {
88
[
99
"@babel/preset-env",
1010
{
11+
modules: false,
1112
targets: {
13+
esmodules: true,
1214
node: "0.12",
1315
},
1416
},
@@ -17,6 +19,16 @@ module.exports = (api) => {
1719
plugins: ["@babel/plugin-transform-object-assign"],
1820
env: {
1921
test: {
22+
presets: [
23+
[
24+
"@babel/preset-env",
25+
{
26+
targets: {
27+
node: "12.13.0",
28+
},
29+
},
30+
],
31+
],
2032
plugins: ["@babel/plugin-transform-runtime"],
2133
},
2234
},

client-src/clients/SockJSClient.js

+4-6
Original file line numberDiff line numberDiff line change
@@ -1,9 +1,7 @@
1-
"use strict";
1+
import SockJS from "../modules/sockjs-client/index.js";
2+
import { log } from "../utils/log.js";
23

3-
const SockJS = require("../modules/sockjs-client");
4-
const { log } = require("../utils/log");
5-
6-
module.exports = class SockJSClient {
4+
export default class SockJSClient {
75
constructor(url) {
86
// SockJS requires `http` and `https` protocols
97
this.sock = new SockJS(
@@ -28,4 +26,4 @@ module.exports = class SockJSClient {
2826
f(e.data);
2927
};
3028
}
31-
};
29+
}

client-src/clients/WebsocketClient.js renamed to client-src/clients/WebSocketClient.js

+3-5
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,6 @@
1-
"use strict";
1+
import { log } from "../utils/log.js";
22

3-
const { log } = require("../utils/log");
4-
5-
module.exports = class WebsocketClient {
3+
export default class WebSocketClient {
64
constructor(url) {
75
this.client = new WebSocket(url);
86
this.client.onerror = (error) => {
@@ -24,4 +22,4 @@ module.exports = class WebsocketClient {
2422
f(e.data);
2523
};
2624
}
27-
};
25+
}

client-src/index.js

+16-18
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,14 @@
1-
"use strict";
2-
3-
/* global __resourceQuery WorkerGlobalScope */
4-
5-
const webpackHotLog = require("webpack/hot/log");
6-
const stripAnsi = require("./modules/strip-ansi");
7-
const parseURL = require("./utils/parseURL");
8-
const socket = require("./socket");
9-
const overlay = require("./overlay");
10-
const { log, setLogLevel } = require("./utils/log");
11-
const sendMessage = require("./utils/sendMessage");
12-
const reloadApp = require("./utils/reloadApp");
13-
const createSocketURL = require("./utils/createSocketURL");
1+
/* global __resourceQuery */
2+
3+
import webpackHotLog from "webpack/hot/log.js";
4+
import stripAnsi from "./modules/strip-ansi/index.js";
5+
import parseURL from "./utils/parseURL.js";
6+
import socket from "./socket.js";
7+
import { show, hide } from "./overlay.js";
8+
import { log, setLogLevel } from "./utils/log.js";
9+
import sendMessage from "./utils/sendMessage.js";
10+
import reloadApp from "./utils/reloadApp.js";
11+
import createSocketURL from "./utils/createSocketURL.js";
1412

1513
const status = { isUnloading: false, currentHash: "" };
1614
const options = {
@@ -66,7 +64,7 @@ const onSocketMessage = {
6664

6765
// Fixes #1042. overlay doesn't clear if errors are fixed but warnings remain.
6866
if (options.overlay) {
69-
overlay.hide();
67+
hide();
7068
}
7169

7270
sendMessage("Invalid");
@@ -100,7 +98,7 @@ const onSocketMessage = {
10098
log.info("Nothing changed.");
10199

102100
if (options.overlay) {
103-
overlay.hide();
101+
hide();
104102
}
105103

106104
sendMessage("StillOk");
@@ -109,7 +107,7 @@ const onSocketMessage = {
109107
sendMessage("Ok");
110108

111109
if (options.overlay) {
112-
overlay.hide();
110+
hide();
113111
}
114112

115113
if (options.initial) {
@@ -156,7 +154,7 @@ const onSocketMessage = {
156154
: options.overlay && options.overlay.warnings;
157155

158156
if (needShowOverlay) {
159-
overlay.show(warnings, "warnings");
157+
show(warnings, "warnings");
160158
}
161159

162160
if (options.initial) {
@@ -184,7 +182,7 @@ const onSocketMessage = {
184182
: options.overlay && options.overlay.errors;
185183

186184
if (needShowOverlay) {
187-
overlay.show(errors, "errors");
185+
show(errors, "errors");
188186
}
189187

190188
options.initial = false;

client-src/modules/logger/index.js

+1-3
Original file line numberDiff line numberDiff line change
@@ -1,3 +1 @@
1-
"use strict";
2-
3-
module.exports = require("webpack/lib/logging/runtime");
1+
export { default } from "webpack/lib/logging/runtime.js";
+1-3
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,2 @@
1-
"use strict";
2-
31
// eslint-disable-next-line import/no-extraneous-dependencies
4-
module.exports = require("sockjs-client");
2+
export { default } from "sockjs-client";
+2-2
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,3 @@
1-
"use strict";
1+
import stripAnsi from "strip-ansi";
22

3-
module.exports = require("strip-ansi").default;
3+
export default stripAnsi;

client-src/overlay.js

+1-3
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,3 @@
1-
"use strict";
2-
31
// The error overlay is inspired (and mostly copied) from Create React App (https://github.com/facebookincubator/create-react-app)
42
// They, in turn, got inspired by webpack-hot-middleware (https://github.com/glenjamin/webpack-hot-middleware).
53

@@ -154,4 +152,4 @@ function show(messages, type) {
154152
});
155153
}
156154

157-
module.exports = { show, hide };
155+
export { show, hide };

client-src/socket.js

+11-9
Original file line numberDiff line numberDiff line change
@@ -1,16 +1,18 @@
1-
"use strict";
2-
31
/* global __webpack_dev_server_client__ */
4-
/* eslint-disable
5-
camelcase
6-
*/
2+
3+
import WebSocketClient from "./clients/WebSocketClient.js";
74

85
// this WebsocketClient is here as a default fallback, in case the client is not injected
6+
/* eslint-disable camelcase */
97
const Client =
8+
// eslint-disable-next-line camelcase, no-nested-ternary
109
typeof __webpack_dev_server_client__ !== "undefined"
11-
? __webpack_dev_server_client__
12-
: // eslint-disable-next-line import/no-unresolved
13-
require("./clients/WebsocketClient");
10+
? // eslint-disable-next-line camelcase
11+
typeof __webpack_dev_server_client__.default !== "undefined"
12+
? __webpack_dev_server_client__.default
13+
: __webpack_dev_server_client__
14+
: WebSocketClient;
15+
/* eslint-enable camelcase */
1416

1517
let retries = 0;
1618
let client = null;
@@ -54,4 +56,4 @@ const socket = function initSocket(url, handlers) {
5456
});
5557
};
5658

57-
module.exports = socket;
59+
export default socket;

client-src/utils/createSocketURL.js

+2-4
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,4 @@
1-
"use strict";
2-
3-
const url = require("url");
1+
import url from "url";
42

53
// We handle legacy API that is Node.js specific, and a newer API that implements the same WHATWG URL Standard used by web browsers
64
// Please look at https://nodejs.org/api/url.html#url_url_strings_and_url_objects
@@ -92,4 +90,4 @@ function createSocketURL(parsedURL) {
9290
});
9391
}
9492

95-
module.exports = createSocketURL;
93+
export default createSocketURL;

client-src/utils/getCurrentScriptSource.js

+1-3
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,3 @@
1-
"use strict";
2-
31
function getCurrentScriptSource() {
42
// `document.currentScript` is the most accurate way to find the current script,
53
// but is not supported in all browsers.
@@ -25,4 +23,4 @@ function getCurrentScriptSource() {
2523
throw new Error("[webpack-dev-server] Failed to get current script source.");
2624
}
2725

28-
module.exports = getCurrentScriptSource;
26+
export default getCurrentScriptSource;

client-src/utils/log.js

+4-4
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,4 @@
1-
"use strict";
2-
3-
const logger = require("../modules/logger");
1+
import logger from "../modules/logger/index.js";
42

53
const name = "webpack-dev-server";
64
// default level is set on the client side, so it does not need
@@ -13,4 +11,6 @@ function setLogLevel(level) {
1311

1412
setLogLevel(defaultLevel);
1513

16-
module.exports = { log: logger.getLogger(name), setLogLevel };
14+
const log = logger.getLogger(name);
15+
16+
export { log, setLogLevel };

client-src/utils/parseURL.js

+3-5
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,5 @@
1-
"use strict";
2-
3-
const url = require("url");
4-
const getCurrentScriptSource = require("./getCurrentScriptSource");
1+
import url from "url";
2+
import getCurrentScriptSource from "./getCurrentScriptSource.js";
53

64
function parseURL(resourceQuery) {
75
let options = {};
@@ -44,4 +42,4 @@ function parseURL(resourceQuery) {
4442
return options;
4543
}
4644

47-
module.exports = parseURL;
45+
export default parseURL;

client-src/utils/reloadApp.js

+3-6
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,5 @@
1-
"use strict";
2-
3-
const { log } = require("./log");
1+
import hotEmitter from "webpack/hot/emitter.js";
2+
import { log } from "./log.js";
43

54
function reloadApp({ hot, liveReload }, { isUnloading, currentHash }) {
65
if (isUnloading) {
@@ -23,8 +22,6 @@ function reloadApp({ hot, liveReload }, { isUnloading, currentHash }) {
2322
if (hot && allowToHot) {
2423
log.info("App hot update...");
2524

26-
const hotEmitter = require("webpack/hot/emitter");
27-
2825
hotEmitter.emit("webpackHotUpdate", currentHash);
2926

3027
if (typeof self !== "undefined" && self.window) {
@@ -53,4 +50,4 @@ function reloadApp({ hot, liveReload }, { isUnloading, currentHash }) {
5350
}
5451
}
5552

56-
module.exports = reloadApp;
53+
export default reloadApp;

client-src/utils/sendMessage.js

+1-3
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,3 @@
1-
"use strict";
2-
31
/* global __resourceQuery WorkerGlobalScope */
42

53
// Send messages to the outside, so plugins can consume it.
@@ -13,4 +11,4 @@ function sendMsg(type, data) {
1311
}
1412
}
1513

16-
module.exports = sendMsg;
14+
export default sendMsg;

client-src/webpack.config.js

+17-1
Original file line numberDiff line numberDiff line change
@@ -4,12 +4,28 @@ const path = require("path");
44
const webpack = require("webpack");
55
const { merge } = require("webpack-merge");
66

7+
const library = webpack.webpack
8+
? {
9+
library: {
10+
// type: "module",
11+
type: "commonjs",
12+
},
13+
}
14+
: { libraryTarget: "umd" };
15+
716
const baseForModules = {
817
devtool: false,
918
mode: "development",
19+
// TODO enable this in future after fix bug with `eval` in webpack
20+
// experiments: {
21+
// outputModule: true,
22+
// },
1023
output: {
1124
path: path.resolve(__dirname, "../client/modules"),
12-
libraryTarget: "commonjs2",
25+
...library,
26+
},
27+
optimization: {
28+
minimize: false,
1329
},
1430
target: webpack.webpack ? ["web", "es5"] : "web",
1531
module: {

lib/utils/DevServerPlugin.js

+1-1
Original file line numberDiff line numberDiff line change
@@ -46,7 +46,7 @@ class DevServerPlugin {
4646
);
4747
} else if (clientTransport === "ws") {
4848
ClientImplementation = require.resolve(
49-
"../../client/clients/WebsocketClient"
49+
"../../client/clients/WebSocketClient"
5050
);
5151
} else {
5252
try {

package.json

+1-1
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@
2727
"test": "npm run test:coverage",
2828
"pretest": "npm run lint",
2929
"prepare": "npm run build:client && husky install",
30-
"build:client": "rimraf ./client/* && babel client-src/ --out-dir client/ --ignore \"webpack.config.js\" && webpack --config client/webpack.config.js",
30+
"build:client": "rimraf ./client/* && babel client-src/ --out-dir client/ --ignore \"client-src/webpack.config.js\" --ignore \"client-src/modules\" && webpack --config client-src/webpack.config.js",
3131
"release": "standard-version"
3232
},
3333
"dependencies": {

test/__snapshots__/validate-options.test.js.snap.webpack4

+2-2
Original file line numberDiff line numberDiff line change
@@ -520,7 +520,7 @@ exports[`options validate should throw an error on the "port" option with 'null'
520520
* options.port should be \\"auto\\"."
521521
`;
522522

523-
exports[`options validate should throw an error on the "proxy" option with 'false' value 1`] = `
523+
exports[`options validate should throw an error on the "proxy" option with '() => {}' value 1`] = `
524524
"ValidationError: Invalid options object. Dev Server has been initialized using an options object that does not match the API schema.
525525
- options.proxy should be one of these:
526526
object { … } | [object { … } | function, ...]
@@ -533,7 +533,7 @@ exports[`options validate should throw an error on the "proxy" option with 'fals
533533
[object { … } | function, ...]"
534534
`;
535535

536-
exports[`options validate should throw an error on the "proxy" option with 'function () {}' value 1`] = `
536+
exports[`options validate should throw an error on the "proxy" option with 'false' value 1`] = `
537537
"ValidationError: Invalid options object. Dev Server has been initialized using an options object that does not match the API schema.
538538
- options.proxy should be one of these:
539539
object { … } | [object { … } | function, ...]

test/__snapshots__/validate-options.test.js.snap.webpack5

+2-2
Original file line numberDiff line numberDiff line change
@@ -520,7 +520,7 @@ exports[`options validate should throw an error on the "port" option with 'null'
520520
* options.port should be \\"auto\\"."
521521
`;
522522

523-
exports[`options validate should throw an error on the "proxy" option with 'false' value 1`] = `
523+
exports[`options validate should throw an error on the "proxy" option with '() => {}' value 1`] = `
524524
"ValidationError: Invalid options object. Dev Server has been initialized using an options object that does not match the API schema.
525525
- options.proxy should be one of these:
526526
object { … } | [object { … } | function, ...]
@@ -533,7 +533,7 @@ exports[`options validate should throw an error on the "proxy" option with 'fals
533533
[object { … } | function, ...]"
534534
`;
535535

536-
exports[`options validate should throw an error on the "proxy" option with 'function () {}' value 1`] = `
536+
exports[`options validate should throw an error on the "proxy" option with 'false' value 1`] = `
537537
"ValidationError: Invalid options object. Dev Server has been initialized using an options object that does not match the API schema.
538538
- options.proxy should be one of these:
539539
object { … } | [object { … } | function, ...]

0 commit comments

Comments
 (0)