2016-01-22 81 views
4

我想创建一个可重复使用的redux表模块,它将存储和更新页码,显示的总页数等,这些可以在我的所有页面之间共享。聆听Redux动作

但是,我需要更新操作来触发refreshdata操作,该操作将根据页面触发不同的端点。

因此,也许沿着页面特定的线侦听'RefreshData'动作然后触发另一个动作。什么是实现这一目标的最佳方式?我目前正在为我的中间件使用redux-thunk,但一直在寻找redux-saga。

达到此目的的最佳方法是什么?

**为了澄清**

我有多个页面/项目表,我希望尽量减少代码重复。我想我也许可以制作一个可放置的redux模块(action + reducer),然后分别为REFRESH_DATA动作指定处理程序,所以我不需要在这个文件中放置开关。我认为使用REDX-SAGA,我可以听取REFRESH_DATA动作,并根据当前页面进行切换?或者有更好的建议。

export const ITEMS_PER_PAGE_UPDATED = 'ITEMS_PER_PAGE_UPDATED' 
export const CURRENT_PAGE_UPDATED = 'CURRENT_PAGE_UPDATED' 
export const REFRESH_DATA = 'REFRESHDATA' 
export const DATA_REFRESHED = 'REFRESHDATA' 

export function currentPageUpdated(value) { 
    return function (dispatch) { 
     dispatch({ 
      type: CURRENT_PAGE_UPDATED, 
      value 
     }) 
     dispatch({type:REFRESH_DATA}) 
    } 
} 

export function itemsPerPageUpdated(value) { 
    return function (dispatch) { 
     dispatch({ 
      type: ITEMS_PER_PAGE_UPDATED, 
      value 
     }) 
     dispatch({type:REFRESH_DATA}) 
    } 
} 

function reducer(state={ pageNumber:1, pageSize:10, totalItems:0, totalPages:1, sortColumn:null, sortAscending:true }, action) { 
    switch(action.type) { 
     case ITEMS_PER_PAGE_UPDATED: 
      return Object.assign({}, state, {pageSize: action.value, pageNumber:1}) 
     case CURRENT_PAGE_UPDATED: 
      return Object.assign({}, state, {pageNumber: action.value}) 
     case DATA_REFRESHED: 
      return Object.assign({}, state, {totalPages: action.values.totalPages, totalItems:action.values.totalItems}) 
     default: 
      return state 
    } 
} 

export default reducer 
+0

你的问题对我来说有点不清楚。你能否提供更多技术性或结构化的例子? –

+0

@TanerTopal我已经添加了一些信息 – Tom

+0

我将需要添加更多的代码排序等 – Tom

回答

1

如果我理解正确的,它听起来就像是REFRESH_DATA作用主要的副作用,这意味着动作只能派遣作为另一个动作的结果。如果是这种情况,那么我会说REDX传奇将是一个不错的选择,因为它可以坐在后台,“倾听”行动,然后触发其他行动。但是,您可能能够通过定制的middleware获得相当好的效果。

使用自定义中间件,您可以在它们在达到减速器之前进行调度时拦截操作。如果您将要执行一系列与更新表和刷新数据相关的操作,则可以为所有这些操作创建通用操作形状,以便您的中间件可以监听它并调度特殊的副作用。

一个简单的实现可能是这个样子:

中间件/ table.js

import fetchData from '../somewhere'; 
import { DATA_REFRESHED } from '../actions'; 

// Make a unique identifier that you're actions can send so you're 
// middleware can intercept it 
export const UPDATE_TABLE = Symbol('UPDATE_TABLE'); 

export default store => next => action => { 
    const tableUpdate = action[UPDATE_TABLE]; 

    // If the action doesn't have the symbol identifier, just move on 
    if (typeof tableUpdate === 'undefined') { 
    return next(action); 
    } 

    // At this point, you know that the action that's been dispatched 
    // is one that involves updating the table, so you can do a fetch 
    // for data 

    // Get whatever data you need to fetch 
    const { id, type, data } = tableUpdate; 

    // Dispatch the actual type of action to the store 
    next({ type, data }); 

    // Go and fetch the data as a side-effect 
    return fetchData(id) 
    .then(response => next({ type: DATA_REFRESHED, data: response })); 
} 

actions.js

import { UPDATE_TABLE } from '../middleware/table.js'; 

// An action creator to dispatch the special table update action 
// This is a simple example, but you'd probably want to be consistent 
// about how the table update actions are shaped. The middleware 
// should be able to pick out all of the data it needs to fetch data 
// from whatever is sent with the action 
function updateTable(action) { 
    return { 
     [UPDATE_TABLE]: action 
    }; 
} 

export function currentPageUpdated(value) { 
    return updateTable({ 
     type: CURRENT_PAGE_UPDATE, 
     value 
    }); 
} 

我拍了很多这从真实世界的例子:https://github.com/rackt/redux/blob/master/examples/real-world/middleware/api.js