【问题标题】:Chaining promises with Thunk and Promise middleware使用 Thunk 和 Promise 中间件链接 Promise
【发布时间】:2017-04-27 09:11:42
【问题描述】:

我同时使用redux-promise-middlewareredux-thunk,如下所示:

import { applyMiddleware, compose, createStore } from 'redux'

import thunk from 'redux-thunk';
import promise from 'redux-promise-middleware'
import logger from 'redux-logger'

import reducer from './reducers'

const middleware = applyMiddleware(thunk, promise(), logger({diff: true}));
const composeEnhancers = window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__ || compose;
const enhancer = composeEnhancers(middleware);

export default createStore(
    reducer,
    enhancer)

所以,我想做的是将几个承诺链接在一起。 redux-promise-middleware 文档建议像这样使用Promise.all

export function startTest(test) {
    return dispatch => {
        return dispatch({
            type: START_TEST,
            id: test,
            payload: Promise.all([
                dispatch(axios.post(urlJoin(config.portalUrl, 'account/login')))
            ])
        })
    };
}

但是,当我将其发送到商店时,我收到以下错误:

错误:动作必须是普通对象。使用自定义中间件进行异步操作。

我配置错了什么?

【问题讨论】:

  • 为什么要在具有单个值的数组上调用Promise.all
  • @Bergi 这是因为我将来会执行更多操作,因为我将它们链接起来;我只需要让架构工作就可以了。我希望这是有道理的。

标签: javascript reactjs redux promise redux-thunk


【解决方案1】:

这不是对您问题的直接回答,但您实际上并不需要使用 redux-promise-middleware 包。您可以简单地创建自己的中间件来处理 Promise。这是我对 Promise 中间件的简单实现:

export default function PromiseMiddleware() {
   return (next) => (action) => {
      const {promise, type, ...rest} = action

      if (!promise) return next(action)

      const REQUEST = type + '_REQUEST'
      const SUCCESS = type + '_SUCCESS'
      const FAILURE = type + '_FAILURE'

      next({...rest, type: REQUEST})

      return promise
         .then(result => {

            next({...rest, result, type: SUCCESS})

            return true
         })
         .catch(error => {
            if (DEBUG) {
               console.error(error)
               console.log(error.stack)
            }
            next({...rest, error, type: FAILURE})

            return false
         })
   }
}

而且你可以像以前一样应用它:

const middleware = applyMiddleware(thunk, PromiseMiddleware, logger({diff: true}))

【讨论】:

    【解决方案2】:

    我发现了这个问题。它需要改成这样:

    export function startTest(test) {
        return dispatch => {
            return dispatch({
                type: START_TEST_THUNK,
                payload: Promise.all([
                    dispatch({
                        type: START_TEST,
                        payload: axios.post(urlJoin(config.portalUrl, 'account/login')),
                        meta: {
                            id: test
                        }
                    })
                ])
            })
        };
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2020-04-17
      • 1970-01-01
      • 2015-01-19
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2020-02-22
      相关资源
      最近更新 更多