Upon page load, I am dispatching, inside my index.js
, an action store.dispatch(getWeatherReports());
that hits a weather API. This action goes through the redux
process and eventually adds the data returned to a property on the state called weatherReports
. This property is an object with an empty array. Now, I'm going to paste in an overview of the code.. not all of it to save you the trouble from going line to line, as outputting the data from the API is NOT the issue I am having.
Here is my index.js
:
import 'babel-polyfill';
import React from 'react';
import {render} from 'react-dom';
import configureStore from './store/configureStore';
import {Provider} from 'react-redux';
import {Router, browserHistory} from 'react-router';
import {StyleRoot} from 'radium';
import routes from './routes';
import {loadBlogs} from './actions/blogActions';
import {loadUsers, getActiveUser} from './actions/userActions';
import {getWeatherReports} from './actions/weatherActions';
import '../node_modules/bootstrap/dist/css/bootstrap.min.css';
import '../node_modules/toastr/build/toastr.min.css';
import './styles/app.scss';
const store = configureStore();
store.dispatch(loadBlogs());
store.dispatch(loadUsers());
store.dispatch(getActiveUser());
store.dispatch(getWeatherReports());
render(
<StyleRoot>
<Provider store={store}>
<Router history={browserHistory} routes={routes}/>
</Provider>
</StyleRoot>,
document.getElementById('app')
);
Trust that this goes through the right process to return the data. I have then created a smart
component that takes this state and looks to pass it to a dumb component.
class DashboardPage extends React.Component {
constructor(props, context) {
super(props, context);
this.state = {
weatherReports: []
};
}
<ContentBox
title="What The Wind Blew In"
content={<WeatherReport reports={this.props.weatherReports} />
/>
Again, trust that I have appropriately mapStateToProps
, mapDispatchToProps
, etc. I then look to display the data in the dumb
component. WeatherReport.js
:
import React, {PropTypes} from 'react';
import styles from '../common/contentBoxStyles';
const WeatherReport = ({reports}) => {
console.log(reports);
return (
<div style={styles.body} className="row">
<div style={styles.weatherBoxContainer}>
<div className="col-sm-2 col-md-offset-1" style={styles.weatherBoxContainer.weatherCard}>
<div style={styles.weatherBoxContainer.weatherReport}>
<div style={styles.weatherBoxContainer.currentTemp}>
HERE IS MY PROBLEM!!
{reports[0].main.temp}
</div>
</div>
CA
</div>
<div className="col-sm-2" style={styles.weatherBoxContainer.weatherCard}>
<div style={styles.weatherBoxContainer.weatherReport}>
Report
</div>
UT
</div>
<div className="col-sm-2" style={styles.weatherBoxContainer.weatherCard}>
<div style={styles.weatherBoxContainer.weatherReport}>
Report
</div>
MN
</div>
<div className="col-sm-2" style={styles.weatherBoxContainer.weatherCard}>
<div style={styles.weatherBoxContainer.weatherReport}>
Report
</div>
DC
</div>
<div className="col-sm-2" style={styles.weatherBoxContainer.weatherCard}>
<div style={styles.weatherBoxContainer.weatherReport}>
Report
</div>
NY
</div>
</div>
</div>
);
};
WeatherReport.propTypes = {
reports: PropTypes.array
};
export default WeatherReport;
My underlying issue is that before my dispatch action returns the data.. I am trying to render it through my dumb
component. Thus I receive the following error when trying to access the data: Uncaught TypeError: Cannot read property 'main' of undefined(…)
when doing the following: reports[0].main.temp
What is happening is this is stopping my application from moving forward so that the store.dispatch(getWeatherReports());
never gets called. Thus if I remove the {reports[0].main.temp}
from the equation, then the process continues and the action gets dispatched. Then I can call the equation w/ HMR and hooray!! The data is there...
So my question, and thanks for bearing with me, is how can I get it so that my dumb component waits to try and access these properties on the state until AFTER my initial dispatched actions occur?