catamphetamine / webpack-isomorphic-tools

Server-side rendering for your Webpack-built applications (e.g. React)
MIT License
1.25k stars 48 forks source link

Checksum mismatch #19

Closed mmahalwy closed 8 years ago

mmahalwy commented 8 years ago

Sorry, changed the issue completely as I figured this out. I have this problem now:

Warning: React attempted to reuse markup in a container but the checksum was invalid. This generally means that you are using server rendering and the markup generated on the server was not what the client was expecting. React injected new markup to compensate which works but you have lost many of the benefits of server rendering. Instead, figure out why the markup being generated is different on the client or server:
 (client) 1fzsg6oe4u8.0"><div class="_3M_6s6ONPXQz
 (server) 1fzsg6oe4u8.0"><div data-reactid=".1fzsg

Seems that the server has not loaded the CSS accordingly and my client is doing that work.

catamphetamine commented 8 years ago

Why?

mmahalwy commented 8 years ago

@halt-hammerzeit updated

catamphetamine commented 8 years ago

Why do you think that the server has not loaded the CSS accordingly?

First you should get your markup in the browser and compare it to the markup in the browser with Javascript disabled. Then you'll find this place by searching 1fzsg6oe4u8.0">. And you'll see what's missing

mmahalwy commented 8 years ago

Yeah, the style-loader loads the css on the server side as {} and not until the browser is it then filled with the class _3M_6s6ONPXQz

My scss:

@import '../bootstrap-config';
@import 'node_modules/bootstrap-sass/assets/stylesheets/bootstrap/variables';
:local(.indexHeader){
  background: url('//quran-1f14.kxcdn.com/images/index-bg.jpg') ;
  background-size: cover;

  .nav{
    width: 100%;
    padding: 5px 15px;
...

My component:

const style = require('styles/partials/indexheader.scss');
console.log(style);
class IndexHeader extends React.Component {
  renderSearch() {
...
return (
      <div className={style.indexHeader}>
        <IndexHeaderNav navlink={this.props.navlink} />
...
mmahalwy commented 8 years ago

Okay found the problem. It's super clever :)

I copied your example:

parser: function(m, options, log) {
        options.development = false;
        log.info(m)
        log.info(m.source)
        if (m.source) {
          var regex = options.development ? /exports\.locals = ((.|\n)+);/ : /module\.exports = ((.|\n)+);/;
          var match = m.source.match(regex);
          log.info(match)
          return match ? JSON.parse(match[1]) : {};
        }
      }

Notice I added option.development = false the reason being is, and probably a good idea to note in the readme, that when in develop, it's best to not use ExtractTextPlugin because the module source looks like this: "source": "// removed by extract-text-webpack-plugin\nmodule.exports = {\"indexHeader\":\"_3M_6s6ONPXQzgbxzXhhBx3\"};"

catamphetamine commented 8 years ago

Well, to begin with, that JSON.parse() hack is long time gone now. Where did you get it?

You should use proper parsers. For example, these should work for you https://github.com/erikras/react-redux-universal-hot-example/blob/master/webpack/webpack-isomorphic-tools.js#L64-L96

As far as I know, ExtractTextPlugin is used only in production and there's no sense to use it in development.

mmahalwy commented 8 years ago

Cool ill update my file to match the redux example

mmahalwy commented 8 years ago

thank you sir!