title: React Redux how to dispatch async actions and update state
body: <p>I try to deal with ajax data in my learning react,redux project and I have no idea how to dispatch an action and set the state inside a component</p>
  
  <p>here is my component</p>
  
  <pre><code>import React, {PropTypes, Component} from 'react';
  import Upload from './Upload';
  import {bindActionCreators} from 'redux';
  import {connect} from 'react-redux';
  import * as profileActions from '../../../actions/profileActions';
  
  
  class Profile extends Component {
  
      static propTypes = {
          //getProfile: PropTypes.func.isRequired,
          //profile: PropTypes.object.isRequired,
      };
  
      constructor(props) {
          super(props);
  
          this.state = {
              profile:{
                  username: '',
                  password: ''
              }
          }
          this.onUpdate = this.onUpdate.bind(this)
      }
  
      onUpdate(event) {
          alert()
      }
  
      componentWillMount() {
      }
  
      componentDidMount() {
      }
  
  
      render() {
  
          const {profile} = this.props;
          return (
              &lt;div&gt;
  
              &lt;/div&gt;
          );
      }
  }
  
  function mapStateToProps(state) {
      console.log(state)
      return {
          profile: state.default.profile,
      };
  }
  
  function mapDispatchToProps(dispatch, ownProps) {
      return {
          actions: bindActionCreators(profileActions, dispatch)
      };
  }
  
  export default connect(mapStateToProps, mapDispatchToProps)(Profile);
  </code></pre>
  
  <p>I create the store as it follows</p>
  
  <pre><code>import { createStore, combineReducers, applyMiddleware } from 'redux'
  import createLogger from 'redux-logger'
  import thunk from 'redux-thunk'
  import { routerReducer, routerMiddleware, push } from 'react-router-redux'
  import reducers from '../reducers'
  import { browserHistory } from 'react-router';
  
  const middleware = [ thunk ];
  if (process.env.NODE_ENV !== 'production') {
      middleware.push(createLogger());
  }
  
  middleware.push(routerMiddleware(browserHistory));
  
  // Add the reducer to your store on the `routing` key
  const store = createStore(
      combineReducers({
          reducers,
          routing: routerReducer
      }),
      applyMiddleware(...middleware),
  
  )
  
  export default store;
  </code></pre>
  
  <p>reducer</p>
  
  <pre><code>export const RESOLVED_GET_PROFILE = 'RESOLVED_GET_PROFILE'
  
  const profileReducer = (state = {}, action) =&gt; {
      switch (action.type) {
          case 'RESOLVED_GET_PROFILE':
              return action.data;
          default:
              return state;
      }
  };
  
  export default profileReducer;
  </code></pre>
  
  <p>actions</p>
  
  <pre><code>import * as types from './actionTypes';
  import Api from '../middleware/Api';
  
  export function getProfile() {
      return dispatch =&gt; {
          dispatch(setLoadingProfileState()); // Show a loading spinner
          Api.getAll('profile').then(profile =&gt; {
              dispatch(doneFetchingProfile(profile));
          }).catch(error =&gt; {
              throw(error);
          });
          /*Api.fetch(`profile`, (response) =&gt; {
              console.log(response)
              dispatch(doneFetchingBook()); // Hide loading spinner
              if(response.status == 200){
                  dispatch(setProfile(response.json)); // Use a normal function to set the received state
              }else {
                  dispatch(error)
              }
          }) */
      }
  }
  
  function setProfile(data) {
      return {type: types.SET_PROFILE, data: data}
      //return { type: types.SET_PROFILE, data: data };
  }
  
  
  function setLoadingProfileState() {
      return {type: types.SHOW_SPINNER}
  }
  
  function doneFetchingProfile(data) {
      console.log(data)
      return {
          type: types.HIDE_SPINNER,
          profile: data
      }
  }
  
  function error() {
      return {type: types.SHOW_ERROR}
  }
  </code></pre>
  
  <p>but I have no idea how would I dispatch action and update the state after getProfile action</p>