2

When clicking on the back button , the url gets changed, but the component that should be rendered for this url, is not rendered. Rerendering seems to be blocked. I am using connected-react-router. Before implementing connected-react-router, the back button worked fine. I tried a suggested solution , wrapping my connect function with the redux store with withRouter, but still see no result.

index.js

const store = configureStore();

ReactDOM.render(
  <Provider store={store}>
    <ConnectedRouter history={history}>
      <App />
    </ConnectedRouter>
  </Provider>,
  document.getElementById('root'),
);

App.js

class App extends Component {
  componentDidMount() {
    const { dispatch } = this.props;
    dispatch(getInitialBookData());
  }

  render() {
    return (
      <div>
        <Navigation /> 
      </div>
    );
  }
}

export default connect()(App);

Navigation.js

const Navigation = () => {
  return (
      <Fragment>
        <Navbar color="light" light expand="md">
          <Collapse className="navbar-collapse">
            <Nav className="ml-sm-auto navbar-nav">
              <NavItem className="p-2">
                <NavLink activeClassName="active" to="/">Dashboard</NavLink>
              </NavItem>
              <NavItem className="p-2">
                 <NavLink activeClassName="active" to="/addbook">Add Book</NavLink>
              </NavItem>
            </Nav>
          </Collapse>
        </Navbar>
        <Container className="content mt-8">
          <Switch>
            <Route exact path="/" component={Dashboard} />
            <Route exact path="/editbook/:id" component={CreateEditBookContainer} />
            <Route exact path="/addbook" component={CreateEditBookContainer} />
            <Route component={Page404} />
           </Switch>
        </Container>
      </Fragment>
  );
};

Dashboard.js

const Dashboard = ({ loading, error, success }) => {
  return (
    <Fragment>
      { error.status === true
        ? <ErrorAlert message={error.message} />
        : null }
      { success.status === true
        ? <SuccessAlert message={success.message} />
        : null }
      <Row className="mt-3">
        <h2 className="mb-5">Welcome to Dashboard</h2>
        { loading === true
          ? null
          : <BookListContainer /> }
      </Row>
    </Fragment>
  );
};

const mapStateToProps = ({fetching, errors, success}) => {
  return { 
    loading: fetching.status,
    error: errors,
    success: success,
  };
}

Dashboard.propTypes = {
  loading: PropTypes.bool.isRequired,
  error: PropTypes.object.isRequired,
  success: PropTypes.object.isRequired,
};

export default withRouter(connect(mapStateToProps)(Dashboard));

BookListContainer.js

class BookListContainer extends Component{

  state = {
    navigateToEditBook: false,
  };

  idBookToEdit = null;
  goToEditComponent = (id) => {
    this.idBookToEdit = id;
    this.setState({ navigateToEditBook: true });
  }

  render() {
    let idBookToEdit = this.idBookToEdit;
    if (this.state.navigateToEditBook === true) {
      return <Redirect push to={{ 
        pathname:`/editBook/${idBookToEdit}`,
        state: { referrer: '/', bookId: idBookToEdit }
      }} />
    }
    const { books } = this.props;
    return(
      <Row>
        { books.map((book) => {
            return ( 
            <Book
               key={book._id}
               book={book}
               handleEditBook={this.goToEditComponent}
            />
          )
        }) }
      </Row> 
    )};
};

const mapStateToProps = (props) => {
    return { 
    books: props.books.books,
    location: props.router.location,
    };
}

BookListContainer.propTypes = {
  books: PropTypes.array.isRequired,
};

export default withRouter((connect(mapStateToProps)(BookListContainer)));

CreateEditBookContainer.js

class CreateEditBookContainer extends Component {

  render() {
    const bookId = this.props.location.state
     ? this.props.location.state.bookId
     :null

    const { books, error, success } = this.props;
    let book = null;
    if(bookId){
      book = books.filter(book => book._id === bookId)
    }
    return(
      <Col sm="12" md="6" className="m-auto pt-5">
        <CreateEditBookForm 
          { ...book ? book = { ...book[0] } : null }
        />
        { error.status === true
          ? <ErrorAlert message={error.message} />
          : null }
        { success.status === true
          ? <SuccessAlert message={success.message} />
          : null }
      </Col>
    )}
}

const mapStateToProps = ({ books, errors, success }) => {
  return {
    books: books.books,
    error: errors,
    success: success,
  }
}

CreateEditBookContainer.propTypes = {
  books: PropTypes.array.isRequired,
  error: PropTypes.object.isRequired,
  success: PropTypes.object.isRequired,
};

export default withRouter(connect(mapStateToProps)(CreateEditBookContainer));

When clicking on EditBook Button, CreateEditBookContainer.js gets correctly rendered, but when clicking on the back button, this components remains, while the Dashboard component should actually get rendered since it corresponds to the path '/', that is correctly set in the url. When clicking on the Route links in specified in Navigation, all components are rendered correctly. It ONLY fails on the back button. Thank you for any suggestions.

JuliaG
  • 21
  • 1

0 Answers0