Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Hot reloading shouldn't stop after an error #1078

Closed
mjhoffm2 opened this issue Oct 8, 2018 · 11 comments

Comments

@mjhoffm2
Copy link

commented Oct 8, 2018

Description

Currently, if there is a compilation error in the code being hot reloaded, I will see an overlay containing information about the errors, as well as a message in the console about these errors. However, after these errors are addressed, hot reloading should continue as normal, but currently isn't.

Expected behavior

When I save a piece of code with an error, then fix the error, I should be able to continue editing and hot reloading my application. This works perfectly fine without using react-hot-loader, and just using webpack-hot-middleware.

function render(rootContainer: JSX.Element) {
    ReactDOM.render(
        <Provider store={store}>
            <ConnectedRouter history={history}>
                {rootContainer}
            </ConnectedRouter>
        </Provider>,
        document.getElementById('root')
    );
}

render(<Routes />);

//configure hot module replacement during development
if(module.hot) {
    module.hot.accept('./routes', () => {
        const NewRoutes = require('./routes').Routes;
        render(<NewRoutes />);
    });
}

image

Actual behavior

What actually happens:

When using react-hot-loader with hot(module)( ... ) in my Routes component, my application is no longer able to hot reload after I fix the error. I see the following:
image

I see the error overlay disappear, but my component does not get updated any more.

Environment

React Hot Loader version: 4.3.11

Run these commands in the project folder and fill in their results:

  1. node -v: v8.10.0
  2. npm -v: 6.4.1

Then, specify:

  1. Operating system: Windows 10
  2. Browser and version: Google Chrome Version 69.0.3497.100 (Official Build) (64-bit)

Reproducible Demo

I can do if necessary

@theKashey

This comment has been minimized.

Copy link
Collaborator

commented Oct 9, 2018

Yeah - it would be great to have a demo.
According to your logs - RHL just didn't setup a new module.hot.accept, and that's strange.

@mjhoffm2

This comment has been minimized.

Copy link
Author

commented Oct 9, 2018

Here is a demo: https://github.com/mjhoffm2/react-demo/tree/2bbdb5bc95e4f322c41ea6ca3150b43309286a81/node

You should just be able to clone it, go to the 'node' folder, run 'npm install' and 'npm run dev'. React Hot Loader seems like it is working just fine until it tries to hot reload something with an error. For example, adding some random words at the bottom of the Counter.tsx component will break it. Things like TypeScript errors are recoverable.

@theKashey theKashey self-assigned this Oct 13, 2018
@theKashey

This comment has been minimized.

Copy link
Collaborator

commented Oct 13, 2018

So - this is actually 3 different things:

  1. ErrorBoundary in AppContainer is doing nothing (unless you set errorReporter), as result - if any error took a place - 💥 , see #811. Probably we need provide some build-in ErrorBoundary.
  2. In this case, after fixing error inside react - everything got broken, as long Application will receive two HMR updated - with error, and without error. Fix - increase timeout in hoc to receive all possible updates.
  3. In case of error out of react code - it will took a place during module execution, and new hot will not be called, and next updates would not be accepted. Patch here is possible, but will require some severe changes in API.

Only .3 is a problem. Here is the proposal how to solve it:

  1. add import 'react-hot-loader/hot' in the beginning of a file.
  2. react-hot-loader/hot would delete itself from a webpack cache(__webpack_require__.c)
  3. setup hot for the parent - __webpack_require__.c[module.parents[0]].hot.accept) using the same hot RHL provides for everyone.
  4. Profit - as long it's a first import - it would be executed in all the cases.
@mattcarlotta

This comment has been minimized.

Copy link

commented Oct 27, 2018

Any updates on this? Would like to implement this into a boilerplate I've built, but with the inability to resume past an error (without a refresh), this module seems rather limited in usage.

@theKashey

This comment has been minimized.

Copy link
Collaborator

commented Oct 27, 2018

Sorry, trying to solve React 16.6 and 16.7 issues first.
Anyway - a lot of fixes will be released soon.

@theKashey

This comment has been minimized.

Copy link
Collaborator

commented Dec 13, 2018

import {hot} from 'react-hot-loader/root'
...
export default hot(MyComponent);// A DIFFERENT API CALL HERE!!

would solve the problem

@mjhoffm2

This comment has been minimized.

Copy link
Author

commented Dec 13, 2018

This works great, thanks!

@MiguelArmendariz

This comment has been minimized.

Copy link

commented May 6, 2019

import {hot} from 'react-hot-loader/root'
...
export default hot(MyComponent);// A DIFFERENT API CALL HERE!!

would solve the problem

This doesn't work for me :C

I first had something like this:

import {hot} from 'react hot loader' ... export default hot(module)(myComponent);

Then I changed it to how you said but it still stops

@theKashey

This comment has been minimized.

Copy link
Collaborator

commented May 6, 2019

/root API is proven to work for webpack only. If it does not work for you - feel free to provide some details to help us understand "why", and "how" to help you.

@MiguelArmendariz

This comment has been minimized.

Copy link

commented May 7, 2019

Well on my dev configuration for wepack I have this for js|jsx files:

 rules: {
        test: /\.(js|jsx)$/,
        exclude: /(node_modules|bower_components)/  //Here I once changed it so I include node_modules
        use: [
            { loader: 'babel-loader', options: { presets: ['@babel/env'] } },
            //Here I added loader: 'react-hot-loader/webpack'. But it said it couldn't be found (after running app)
        ],
    },

In .babelrc file I have:

{
    "presets": ["@babel/env", "@babel/preset-react"],
    "plugins": ["react-hot-loader/babel"]
}

And on the App.js I have this:

import {hot} from 'react-hot-loader/root';
import React....

class App extends Component...

export default hot(App);

But if I have a syntaxis error there and then fix it, the HMR stops, saying that it needs a full reload or something like that.

EDIT: I migrated to this after using hot(module)(App)

@theKashey

This comment has been minimized.

Copy link
Collaborator

commented May 7, 2019

Could you please set a breakpoint at the error location, and try to understand why its throwing the exception. The "old" API was using module.hotfrom the module you provided, a "new" one is accessing yourmoduleviaroot` module "parent", which (according to condition) does not exist)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
4 participants
You can’t perform that action at this time.