Description
This might be expected behavior- in this case I'd really appreciate explanation for it.
tl;dr;
For SSR parent component render is not triggered if child updates shared state. Client browser renders as expected.
Issue details
we have App.jsx - all it does is adding no-scroll class for container when Modal window is rendered.
// simplified
const mapStateToProps = state => ({
isNoScroll: !state.modal.visible
})
const App = ({children, isNoScroll}) => (
<div className={cx('app__root', {'no-scroll': isNoScroll})}>
{ console.log(`App rendered with ${isNoScroll}` }
{/* rest of stuff*/}
{children}
</div>
)
export default connect(mapStateToProps)(App);
Modal is using componentWillMount to dispatch state change
const mapDispatchToProps = dispatch => ({
onShow: () => dispatch(toogleModal(true)),
});
export class Modal extends Component {
componentWillMount() { this.props.onShow(); }
render() { <div> {this.props.children} </div>}
}
export default connect(() =>({}), mapDispatchToProps)(Modal);
Somewhere in app we use <Modal>stuff</Modal>
. Modals have url and can be directly refreshed in browser like /profile/modalStuff
using RR v4.
We have SSR and when page source is viewed we can see that state.modal.visible === true
- meaning that componentWillMount was triggered and redux state got updated.
Client in this case renders no-scroll
class as expect. At the same time server does not have this class name added. Causes react warning.
also if you look at server console you will see that
App rendered with false
instead of expected 1 false and 2 true.
Client side on other hand when opening modal in browser will log false and true as expected.
It looks like state change done in componentWillMount never triggered rerended of App.jsx on server while it does so on client.
calling render on server side again for 2nd time causes App to have correct class again.
Any thoughts on this?
Version
React 15.4.1
react-redux 5.0.1