zS1L3NT
zS1L3NT

Reputation: 500

Dynamic Page according to React-Redux state not updating rendered data

I want to build a one-page login system which renders different pages according to the state I set in the React-Redux store. The render() {} function isn't updating when the state of the store updates.

App.js

import React from 'react'

import store from './redux/store'
import { Provider } from 'react-redux'

// Route to Renderer.js below
import Renderer from './Renderer'

class App extends React.Component {
    render() {
        return (
            <Provider store={ store }>
                <Renderer page={store.getState().page} />
            </Provider>
        )
    }
}

export default App;

Renderer.js

import React, { Component } from 'react'

// Routes to my pages I plan to render
import Login from './routes/Login'
import About from './routes/About'
import Register from './routes/Register'

class Renderer extends Component {
    render() {
        let page = this.props.page
        let returned

        switch (page) {
            case 'About':
                returned = <About />
                break
            case 'Login':
                returned = <Login />
                break
            case 'Register':
                returned = <Register />
                break
            default:
                returned = <About />
        }

        return returned
    }
}

export default Renderer

I have a component linked to a Redux Action which changed the state of the page field. This isn't shown for simplicity sake. The change in the state is confirmed because the Redux Development Tools tells me that the state changed when I dispatch the actions to change the page Redux state. When I change the Redux state of the page field, the rendered page doesn't update and stays at the default page.

Upvotes: 1

Views: 619

Answers (1)

itaydafna
itaydafna

Reputation: 2086

Instead of passing page as an implicit prop to Renderer, use react-redux connect in order to pass this prop to the component using a mapStateToProps function:

Renderer.js

import React, { Component } from 'react'
import {connect} from 'react-redux'

// Routes to my pages I plan to render
import Login from './routes/Login'
import About from './routes/About'
import Register from './routes/Register'

class Renderer extends Component {
    render() {
        let page = this.props.page
        let returned

        switch (page) {
            case 'About':
                returned = <About />
                break
            case 'Login':
                returned = <Login />
                break
            case 'Register':
                returned = <Register />
                break
            default:
                returned = <About />
        }

        return returned
    }
}

const mapStateToProps = (state)=>({
  page: state.page
})

export default connect(mapStateToProps)(Renderer)

App.js

import React from 'react'

import store from './redux/store'
import { Provider } from 'react-redux'

// Route to Renderer.js below
import Renderer from './Renderer'

class App extends React.Component {
    render() {
        return (
            <Provider store={ store }>
              // remove the page prop here
                <Renderer />
            </Provider>
        )
    }
}

export default App;

By passing the page prop like this: page={store.getState().page} your Renderer component doesn't actually subscribe to store changes, so it will always return the initial page value.

The react-redux connect wrapper takes care of this subscription to the store - so your component will get an updated page value from the Provider on each store update.

Upvotes: 1

Related Questions