Git Product home page Git Product logo

webpack-plugin-serve's Introduction

webpack-plugin-serve

tests cover size libera manifesto

webpack-plugin-serve

A Webpack development server in a plugin.

Be sure to browse our recipes and peruse the FAQ after reading the documentation below.

Please consider donating if you find this project useful.

Requirements

webpack-plugin-serve is an evergreen 🌲 module.

This module requires an Active LTS Node version (v10.0.0+). The client scripts in this module require browsers which support async/await. Users may also choose to compile the client script via an appropriately configured Babel webpack loader for use in older browsers.

Feature Parity

In many ways, webpack-plugin-serve stands out from the alternatives. Feature parity with existing solutions is a high priority. If a feature you've come to expect in an alternative isn't directly available, it's likely easy to implement via middleware. Feel free to open an issue for direction.

For those interested in direct comparisons, please see the Feature Grid for a breakdown of feature comparisons between webpack-plugin-serve and the alternatives.

Install

Using npm:

npm install webpack-nano webpack-plugin-serve --save-dev

Note: We recommend using webpack-nano, a very tiny, very clean webpack CLI.

Usage

Create a webpack.config.js file:

const { WebpackPluginServe: Serve } = require('webpack-plugin-serve');
const options = { ... };

module.exports = {
	// an example entry definition
	entry: [
		'webpack-plugin-serve/client' // ← important: this is required, where the magic happens in the browser
		'app.js'
	]
  ...
  plugins: [
    new Serve(options)
  ],
  watch: true  // ← important: webpack and the server will continue to run in watch mode
};

Note: For more information and examples on configuring the entry property, please see the Configuring Entry Points recipe.

And run webpack:

$ npx wp
...
⬡ wps: Server Listening on: http://[::]:55555
...

Options

client

Type: Object
Default: null

Sets options specifically for the client script. In most situations this option doesn't need to be modified.

Properties

client.address

Type: String

If set, allows for overriding the WebSocket address, which corresponds to the server address by default. Values for this option should be in a valid {host}:{port} format. e.g. localhost:433.

client.protocol

Type: String

If set, allows for overriding the WebSocket protocol scheme string, which corresponds to the server protocol scheme by default. Values for this option should be one of the following: ws or wss.

client.retry

Type: Boolean

If true, instructs the client to attempt to reconnect all WebSockets when their connects are interrupted, usually as a result of the server being stopped and/or restarted. Note: This can be very spammy in the browser console, as there is no way to suppress error messages from the browser when a WebSocket fails to connect.

client.silent

Type: Boolean

If true, instructs the client not to log anything to the console.

compress

Type: Boolean
Default: false

If true, enables compression middleware which serves files with GZip compression.

historyFallback

Type: Boolean | Object
Default: false

If true, enables History API Fallback via connect-history-api-fallback. Users may also pass an options Object to this property. Please see connect-history-api-fallback for details.

This setting can be handy when using the HTML5 History API; index.html page will likely have to be served in place of any 404 responses from the server, specially when developing Single Page Applications.

Note: The Accept header is explicitly stripped from the /wps WebSocket path when using historyFallback, due to an issue with how Firefox and the middleware interact.

hmr

Type: boolean | 'refresh-on-failure'
Default: true

If true, will enable Hot Module Replacement which exchanges, adds, or removes modules from a bundle dynamically while the application still running, without the need of a full page reload.

Note: If the build process generates errors, the client (browser) will not be notified of new changes and no HMR will be performed. Errors must be resolved before HMR can proceed. To force a refresh, pass `refresh-on-failure' to this option.

Note: If using in combination with http2, the http2 option allowHTTP1 must be enabled for the HMR WS connection to work.

host

Type: String | Promise
Default: :: for IPv6, 127.0.0.1 for IPv4

Sets the host the server should listen from. Users may choose to set this to a Promise, or a Function which returns a Promise for situations in which the server needs to wait for a host to resolve.

Note: The default URI is http://[::]:{port}. For more info, please read the FAQ.

http2

Type: boolean | http2 options | secure http2 options

If set, this option will instruct the server to enable HTTP2. Properties for this option should correspond to HTTP2 options or HTTP2 SSL options.

Note: If using in combination with hmr, the option allowHTTP1 must be enabled for the HMR WS connection to work.

https

Type: Object
Default: null

If set, this option will instruct the server to enable SSL via HTTPS. Properties for this option should correspond to HTTPS options.

liveReload

Type: boolean
Default: false

If true, will instruct the client to perform a full page reload after each build.

Note: This option overrides any value set for the hmr option property.

log

Type: Object
Default: { level: 'info' }
Valid level Values: 'trace' | 'debug' | 'info' | 'warn' | 'error'

Sets a level for which messages should appear in the console. For example: if warn is set, every message at the warn and error levels will be visible. This module doesn't produce much log output, so you probably won't have to fiddle with this.

A timestamp: true property/value may also be used to preface each log line with an HH:mm:ss format timestamp.

middleware

Type: Function
Default: (app, builtins) => {}

Allows users to implement custom middleware, and manipulate the order in which built-in middleware is executed. This method may also return a Promise to pause further middleware evaluation until the Promise resolves. This property should only be set by users with solid knowledge of Express/Koa style middleware and those which understand the consequences of manipulating the order of built-in middleware.

Example

// webpack.config.js
module.exports = {
  plugins: [
    new WebpackPluginServe({
      middleware: (app, builtins) =>
        app.use(async (ctx, next) => {
          ctx.body = 'Hello world';
          await next();
        })
    })
  ]
};

Built-in Middleware

The builtins parameter provides access to all of the underlying middleware that the plugin uses internally. That provides users with a maximum amount of control over behavior of the server. For more information and examples of use, please see the Built-in Middleware recipe.

open

Type: boolean | Object
Default: false

If true, opens the default browser to the set host and port. Users may also choose to pass an Object containing options for the open module, which is used for this feature.

port

Type: Number | Promise
Default: 55555

Sets the port on which the server should listen. Users may choose to set this to a Promise, or a Function which returns a Promise for situations in which the server needs to wait for a port to resolve.

progress

Type: boolean | String
Default: true

If truthy, the module will add a ProgressPlugin instance to the webpack compiler, and display a progress indicator on the page within the browser.

If a value of 'minimal' is set, the progress indicator will render as a small, colored bar at the top of the window. This can be useful when the default fancy progress indicator interferes with elements in the page.

publicPath

Type: String
Default: webpack.output.publicPath

Sets the publicPath that the server should use to serve assets. You probably only need to set this explicitly if you are using Webpack's auto feature for public path detection.

ramdisk

Type: boolean | Object
Default: false
Support: MacOS and Linux, Windows with WSL 2.0.

If true or Object (options), will apply webpack-plugin-ramdisk to the build. output configuration does not have to be modified, a symlink will be created from the original output path to the output path on the ramdisk. Note: This will remove an existing directory at the defined output path.

Leveraging this option can result in significant reduction of build time, which is especially useful when using hmr: true or liveReload: true. Typical build times can be cut by 25-32% or more depending on hardware and webpack configuration. This is also recommended for users with SSD, as it reduces hard disk thrashing.

Windows users without WSL 2.0 are encouraged to install it to make use of this feature, or create a ramdisk manually using a tool like ImDisk.

static

Type: String | Array(String) | Object
Default: compiler.context

Sets the directory(s) from which static files will be served from the root of the application. Bundles will be served from the output config setting. For specifying options for static file directories, please see koa-static. For an in-depth example, check out the Static HTML File recipe.

The static option supports glob patterns when an Object is passed with a glob property. This is useful for targeting only specific directories in a complex tree. Users may also provide an options property which supports globby options. For example:

static: {
  glob: [path.join(__dirname, 'dist/**/public')],
  options: { onlyDirectories: true }
}

status

Type: boolean
Default: true

By default, webpack-plugin-serve will display a status overlay when a build results in errors and/or warnings. To disable this feature, set status: false in the options.

status overlay

When the minimize button (yellow dot) is clicked, the overlay will shrink to a single small box in the lower right corner of the page and display a status beacon using the same green, red, and yellow colors for build success, errors, and warnings, respectively.

status beacons

waitForBuild

Type: boolean
Default: false

If true, instructs the server to halt middleware processing until the current build is done.

Proxying

Proxying with webpack-plugin-serve is supported via the middleware option, specifically the proxy built-in. But while this plugin module doesn't contain any fancy options processing for proxying, it does include access to the http-proxy-middleware module by default, and the rest should look familiar to users of http-proxy-middleware.

// webpack.config.js
module.exports = {
  ...,
  plugins: [
    new WebpackPluginServe({
      middleware: (app, builtins) => {
        app.use(builtins.proxy('/api', { target: 'http://10.10.10.1:1337' }));
      }
    })
  ]
};

Note: The app.use(...) call here is slightly different than what Express users are used to seeing with http-proxy-middleware. This is due to subtle differences in how the module interacts with Koa, which is used under the hood in this plugin.

TypeScript Types

To get type definitions for this project:

npm install -D @types/webpack-plugin-serve

Meta

CONTRIBUTING

LICENSE (Mozilla Public License)

webpack-plugin-serve's People

Contributors

agilgur5 avatar alexsergey avatar artembatura avatar bebraw avatar bz2 avatar cpylua avatar davidroeca avatar dependabot[bot] avatar evalon avatar g-rath avatar hudochenkov avatar karlhorky avatar kylew avatar lxe avatar matheus1lva avatar midudev avatar nicksrandall avatar niieani avatar pappasam avatar pearofducks avatar rosskevin avatar savo92 avatar serkanyersen avatar shellscape avatar sirbarrence avatar stephtr avatar stnwk avatar styfle avatar trysound avatar zauan avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

webpack-plugin-serve's Issues

documentation showing multiple named entry points in webpack.config.js

Documentation Is:

  • Missing
  • Needed
  • Confusing
  • Not Sure?

Please Explain in Detail...

The documentation currently shows how to set up webpack-plugin-serve using a single array in the "entry" configuration like so:

entry: ['app.js', 'webpack-plugin-serve/client']

It would be helpful to provide an example(s) of other, equally popular, entry configurations. For instance, if my webpack config currently looks like:

entry: {
  main: ['src/index.js'],
  account: ['src/account/index.js'],
  legacyStyles: ['src/scss/styles.scss']
}

It is unclear how to properly "wire-up" webpack-plugin-serve based on the named and multiple entry point configurations

Your Proposal for Changes

Provide further examples in that portion of the docs describing the entry point setup, and maybe explain why webpack-plugin-serve/client is needed and what it offers. That with the further example configurations may clear up any configuration questions moving forward

vote: unix socket support

Please vote for this feature by using the Github Reactions button and the 👍 reaction. When this feature reaches 10 votes, it will be implemented.

Feature Use Case

const { createServer } = require('http');

const unixSocket = '/opt/tmp/.socket';
const server = createServer(...);

server.listen(unixSocket, () => { ... });

Feature Proposal

Proposed socket options property. This property will override (and discard) any host and port combination set in the options.

Serve output.path from output.publicPath

Expected Behavior / Situation

If I set output.publicPath to something other than /, it would be very convenient if the output.path files could be served from this path.

// does not work appropriately
const path = require('path');
// ...
const outputPath = path.join(__dirname, 'build');
module.exports = {
  // ...
  output: {
    path: outputPath,
    publicPath: '/app/',
  },
  static: outputPath,
  // I've tried with the historyFallback
  historyFallback: {
    index: '/app/index.html'
  },
}

Actual Behavior / Situation

Right now, if I set output.publicPath, my build directory must match this, and I must also set the static option as well.

// works
const { path } = require('path');
// ...
const publicPathName = 'app'
const outputPath = path.join(__dirname, publicPathName);
module.exports = {
  // ...
  output: {
    path: outputPath,
    publicPath: `/${publicPathName}/`,
  },
  static: outputPath,
}

Modification Proposal

I understand that this works because by default this plugin will serve files from the current working directory. However, it would be much more convenient to resolve the public path as well, since publicPath is appended to the urls in html-webpack-plugin, and this seems to happen in other webpack references as well.

This works brilliantly with webpack-serve here, and I'd love for it to work with this plugin as well.

Let me know if you're open to supporting this; if that's not the case, would webpack-dev-middleware be a feasible thing for me to mix into this plugin manually?

vote: add option to control progress bar vanish timeout

First of all, this package is fantastic. Great work, and thank you. The progress bar totally helps with a huge problem with webpack HMR... you just don't trust it and/or know when it has reloaded. It's great. That said...

Expected Behavior / Situation

I'd like to be able to see my full page immediately after an HMR and use the larger progress bar. The small one is nice, but not quite visible enough.

Actual Behavior / Situation

It takes 5 seconds for the progress bar to disappear, which means if what I'm looking for is obscured by the progress bar I have to wait a whole 5 seconds before I can see it after an HMR.

Modification Proposal

Make it configurable or remove the delay. Personally, I'd probably set it to 0, especially since the HMR seems to happen around 98% for me.

feat: use joi for options validation

Feature Use Case

Options validation is a good thing. We can reasonably assert the accepted values for plugin-specific options, and reasonably predict the general shape of pass-through (to third party middleware/modules) options.

Feature Proposal

I'd like to use joi, which is expressive and far more elegant than other options.

Invalid arguments: hostname must be a string or falsey

  • Webpack Version: 4.26.1
  • Operating System (or Browser): mac os x
  • Node Version: 10.14.0
  • webpack-plugin-dev Version: 0.1.1

How Do We Reproduce?

    new WebpackPluginServe({
      host: '0.0.0.0',
      historyFallback: true,
      static: path.join(__dirname, 'public'),
    }),

Expected Behavior

No errors

Actual Behavior

⬡ webpack: Watching Files
[HPM] Proxy created: reqPath => ...
⬢ webpack: TypeError: Invalid arguments: hostname must be a string or falsey
    at Object.lookup (dns.js:130:11)
    at lookupAndListen (net.js:1500:7)
    at Server.listen (net.js:1476:7)
    at WebpackPluginServe.start (/Users/.../node_modules/webpack-plugin-serve/lib/server.js:77:10)
    at <anonymous>
    at process._tickCallback (internal/process/next_tick.js:188:7)
    at Function.Module.runMain (module.js:695:11)
    at startup (bootstrap_node.js:191:16)
    at bootstrap_node.js:612:3
(node:72755) ExperimentalWarning: The http2 module is an experimental API.
error Command failed with exit code 1.

Support attempting automatic reconnection

Feature Use Case

When I restart the server to apply new changes, I currently have to refresh the page manually; this means having to change focus from my IDE to my browser, which is annoying when fiddling with the development servers configuration.

Feature Proposal

The client makes a series of attempts to reconnect via websocket to the development server, over a period of intervals, before giving up.

This is a feature currently done by webpack-dev-middleware. While it's not the nicest thing to have, as it results in unavoidable console spam (as most browsers log failed ws connection attempts as security messages, meaning they're not visible nor surpressable by JS), I feel it's a justifiable enough feature, since the console is usually cleared on page reloading anyway.

running multiple instances at the same time

Hi,

I have a question. My use case:

We have a webapp that has end-to-end tests performed via Selenium. We often want to run two instances of Webpack: one for development, one for end-to-end tests, with different bundles. I can run them in parallel on two different ports, but I face the issue that whatever instance is launched last ends up serving its own bundle on both ports for some reason.

Am I clear enough? If so, is it something you're aware of?

recipe: server-side rendering

Documentation Is:

  • Missing
  • Needed
  • Confusing
  • Not Sure?

Please Explain in Detail...

Our server-side rendered app uses webpack to build bundles for both client and server (via multicompiler). Currently we're using https://github.com/60frames/webpack-hot-server-middleware for smooth DX. Code is being hot-reloaded on both client and server. Is this something that can be achieved using webpack-plugin-serve?

Your Proposal for Changes

docs: add entry in usage

Documentation Is:

  • Missing
  • Needed
  • Confusing
  • Not Sure?

Please Explain in Detail...

We need to add the entry file to the Usage section

Your Proposal for Changes

liveReload: page not reloading

  • Webpack Version: 4.17.1
  • Operating System (or Browser): Fedora 29, Chrome 71
  • Node Version: 10.13.0
  • webpack-plugin-serve Version: 0.2.2

How Do We Reproduce?

I can't seem to get the browser to reload after a build. here's the branch and dir of the app. all I'm doing to test this is an alert change in index.js,

https://github.com/jimfrenette/uiCookbook/tree/wp-plugin-serve/sidebars

Expected Behavior

Reload the page when a build finishes

Actual Behavior

Note this is my first attempt at using this plugin instead of webpack-dev-server. No errors are being output and the app does build, just not getting a page reload as expected.
Works as expected in master branch using the old webpack-dev-server:

https://github.com/jimfrenette/uiCookbook/tree/master/sidebars

Open and no host redirecting to weird url

  • Webpack Version: 4.23.1
  • Operating System (or Browser): google-chrome/ubuntu LTS
  • Node Version: 10.11.0
  • webpack-plugin-dev Version: 0.0.1

How Do We Reproduce?

new Serve.WebpackPluginServe({
      port: () => 7001,
      historyFallback: true,
      open: true
    }),

Browser opens on http://[::]:7001/

Expected Behavior

open on a "normal" url?? Maybe localhost??

Actual Behavior

Browser opens on http://[::]:7001/

FAQ - leak comparison

I read the medium post and docs listed here: #48

Regarding the leaks in webpack-dev-server webpack/webpack#6929, is this plugin taking a different approach than webpack-dev-server with HMR or should I expect the same leaks due to upstream dependencies?

Any impetus for me to switch at this point is:

  1. memory leak/crash (both with storybook and our app's webpack.config) - really painful
  2. any speed improvements

Do I have any hope looking here for a resolution?

recipes: common code patterns for users

We should create a directory of recipes for users that demonstrate common code patterns. Recipes could include:

  • using proxy
  • using a local IP address for the host (via internal-ip)
  • using a dynamic port number (via get-port)
  • bonjour broadcasting
  • watching static content and reloading

Support Node v8

Expected Behavior / Situation

n/a

Actual Behavior / Situation

webpack-plugin-serve doesn't support Node v8 at the moment. Node v10 is Active LTS now, but there are a lot of people that can't move to v10 yet.

Modification Proposal

Can we support Node v8?

Error on page reload

  • Webpack Version: 4.27.1
  • Operating System (or Browser): mac os sierra
  • Node Version: 8.12
  • webpack-plugin-serve Version: 0.2.2

How Do We Reproduce?

Expected Behavior

Not error on reload

Actual Behavior

image

faq: talk about `static` and `not found`

Documentation Is:

  • Missing
  • Needed
  • Confusing
  • Not Sure?

Please Explain in Detail...

Need to add to FAQ:

  • a section to when user saw a "not found" similar to what sibelius saw
  • explain the static option values, what should be the "preferable" value.

Your Proposal for Changes

vote: make underlying server lib replaceable

Please vote for this feature by using the Github Reactions button and the 👍 reaction. When this feature reaches 70 votes, it will be reconsidered.


I have a feeling that this is a "won't fix", but still...

Feature Use Case

It's a best practice to have local dev and prod setups as similar as possible. So, if we are using express or hapi as our production server (with different middlewares, sessions, authorization logic etc.), it's quite strange to implement the same server logic with koa for local development.

Feature Proposal

Have no idea what's the best way to implement it.

cheap-module-source-map bug

  • Webpack Version: 4.27.1
  • Operating System (or Browser): macOS Mojave
  • Node Version: 10.13
  • webpack-plugin-serve Version: 0.2.2

How Do We Reproduce?

  1. Use react example in recipes folder of this repo
  2. Change webpack config devtool to cheap-module-source-map value
  3. Run server and change some code for hot reload

Expected Behavior

server should work

Actual Behavior

server stops on error

/Users/a/repos/github/webpack-plugin-serve/recipes/react/node_modules/webpack/lib/SourceMapDevToolPlugin.js:36
        if (asset.sourceAndMap) {
                  ^

TypeError: Cannot read property 'sourceAndMap' of undefined
    at getTaskForFile (/Users/a/repos/github/webpack-plugin-serve/recipes/react/node_modules/webpack/lib/SourceMapDevToolPlugin.js:36:12)
    at files.forEach (/Users/a/repos/github/webpack-plugin-serve/recipes/react/node_modules/webpack/lib/SourceMapDevToolPlugin.js:136:20)
    at Array.forEach (<anonymous>)
    at compilation.hooks.afterOptimizeChunkAssets.tap (/Users/a/repos/github/webpack-plugin-serve/recipes/react/node_modules/webpack/lib/SourceMapDevToolPlugin.js:130:12)
    at SyncHook.eval [as call] (eval at create (/Users/a/repos/github/webpack-plugin-serve/recipes/react/node_modules/tapable/lib/HookCodeFactory.js:19:10), <anonymous>:14:1)
    at SyncHook.lazyCompileHook (/Users/a/repos/github/webpack-plugin-serve/recipes/react/node_modules/tapable/lib/Hook.js:154:20)
    at hooks.optimizeChunkAssets.callAsync.err (/Users/a/repos/github/webpack-plugin-serve/recipes/react/node_modules/webpack/lib/Compilation.js:1313:42)
    at AsyncSeriesHook.eval [as callAsync] (eval at create (/Users/a/repos/github/webpack-plugin-serve/recipes/react/node_modules/tapable/lib/HookCodeFactory.js:32:10), <anonymous>:10:1)
    at AsyncSeriesHook.lazyCompileHook (/Users/a/repos/github/webpack-plugin-serve/recipes/react/node_modules/tapable/lib/Hook.js:154:20)
    at hooks.additionalAssets.callAsync.err (/Users/a/repos/github/webpack-plugin-serve/recipes/react/node_modules/webpack/lib/Compilation.js:1309:36)
error Command failed with exit code 1.

Absolute position wps-status

Expected Behavior / Situation

Build warnings & errors are visible on top of page content.

Actual Behavior / Situation

Build warnings & errors are pushed to the bottom of the page, when there is a large amount of content on the page, and in some cases even hidden (when things like modals are open).

Modification Proposal

Currently the wps-status overlay sits inline with the rest of the page. This means it can be pushed around by the rest of the page, which can result (in particular) in it pushed out of sight.

It would make sense for the overlay to be absolutely positioned, so that it 'hovers' above the entire page. This is usually how build status overlays are done in the other webpack build tools, and (I think) makes sense given that you can minimise the overlay, and wps-status-beacon is already absolutely positioned.

Compile files in-memory, not in dist of workdir

Expected Behavior / Situation

In development mode, all that I need is a server which somehow gives me good DX for work on the project. Don't see any benefits of dist folder in project root in dev mode.

Actual Behavior / Situation

Now wps create dist folder at the project root. Many projects using this folder for their production builds, I think this creates some confuse.

Modification Proposal

Keep dev builds in-memory or hidden folder that should destroy after each server stop.

webpack-plugin-serve/client is wrongly transpiled with babel

  • Webpack Version: 4.27.1
  • Operating System (or Browser): mac os sierra
  • Node Version: 8.12
  • webpack-plugin-serve Version: 0.2.2

How Do We Reproduce?

Expected Behavior

webpack-plugin-serve/client should not be touched by babel loader if node_modules are excluded

Actual Behavior

webpack-plugin-serve/client is tranpiled by babel loader even with exclude: /node_modules/

Allow resolution of .html files when no extension is requested

Feature Use Case

Client-side rendered apps break when file extensions such as .html are present on the URL. I would like to be able to request a route, /account/test for example, and have webpack-plugin-serve resolve to /account/test.html (if the corresponding html file is present) without changing the URL on the client (i.e. no redirect). It seems the included koa-static middleware allows for this through an options setting 'extensions', which is an array of file extensions to be resolved by koa. I believe the pattern looks like this:

{ extensions: [ '.html', '.htm'] }

(honestly, it's unclear to me if the leading period is needed)

Feature Proposal

Please allow for requesting routes without file-extensions which successfully resolve to matching filenames containing specified extensions (or even allowing the behavior for .html files by default). Ideally, this would happen without altering the URL on the client.

Example:
a /dist directory has been specified as a static path to resolve from site-root, all files are contained within that directory. within that directory is another directory named account. within the account directory is a file named test.html.

Browser requests: /account/test
webpack-plugin-serve finds file: /account/test.html
WPS returns the contents of the .html file at route /account/test.

Perhaps the most straightforward way to allow for this would be to provide a place to pass options into koa-static along with filesystem paths to resolve?

Thank you!

mod: client entry duplicate guards

Expected Behavior / Situation

I haven't checked yet, but it occurs to me that all scripts which are potential client entrypoints need guards against multiple entries being loaded.

Actual Behavior / Situation

Unsure, might already be handled.

Possible scenario: someone manually adds a status overlay entry, and the plugin itself adds the entry manually, resulting in two status overlay entries for a build. The overlay script could run twice, creating two status dialogs at the same time. Could be other potential issues.

Modification Proposal

Scripts should set a variable on window to indicate that the script has already been loaded once in another context, display a warning in the console, and return without executing.

feat: liveReload

Feature Use Case

There will be setups (like a from-scratch Angular app) that doesn't have HMR enabled. In that situation it'd be valuable to provide the option of reloading the page. This isn't something I wanted to implement until we had a reason, but I think that's a valid use-case.

Feature Proposal

add liveReload option, which reloads the page when a build finishes. (Note: Rollup will use this once the plugin is abstracted)

Serve same index.html for all requests beneath a declared route

Documentation Is:

  • Missing
  • Needed
  • Confusing
  • Not Sure?

Please Explain in Detail...

First off, this is probably me lacking understanding in how to tie Koa middleware in properly, please close if this request is inappropriate in this forum.

I am working on a feature branch that is a React application. All URL paths under /account are controlled by Reach Router. Currently, I have to explicitly create .html files for every path in the application underneath the /account path for them to be served properly by the webpack-plugin-serve server.

I would like to have a physical file /account/index.html that is served for any request at /account/* without altering the requesting URL. Example: if during development I hit the development server at /account, or /account/welcome, or /account/overview or /account/overview/detail/1234 each request would serve /account/index.html while the client maintains the requested path.

Normally, when developing a Koa server I would just set up a router.get('/account/*') route but am unclear how to successfully accomplish this within the confines of WPS. (this is an example of the difficulties in co-locating server needs with client needs I mentioned in another issue)

Your Proposal for Changes

Please detail how to accomplish, for lack of a better term, virtual path mapping in WPS if it is possible?

Comparison to webpack-dev-server

Thanks for your work, I love seeing competing solutions that mix up a space. Can you please provide a comparison to webpack-dev-server? What are your value props over the existing solution?

HMR broken with historyFallback in Firefox

  • Webpack Version: 4.23.1
  • Operating System (or Browser): Linux Mint 18.2 Cinammon 64-bit (Firefox 65.0 and 64.0.2)
  • Node Version: 11.3.0
  • webpack-plugin-serve Version: 0.4.0

How Do We Reproduce?

With the given Firefox versions, run the react recipe in this repo.

Expected Behavior

HMR works as expected with historyFallback on Firefox. This is especially important if I'm developing an app that relies on something like https://github.com/ReactTraining/react-router for SPA purposes.

Actual Behavior

Notice in the console that the following error occurs: Firefox can’t establish a connection to the server at ws://[::]:55555/wps..

Now kill the start script, remove the historyFallback option and restart. The bug now should be fixed.

Note that this problem does not exist on current versions of Chrome/Chromium.

Support MultiCompilers

Feature Use Case

Serving a project that has both target: 'web' and target: 'webworker' e.g.

webpack.config.js

module.exports = [
  { 
    entry: 'web.js',
    target: 'web'
  },
  {
    entry: 'worker.js',
    target: 'webworker'
  }
]

Feature Proposal

Documenting how this could might be possible.

Adding custom headers

webpack-dev-server and webpack-serve supported adding custom headers. Have I overlooked something or is this not supported here?

Thank you in advance.

Bundles are rebuilt on every load when using "production" mode

  • Webpack Version: 4.28.4
  • Operating System (or Browser): MacOS 10.14.3
  • Node Version: v11.6.0
  • webpack-plugin-serve Version: 0.4.0

How Do We Reproduce?

When I try to use webpack-plugin-serve with "mode": "production" in my webpack config, I'm seeing a strange behavior. Everytime I refresh my page in the browser, webpack rebuilds the entire production build before it gets served. This means that refreshing the page takes several seconds (in my case).

When using "mode": "development" this doesn't seem to happen (or it happens so fast that I can't notice this anymore).

Expected Behavior

The files should be built once, and the re-served on every page refresh.

Actual Behavior

Everytime I refresh the page, webpack rebuilds my entire bundle set making reloads extremely slow.

Ensure wps-status indicators are always top z-index on page

Feature Use Case

Current problem: Using WPS on a legacy codebase where I'm switching the build over from gulp. Legacy codebase has styles I cannot safely alter without triggering full-scale regression testing. If the z-index is too high on an element (the top-nav in my case), the wps-status indicator is hidden from view.

See attached animated gif.
wps-progress-indicator

Feature Proposal

One of two options come to mind:

Setting the z-index of the WPS progress widget(s) to the max allowed z-index of 2147483647 (StackOverflow answer on max z-index)

OR

Dynamically find highest z-index on the page post-render and add 1 to that number for the progress widget(s). (Find highest z-index)

vote: custom headers option support

Please vote for this feature by using the Github Reactions button and the 👍 reaction. When this feature reaches 10 votes, it will be implemented.

Feature Use Case

Users may need the ability to specify custom request headers frequently enough to warrant a formal option for defining them quickly and easily. At present, custom headers can be defined by following the method described in #36.

Feature Proposal

Proposed headers options property. This property will specify headers in a key-value set from which the server will add headers to every request.

new WebpackPluginServe({
  headers: {
    'X-Superhero': 'batman'
  }
})

HMR issues

First of, great project, hands down I has the least issues with setting this up as opposed to webpack-dev-server / webpack-serve. Both failed at some point when using things like HTTPS and multiple windows.
The only two issues I had was the me understanding that I needed to add the webpack-plugin-serve client script to my entry points. And the fact that the default was to use IPv6 while this was disabled on my machine, so the page refused to load etc. After I set the host to localhost and added the client scripts to the entrypoints it worked like a charm. Very nice. The added progress bar is such a nice touch, I never knew I missed it until now.

I do have some questions however:
One thing that absolutely never worked for me was HMR and I always ended up using liveReload, So I thought, let's have a try with this plugin. After I turned liveReload off and applied a change to my sources the an error message in the browser's console, I will post it below along with the webpack.config.js etc. Do mind that I didn't change a thing in the monaco editor, so I think it is just the behavior of the manaco webpack plugin, but I am not sure.

One other thing is that the async errors from ATL (Awesome-Typescript-Loader) CheckerPlugin do not get shown in a status window, I don't know if that is the expected behavior or not, but it would be nice if they did. Maybe they do when HMR works.

The last thing is probably a bug. When setting HMR to false and liveReload to true I will get an error message about __webpack_hash__ not defined when loading the page. I will add the full error below.

webpack.config.js
Note: isDev and therefor isDevServer are both true

var webpack = require("webpack");
const path = require("path");
var MiniCssExtractPlugin = require("mini-css-extract-plugin");
var atl = require("awesome-typescript-loader");
let CircularDependencyPlugin = require("circular-dependency-plugin");
const UglifyJsPlugin = require("uglifyjs-webpack-plugin");
const fs = require("fs");
const MonacoWebpackPlugin = require("monaco-editor-webpack-plugin");
const GitRevisionPlugin = require("git-revision-webpack-plugin");
const { WebpackPluginServe: Serve } = require("webpack-plugin-serve");
var gitRevisionPlugin = new GitRevisionPlugin();

var extractCss = new MiniCssExtractPlugin({
    filename: "[name].css",
});

let mode = process.env.NODE_ENV || "development";
const isDev = mode === "development";
const isDevServer = isDev && !process.env.NO_SERVE;

console.log(!isDevServer ? "[Webpack.config.js] IS_DEV_SERVER" : "[Webpack.config.js] COMPILE");
const authUrl = process.env.AUTH_URL || (isDev ? "https://domain.com/auth/" : "/auth/");
console.log("[Webpack.config.js] AUTH_URL: " + authUrl);

const options = {
    https: {
        key: fs.readFileSync(__dirname + "/ssl/localhost.key"),
        cert: fs.readFileSync(__dirname + "/ssl/localhost.crt"),
        ca: fs.readFileSync(__dirname + "/ssl/ca.crt"),
    },
    host: "localhost",
    progress: "minimal",
    port: 8080,
    hmr: true,
    liveReload: false,
};

const entryPoints = {
    gof: ["./src/app.ts"],
    style: ["./style/index.js"],
};

const plugins = [
    new webpack.DefinePlugin({
        AUTH_URL: JSON.stringify(authUrl),
        VERSION: JSON.stringify(gitRevisionPlugin.version()),
        COMMITHASH: JSON.stringify(gitRevisionPlugin.commithash()),
        BRANCH: JSON.stringify(gitRevisionPlugin.branch()),
    }),
    extractCss,
    new atl.CheckerPlugin(),
    new CircularDependencyPlugin({
        // exclude detection of files based on a RegExp
        exclude: /a\.js|node_modules/,
        // add errors to webpack instead of warnings
        failOnError: true,
    }),
    new MonacoWebpackPlugin(),
    // new webpack.optimize.UglifyJsPlugin({ output: {comments: false} }),
    // new webpack.optimize.OccurenceOrderPlugin()
];

if (isDevServer) {
    entryPoints.gof.push("webpack-plugin-serve/client");
    entryPoints.style.push("webpack-plugin-serve/client");

    plugins.push(new Serve(options));
}
module.exports = {
    mode: isDevServer ? "development" : "production",
    entry: entryPoints,
    target: "web",
    devtool: isDevServer ? "cheap-module-eval-source-map" : undefined,
    output: {
        publicPath: "/dist/",
        path: path.resolve(__dirname, "dist"),
        filename: "[name].js",
    },
    performance: { hints: false },
    watch: isDevServer,
    resolve: {
        extensions: [".ts", ".js", ".css", ".less"],
    },
    module: {
        rules: [
            {
                test: /\.tsx?$/,
                include: [path.resolve(__dirname, "src")],
                loader: "awesome-typescript-loader",
                options: {
                    useCache: true,
                    usePrecompiledFiles: true,
                    forceIsolatedModules: true,
                    reportFiles: ["src/**/*.ts"],
                },
            },
            {
                test: /\.less$/,
                include: [path.resolve(__dirname, "style")],
                use: [
                    MiniCssExtractPlugin.loader,
                    {
                        loader: "css-loader",
                        options: {
                            sourceMap: true,
                        },
                    },
                    {
                        loader: "less-loader",
                        options: {
                            sourceMap: true,
                        },
                    },
                ],
            },
            {
                test: /\.(png|jpg|cur|woff|woff2|ttf|svg|gif)$/,
                use: {
                    loader: "url-loader",
                    options: {
                        limit: "100",
                        name: "[path][name].[ext]",
                    },
                },
            },
            {
                test: /\.css$/,
                use: ["style-loader", "css-loader"],
            },
        ],
    },
    optimization: !isDevServer
        ? {
              minimizer: [
                  new UglifyJsPlugin({
                      cache: true,
                      parallel: true,
                      uglifyOptions: {
                          ecma: 6,
                          mangle: true,
                      },
                  }),
              ],
          }
        : undefined,
    plugins: plugins,
};

Error message for HMR monaco issue

Uncaught (in promise) Error: Aborted because ./node_modules/monaco-editor/esm/vs/basic-languages/monaco.contribution.js is not accepted
Update propagation: ./node_modules/monaco-editor/esm/vs/basic-languages/monaco.contribution.js -> ./node_modules/monaco-editor/esm/vs/editor/editor.main.js -> ./include-loader!./node_modules/monaco-editor/esm/vs/editor/editor.main.js -> ./src/designers/customEditors/functionEditor.ts -> ./src/designers sync recursive \.ts$ -> ./src/imports.ts -> ./src/app.ts -> 0
    at hotApply (gof.js:506)
    at replace (hmr.js?797c:60)
hotApply @ gof.js:506
replace @ hmr.js?797c:60
async function (async)
replace @ hmr.js?797c:47
socket.addEventListener @ client.js?a662:67

Error message for HMR : false, liveReload: true

Uncaught ReferenceError: __webpack_hash__ is not defined
    at eval (client.js?1382:19)
    at eval (client.js?1382:20)
    at Object../node_modules/webpack-plugin-serve/client.js (gof.js:15512)
    at __webpack_require__ (gof.js:64)
    at Object.0 (gof.js:18368)
    at __webpack_require__ (gof.js:64)
    at gof.js:197
    at gof.js:200
(anonymous) @ client.js?1382:19
(anonymous) @ client.js?1382:20
./node_modules/webpack-plugin-serve/client.js @ gof.js:15512
__webpack_require__ @ gof.js:64
0 @ gof.js:18368
__webpack_require__ @ gof.js:64
(anonymous) @ gof.js:197
(anonymous) @ gof.js:200

Keep a CHANGELOG

Documentation Is:

  • Missing
  • Needed
  • Confusing
  • Not Sure?

Please Explain in Detail...

Changelogs are useful for knowing what changed in a... log?

But seriously: It's be awesome if a changelog was used to track changes between releases, as it makes things easier for developers to find out what to expect when comparing versions, without having to read through all the commit logs.

Your Proposal for Changes

Keep a Changelog

bug: navigating from 0.0.0.0 to localhost before build done

I think this happens because the websocket is not ready yet

Error: WebSocket is not open: readyState 2 (CLOSING)
    at WebSocket.send (/Users/sibelius/Dev/app/app/app-admin/packages/webpack-plugin-serve/node_modules/ws/lib/websocket.js:314:19)
    at WebpackPluginServe.socket.progress.data (/Users/sibelius/Dev/app/app/app-admin/packages/webpack-plugin-serve/lib/routes.js:78:16)
    at Object.apply (/Users/sibelius/Dev/app/app/app-admin/node_modules/harmony-reflect/reflect.js:2064:37)
    at WebpackPluginServe.emit (events.js:182:13)
    at ProgressPlugin (/Users/sibelius/Dev/app/app/app-admin/packages/webpack-plugin-serve/lib/index.js:130:16)
    at update (/Users/sibelius/Dev/app/app/app-admin/packages/webpack-plugin-serve/node_modules/webpack/lib/ProgressPlugin.js:103:5)
    at moduleDone (/Users/sibelius/Dev/app/app/app-admin/packages/webpack-plugin-serve/node_modules/webpack/lib/ProgressPlugin.js:119:5)
    at SyncHook.eval [as call] (eval at create (/Users/sibelius/Dev/app/app/app-admin/node_modules/tapable/lib/HookCodeFactory.js:19:10), <anonymous>:9:1)
    at module.build.error (/Users/sibelius/Dev/app/app/app-admin/node_modules/webpack/lib/Compilation.js:668:30)
    at handleParseError (/Users/sibelius/Dev/app/app/app-admin/node_modules/webpack/lib/NormalModule.js:435:12)
    at doBuild.err (/Users/sibelius/Dev/app/app/app-admin/node_modules/webpack/lib/NormalModule.js:466:5)
    at runLoaders (/Users/sibelius/Dev/app/app/app-admin/node_modules/webpack/lib/NormalModule.js:327:12)
    at /Users/sibelius/Dev/app/app/app-admin/node_modules/loader-runner/lib/LoaderRunner.js:370:3
    at iterateNormalLoaders (/Users/sibelius/Dev/app/app/app-admin/node_modules/loader-runner/lib/LoaderRunner.js:211:10)
    at Array.<anonymous> (/Users/sibelius/Dev/app/app/app-admin/node_modules/loader-runner/lib/LoaderRunner.js:202:4)
    at Storage.finished (/Users/sibelius/Dev/app/app/app-admin/node_modules/enhanced-resolve/lib/CachedInputFileSystem.js:43:16)
    at provider (/Users/sibelius/Dev/app/app/app-admin/node_modules/enhanced-resolve/lib/CachedInputFileSystem.js:79:9)
    at /Users/sibelius/Dev/app/app/app-admin/node_modules/graceful-fs/graceful-fs.js:78:16
    at FSReqWrap.readFileAfterClose [as oncomplete] (internal/fs/read_file_context.js:53:3)

Logging issues on HMR accept

  • Webpack Version: 4.29
  • Operating System (or Browser): Chrome 71
  • Node Version: 11.6.0
  • webpack-plugin-serve Version: 0.5.0

How Do We Reproduce?

webpack.config.js

const { WebpackPluginServe } = require('webpack-plugin-serve')
const HtmlWebpackPlugin = require('html-webpack-plugin')
const path = require('path')

const outputDir = path.resolve(process.cwd(), 'dist')

module.exports = {
  mode: 'development',
  entry: [path.resolve(__dirname, 'src'), 'webpack-plugin-serve/client'],
  output: {
    path: outputDir,
    filename: 'bundle.js',
    publicPath: '/',
  },
  module: {
    rules: [
      {
        test: /\.tsx?$/,
        exclude: /node_modules/,
        loader: 'babel-loader',
        options: {
          cacheDirectory: true,
        },
      },
    ],
  },
  plugins: [
    new WebpackPluginServe({
      static: outputDir,
      progress: 'minimal',
    }),
    new HtmlWebpackPlugin({
      template: path.resolve(__dirname, 'template.html'),
    }),
  ],
  watch: true,
  resolve: {
    extensions: ['.js', '.jsx', '.json', '.tsx', '.ts'],
  },
}

src/index.ts

console.log('Hello')

if (module.hot) {
  module.hot.accept()
}

Expected Behavior

No error? My guess is it's something to do with with lib/client/hmr.js on line 11:

const { error, info, refresh, warn } = require('./log');

should be?

const { error, info, refresh, warn } = require('./log').log;

My guess is that { silent } in client is failing this way as well.

Actual Behavior

Modify console.log('Hello') to anything else and you get the error:
Uncaught (in promise) TypeError: info is not a function at replace (webpack:///(:55555/webpack)-plugin-serve/lib/client/hmr.js?:64:7)

Allow users to specify a page to open after build is complete

Feature Use Case

For some idiosyncratic reasons, I'd like my browser to open 'http://[::]:5555/#/local' after the build is complete instead of 'http://[::]:5555'. However, open.target isn't currently supported in the config.

Feature Proposal

Allow users to specify a custom path to open once build is complete. The value should probably live at config.open.target and gets passed onto opn in lib/server.js:100

Receiving "Uncaught ReferenceError: ʎɐɹɔosǝʌɹǝs is not defined" in production build

  • Webpack Version: 4.29.0
  • Operating System (or Browser): macOS Mojave
  • Node Version: 10.13.0
  • webpack-plugin-serve Version: 0.4.0

How Do We Reproduce?

Standard webpack build, the following configuration:

plugs.push(new Serve({
		hmr: true,
		historyFallback: true,
		open: true,
		port: 9000,
		status: true,
		middleware: (app, builtins) => {
			const koaStaticOpts = {
				extensions: ['.html', '.htm']
			};
			builtins.static([path.join(ROOT_DIR, 'stub'), path.join(ROOT_DIR, 'dist')], koaStaticOpts)
		}
	}));

then I run my build command from package.json:

cross-env npx wp --mode production --site SITENAME --progress
// side-note: the --progress flag doesn't work either but that's not what i'm reporting here

Expected Behavior

the production build to be free of all references to/code around WPS or any variables output by it gracefully handled to prevent ReferenceErrors.

I tried hiding the "plugs.push" call behind a "if production" flag but was receiving a webpack_hash is undefined error. Upon removing that I got the error I am now seeing.

Actual Behavior

It would seem that WPS is being included in the production bundle. It also looks like, despite the production flag being set, that React Hot Loader is also still being looked for/called (see screenshot). Not sure what's going on but it was my understanding that React Hot Loader and WPS no-op altogether when built to production.

screen shot 2019-01-22 at 2 13 46 pm

clientside error when hmr is false: Cannot destructure property `apply` of 'undefined' or 'null'.

When hmr option is false, an error occurs clientside.

  • Webpack Version: v4.26.1
  • Operating System (or Browser): Windows 10, Chrome 71.0.3578.80
  • Node Version: v10.14.1
  • webpack-plugin-dev Version: v0.1.2

How Do We Reproduce?

https://github.com/G-Rath/js-bugs/tree/webpack-plugin-serve/hmr-false-bug

Expected Behavior

No errors in console.

Actual Behavior

Errors in console:

client-hmr.js:13 Uncaught TypeError: Cannot destructure property `apply` of 'undefined' or 'null'.
    at Object.eval (webpack:///(:55555/webpack)-plugin-serve/lib/client-hmr.js?:13:41)
    at eval (webpack:///(:55555/webpack)-plugin-serve/lib/client-hmr.js?:61:30)
    at Object../node_modules/webpack-plugin-serve/lib/client-hmr.js (output.js:129)
    at __webpack_require__ (output.js:20)
    at eval (webpack:///(:55555/webpack)-plugin-serve/lib/client.js?:11:21)
    at Object../node_modules/webpack-plugin-serve/lib/client.js (output.js:151)
    at __webpack_require__ (output.js:20)
    at eval (webpack:///(:55555/webpack)-plugin-serve/client.js?:24:3)
    at eval (webpack:///(:55555/webpack)-plugin-serve/client.js?:25:3)
    at Object../node_modules/webpack-plugin-serve/client.js (output.js:118)

Enable node 11 support?

Expected Behavior / Situation

Support for node 11 in engines.

Per this comment from the related node regression (as mentioned in the FAQ), it seems node 11 shouldn't be affected.

Actual Behavior / Situation

Node 11 not supported, so yarn users unable to use without --ignore-engines (which causes headaches that are yarn's fault).

Modification Proposal

  "engines": {
    "node": ">= 8.0.0 < 9.0.0 || >= 10.0.0 < 10.14.0 || >= 11.0.0"
  },

(Add >= 11.0.0 to engines)

Provide a way to silence "wps: Build 18adad2 replaced:" messages

Expected Behavior / Situation

It would be good to keep the browser developer console clear of any webpack-plugin-serve noise.

Actual Behavior / Situation

Currently, the console is updated with a message saying "wps: Build 18adad2 replaced:" on every HMR update. This can get very noisy and clutter the development console.

Modification Proposal

Could we add some flag to webpack-plugin-serve to disable these update messages?

Refreshing the page causes ERR_STREAM_WRITE_AFTER_END error

When refreshing the page with hmr enabled (and connected via websocket to the serve server), an exception is logged to the webpack console.

This doesn't actually stop anything from working.

  • Webpack Version: v4.26.1
  • Operating System (or Browser): Windows 10, Chrome 71.0.3578.80
  • Node Version: v10.14.1
  • webpack-plugin-dev Version: v0.1.2

How Do We Reproduce?

https://github.com/G-Rath/js-bugs/tree/base/webpack-plugin-serve

Expected Behavior

No errors in webpack console when refreshing page.

Actual Behavior

Error is logged:

Error [ERR_STREAM_WRITE_AFTER_END]: write after end
      at writeAfterEnd (_stream_writable.js:243:12)
      at Socket.Writable.write (_stream_writable.js:291:5)
      at Sender.sendFrame (C:\Users\G-Rath\workspace\projects-personal\js-bugs\node_modules\ws\lib\sender.js:404:20)
      at Sender.doClose (C:\Users\G-Rath\workspace\projects-personal\js-bugs\node_modules\ws\lib\sender.js:141:10)
      at Sender.close (C:\Users\G-Rath\workspace\projects-personal\js-bugs\node_modules\ws\lib\sender.js:128:12)
      at WebSocket.close (C:\Users\G-Rath\workspace\projects-personal\js-bugs\node_modules\ws\lib\websocket.js:215:18)
      at Receiver.receiverOnConclude (C:\Users\G-Rath\workspace\projects-personal\js-bugs\node_modules\ws\lib\websocket.js:695:32)
      at Receiver.emit (events.js:182:13)
      at Receiver.controlMessage (C:\Users\G-Rath\workspace\projects-personal\js-bugs\node_modules\ws\lib\receiver.js:436:14)
      at Receiver.getData (C:\Users\G-Rath\workspace\projects-personal\js-bugs\node_modules\ws\lib\receiver.js:330:42)

Socket errors during recompile

  • Webpack Version: "4.28.4
  • Operating System (or Browser): MacOS v10.14.2
  • Node Version: v11.6.0
  • webpack-plugin-serve Version: 2.0.3

How Do We Reproduce?

Currently these crashes seem to happen at random when saving files or switching between branches but webpack-plugin-serve crashes hard during recompiling.

Expected Behavior

That webpack-serve-plugin would recompiled the code and force a browser refresh.

Actual Behavior

webpack-serve-plugin crashes during recompilation with the following error stack

⬡ wps: Server Listening on: http://192.168.86.130:8083

✓ App bundle compiled
^[^[✓ App bundle compiled
node_modules/ws/lib/websocket.js:328
      throw err;
      ^

Error: WebSocket is not open: readyState 2 (CLOSING)
    at WebSocket.send (node_modules/ws/lib/websocket.js:322:19)                                                                                              
    at WebpackPluginServe.socket.progress (node_modules/webpack-plugin-serve/lib/routes.js:85:16)                                                            
    at WebpackPluginServe.emit (events.js:188:13)
    at ProgressPlugin (ode_modules/webpack-plugin-serve/lib/index.js:197:16)                                                                                
    at Object.call (node_modules/webpack/lib/ProgressPlugin.js:304:6)                                                                                        
    at AsyncSeriesHook.eval [as callAsync] (eval at create (node_modules/tapable/lib/HookCodeFactory.js:32:10), <anonymous>:8:18)                            
    at AsyncSeriesHook.lazyCompileHook (node_modules/tapable/lib/Hook.js:154:20)                                                                             
    at asyncLib.forEach.err (node_modules/webpack/lib/Compiler.js:358:27)                                                                                    
    at node_modules/neo-async/async.js:2825:7
    at done (node_modules/neo-async/async.js:2861:11)
error Command failed with exit code 1.

This is the only part of the crash which seems to be consistent, i.e. this crash complains about a closing socket)

cc: @EvHaus

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.