diff --git a/client/index.js b/client/index.js
index 4903179b6a..30b8fe4869 100644
--- a/client/index.js
+++ b/client/index.js
@@ -170,12 +170,20 @@ if(hostname && (self.location.protocol === "https:" || urlParts.hostname === "0.
protocol = self.location.protocol;
}
+var rootPathName = url.parse(__webpack_public_path__).pathname || ""; // eslint-disable-line no-undef
+
+if(rootPathName.length > 1) {
+ rootPathName = rootPathName.replace(/\/+$/, "");
+}
+
+var sockjsPath = rootPathName + "/sockjs-node";
+
var socketUrl = url.format({
protocol: protocol,
auth: urlParts.auth,
hostname: hostname,
port: (urlParts.port === "0") ? self.location.port : urlParts.port,
- pathname: urlParts.path == null || urlParts.path === "/" ? "/sockjs-node" : urlParts.path
+ pathname: urlParts.path == null || urlParts.path === "/" ? sockjsPath : urlParts.path
});
socket(socketUrl, onSocketMsg);
diff --git a/examples/node-api-sockjs-prefix/README.md b/examples/node-api-sockjs-prefix/README.md
new file mode 100644
index 0000000000..1ce352b141
--- /dev/null
+++ b/examples/node-api-sockjs-prefix/README.md
@@ -0,0 +1,15 @@
+# Node.js API - Simple
+
+```shell
+node server.js
+```
+
+Starts a simple webpack-dev-server setup via the Node API. Open `http://localhost:8080/` to go the app.
+
+## What should happen
+
+In the app you should see "It's working."
+
+In `app.js`, uncomment the code that results in an error and save. This error should be visible in the CLI and devtools.
+
+Then, in `app.js`, uncomment the code that results in a warning. This warning should be visible in the CLI and devtools.
diff --git a/examples/node-api-sockjs-prefix/app.js b/examples/node-api-sockjs-prefix/app.js
new file mode 100644
index 0000000000..731be32436
--- /dev/null
+++ b/examples/node-api-sockjs-prefix/app.js
@@ -0,0 +1,7 @@
+document.write("It's working under a subapp");
+
+// This results in a warning:
+if(!window) require("./" + window + "parseable.js");
+
+// This results in an error:
+// if(!window) require("test");
diff --git a/examples/node-api-sockjs-prefix/index.html b/examples/node-api-sockjs-prefix/index.html
new file mode 100644
index 0000000000..86fc28b105
--- /dev/null
+++ b/examples/node-api-sockjs-prefix/index.html
@@ -0,0 +1,9 @@
+
+
+
+
+
+
+ Example: Node.js API - Simple
+
+
diff --git a/examples/node-api-sockjs-prefix/server.js b/examples/node-api-sockjs-prefix/server.js
new file mode 100644
index 0000000000..e2307d5360
--- /dev/null
+++ b/examples/node-api-sockjs-prefix/server.js
@@ -0,0 +1,25 @@
+"use strict";
+
+const Webpack = require("webpack");
+const path = require("path");
+const WebpackDevServer = require("../../lib/Server");
+const webpackConfig = require("./webpack.config");
+
+const compiler = Webpack(webpackConfig);
+const server = new WebpackDevServer(compiler, {
+ stats: {
+ colors: true
+ },
+ contentBase: path.resolve(__dirname),
+ watchContentBase: true,
+ sockjsPrefix: "/subapp",
+ publicPath: "/subapp/",
+ historyApiFallback: {
+ disableDotRule: true,
+ index: "/subapp/"
+ },
+});
+
+server.listen(8080, "127.0.0.1", function() {
+ console.log("Starting server on http://localhost:8080");
+});
diff --git a/examples/node-api-sockjs-prefix/webpack.config.js b/examples/node-api-sockjs-prefix/webpack.config.js
new file mode 100644
index 0000000000..4afd582e86
--- /dev/null
+++ b/examples/node-api-sockjs-prefix/webpack.config.js
@@ -0,0 +1,8 @@
+module.exports = {
+ context: __dirname,
+ entry: ["./app.js", "../../client/index.js?http://localhost:8080/"],
+ output: {
+ filename: "bundle.js",
+ publicPath: "/subapp/"
+ },
+}
diff --git a/lib/Server.js b/lib/Server.js
index 0805d8b910..07ff2878ab 100644
--- a/lib/Server.js
+++ b/lib/Server.js
@@ -42,6 +42,7 @@ function Server(compiler, options) {
this.disableHostCheck = !!options.disableHostCheck;
this.publicHost = options.public;
this.allowedHosts = options.allowedHosts;
+ this.sockjsPrefix = options.sockjsPrefix || ""
this.sockets = [];
this.contentBaseWatchers = [];
@@ -520,7 +521,7 @@ Server.prototype.listen = function(port, hostname) {
});
sockServer.installHandlers(this.listeningApp, {
- prefix: "/sockjs-node"
+ prefix: `${this.sockjsPrefix}/sockjs-node`
});
return returnValue;
}
diff --git a/lib/optionsSchema.json b/lib/optionsSchema.json
index 885c64191c..be7079c089 100644
--- a/lib/optionsSchema.json
+++ b/lib/optionsSchema.json
@@ -54,6 +54,10 @@
}
]
},
+ "sockjsPrefix": {
+ "description": "Optional prefix for the sockjs handler to be mounted to.",
+ "type": "string"
+ },
"socket": {
"description": "The Unix socket to listen to (instead of on a host).",
"type": "string"
diff --git a/test/Validation.test.js b/test/Validation.test.js
index 8da8b29815..61024ded12 100644
--- a/test/Validation.test.js
+++ b/test/Validation.test.js
@@ -48,7 +48,7 @@ describe("Validation", function() {
config: { asdf: true },
message: [
" - configuration has an unknown property 'asdf'. These properties are valid:",
- " object { hot?, hotOnly?, lazy?, bonjour?, host?, allowedHosts?, filename?, publicPath?, port?, socket?, " +
+ " object { hot?, hotOnly?, lazy?, bonjour?, host?, allowedHosts?, filename?, publicPath?, port?, sockjsPrefix?, socket?, " +
"watchOptions?, headers?, clientLogLevel?, overlay?, key?, cert?, ca?, pfx?, pfxPassphrase?, " +
"inline?, disableHostCheck?, public?, https?, contentBase?, watchContentBase?, open?, useLocalIp?, openPage?, features?, " +
"compress?, proxy?, historyApiFallback?, staticOptions?, setup?, stats?, reporter?, " +