如何在Redux中管理(异步)级联数据?

时间:2015-11-27 00:46:10

标签: javascript redux

想象一下汽车配置应用程序。这是一个示例状态树:

{
  // selections
  modelYear,
  modelId,
  transmissionId,

  // options
  modelYears: [],
  models: [],
  transmissions: [],
  accessories: []
}

当应用程序启动时,它会加载一些初始数据。然后,您将首先选择模型年份来填充模型列表,然后选择模型,然后选择传输,附件等。每个数据都依赖于先前的分层方式选择。页面加载的事件序列示例如下:

  1. 检索所有年份并填充下拉列表。
  2. 默认选择第一年
  3. 根据所选年份检索模型
  4. 默认选择第一个模型
  5. 根据所选模型检索传输
  6. 默认选择传输
  7. 根据所选型号检索配件 等...
  8. 当用户更改任何数据的选择时,必须检索层次结构中较低的新数据,并且必须重新填充UI。

    以下是我写的一些片段:

    操作

    export function getModelYears() {
      return dispatch => {
        vehiclesApi.getModelYears(years => {
          dispatch(receiveModelYears(years))
        })
      }
    }
    
    export function getModels(year) {
      return dispatch => {
        vehiclesApi.getModels(year, models => {
          dispatch(receiveModels(models))
        })
      }
    }
    
    function receiveModelYears(years) {
      return {
        type: types.RECEIVE_MODEL_YEARS,
        years: years
      }
    }
    
    function receiveModels(models) {
      return {
        type: types.RECEIVE_MODELS,
        models: models
      }
    }
    
    export function selectModelYear(year) {
      return {
        type: types.SELECT_MODEL_YEAR,
        year
      }
    }
    

    减速器

    function vehicle(state = {}, action) {
      switch (action.type) {
        case SELECT_MODEL_YEAR:
          return Object.assign({}, state, {
            modelYear: action.year
          })
        case SELECT_MODEL:
          return Object.assign({}, state, {
            modelId: action.modelId
          })
        default:
          return state
      }
    }  
    
    function modelYears(state = [], action) {
      switch (action.type) {
        case RECEIVE_MODEL_YEARS:
          return state.concat(action.years)
        default:
          return state
      }
    }
    
    function models(state = [], action) {
      switch (action.type) {
        case RECEIVE_MODELS:
          return state.concat(action.models)
        default:
          return state
      }
    }
    

    我不确定如何构建我的减速机和减速机。处理默认选择并在选择后请求新数据的操作。手动操作很简单(用户点击,调度操作)。但是,如何在默认选择第一年后手动调度getModels(year)

    这是我用伪代码描述流程的最佳方法:

    store.dispatch(getModelYears())
    
    store.subscribe(() => {
      // if model years received
      store.dispatch(selectModelYear(store.getState().modelYears[0]))
    
      // if modelYear selected
      store.dispatch(getModels(store.getState().modelYear))
    
      // if models received
      store.dispatch(selectModel(store.getState().models[0].id))
    
      // if model selected
      store.dispatch(getTransmissions(store.getState().modelId))
      store.dispatch(getAccessories(store.getState().modelId))
    
      // ...etc
    })
    

    我想测试这个系统与任何UI框架无关,因为我将其构建为管理我的客户端状态的概念证明,并且可能无法使用React。

1 个答案:

答案 0 :(得分:2)

如果我正确理解了您的要求,那么您正在寻找通过触发其他操作来响应状态更改的方法。例如,每当store.modelYear更改时,您都需要触发RECEIVE_MODELS操作。

订阅方法适合该作业。如果您想要更结构化的设计,可以在subscribe之上构建模式,例如演员:http://jamesknelson.com/join-the-dark-side-of-the-flux-responding-to-actions-with-actors/