Redux-调度动作时未调用Reducer

时间:2019-06-04 19:26:42

标签: reactjs redux redux-thunk

我有一个简单的react应用,可从本地的JSON获取数据并更新状态。我面临的问题是调度动作时未调用我的reducer。我可以看到调度程序从JSON获取响应,但状态未更新

我在reducer上做了console.log,但是没有运气。我检查了Redux devtools,但看不到状态已更新。这是我的代码,

store.js

import {createStore, compose, applyMiddleware} from 'redux'
import thunk from 'redux-thunk'
import {routerMiddleware} from 'react-router-redux'
import rootReducer from './combined.reducer'
import {createLogger} from 'redux-logger'

let middlewares = [
    thunk
]

const logger = createLogger();

if (process.env.Node_ENV !== "production" && process.env.Node_ENV !== "test") {
    middlewares = [
        ...middlewares,
        logger,
        require("redux-immutable-state-invariant").default()
    ]
}

export default function configureStore(history) {
    const composeEnhancers =
        window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ || compose;
    const enhancer = composeEnhancers(
        applyMiddleware(...middlewares, routerMiddleware(history))
    );
    const store = createStore(
        rootReducer(history),
        enhancer
    )

    if (process.env.Node_ENV !== "production" && process.env.Node_ENV !== "test" && module.hot) {
        module.hot.accept("./combined.reducer", () => {
            const nextReducer = require("./combined.reducer").default
            store.replaceReducer(nextReducer)
        })
    }

    return store

combined.reducer.js

import { connectRouter } from 'connected-react-router';
import { combineReducers } from 'redux';
import * as workoutReducer from './features/WorkoutList/Containers/Workout.Reducer'

const createAppReducer = (history) => combineReducers({
  router: connectRouter(history),
  workoutReducer: workoutReducer
})

const rootReducer = (history) => (state, action) => {
  return createAppReducer(history)(state,action)
};

export default rootReducer;

文件夹结构:

src
 features
   Workout
     Components
     Containers
       Workout.Actions.js
       Workout.Constants.js
       Workout.Container.js
       Workout.Reducer.js
       Workout.js

Workout.Constants.js:

const constants = {
    GET_WORKOUT_LIST_REQUEST: "GET_WORKOUT_LIST_REQUEST",
    GET_WORKOUT_LIST_SUCCESS: "GET_WORKOUT_LIST_SUCCESS",
    GET_WORKOUT_LIST_FAILURE: "GET_WORKOUT_LIST_FAILURE"
    }

export default constants

Workout.Container.js:

import { connect } from 'react-redux'
import {withRouter} from 'react-router'
import {bindActionCreators} from 'redux'
import Workout from './Workout'
import * as workoutAction from './Workout.Actions'

export default withRouter(connect(
    (state) => ({
        workoutListData: state.workoutListData
    }), 
    (dispatch) => ({
        workoutActions:bindActionCreators(workoutAction, dispatch)
    })
)(Workout))

Workout.Actions.js:

import constants from "./Workout.Constants"
import {getConfigProperty} from "../../../settings"
import {makeGetCall} from "../../../utils/Api"
const WORKOUT_LIST = getConfigProperty("workoutList")

export function getWorkoutList(url = WORKOUT_LIST) {
    return (dispatch, getState) => {
        dispatch(getWorkoutListRequest(true))
        return makeGetCall(url, getState)
            .then(res => res.json())
            .then(json => {
                dispatch(getWorkoutListSuccess(json))
                dispatch(getWorkoutListRequest(false))
            })
            .catch(ex => {
                dispatch(getWorkoutListFailure(ex))
                dispatch(getWorkoutListRequest(false))
            })
    }
}

export function getWorkoutListRequest(req) {
    return {
        type: constants.GET_WORKOUT_LIST_REQUEST,
        req
    }
}

export function getWorkoutListSuccess(response) {
    return {
        type: constants.GET_WORKOUT_LIST_SUCCESS, 
        response
    }
}

export function getWorkoutListFailure(exception) {
    return {
        type: constants.GET_WORKOUT_LIST_FAILURE,
        exception
    }
}

Workout.Reducer.js

import constants from "./Workout.Constants"


const initialState = {
    workoutListData :{}
}

 function reducer(state = initialState, action) {
  console.log(".................I'm here................")
     switch(action.type) {
         case constants.GET_WORKOUT_LIST_SUCCESS: {
         return Object.assign({}, state, {
             workoutListData: action.response.GET_LIST_DATA
         })
        }
          case constants.GET_WORKOUT_LIST_FAILURE: {
          return Object.assign({}, state, initialState)    
        } 
     default:
     return state
    }
 }

 export {initialState}
 export default reducer

workout.js:

import React, {Component} from 'react'
import PropTypes from 'prop-types'
import {WorkoutListItem} from './../StyledComponents/WorkoutListItem'
import {isEmpty, isEqual} from 'lodash'
import {getConfigProperty} from "../../../settings"
const ROWS_PER_PAGE = getConfigProperty("rowsPerPage")



export default class Workout extends Component {


    static get PropTypes() {
        return {
            workoutListData: PropTypes.array.isRequired
        }
    }


    constructor(props){
        super(props)


     this.state = {
        workoutListData: []
     }
    }

    componentWillMount(){
        if(isEmpty(this.props.workoutListData)){
            this.props.workoutActions.getWorkoutList()
        }     
    } 


    loadWorkoutListItem = () => {
        return <WorkoutListItem / >
    }

    render() {
        return (
            <div>
                {this.loadWorkoutListItem()}
            </div>)
    }
}

应该调用reducer函数。我什至都看不到控制台日志

1 个答案:

答案 0 :(得分:0)

我不认为你想要

4/3/2019

但只是

import * as workoutReducer from './features/WorkoutList/Containers/Workout.Reducer'

首先是将initialState和reducer作为组合对象导入,而不是仅导入reducer。

编辑:这在import workoutReducer from './features/WorkoutList/Containers/Workout.Reducer'