我有一个redux saga设置,可以正常工作。我的调度之一是创建一个新订单,然后在创建新订单后,我要使用更新后的状态进行处理。
// this.props.userOrders = []
dispatch(actions.createOrder(object))
doSomethingWith(this.props.userOrders)
由于createOrder操作触发了调用API的redux传奇,因此存在延迟,因此在调用我的函数doSomethingWith之前不会更新this.props.userOrders。我可以设置一个超时时间,但这似乎不是一个可持续的想法。
我已经阅读了有关Stack Overflow的类似问题,并尝试实现了相关的方法,但是我似乎无法使其正常运行。我希望下面的代码可以有人添加几行来完成。
以下是其他相关文件:
actions.js
export const createUserOrder =(数据)=>({ 类型:“ CREATE_USER_ORDER”, 数据 })
Sagas.js
function * createUserOrder () {
yield takeEvery('CREATE_USER_ORDER', callCreateUserOrder)
}
export function * callCreateUserOrder (newUserOrderAction) {
try {
const data = newUserOrderAction.data
const newUserOrder = yield call(api.createUserOrder, data)
yield put({type: 'CREATE_USER_ORDER_SUCCEEDED', newUserOrder: newUserOrder})
} catch (error) {
yield put({type: 'CREATE_USER_ORDER_FAILED', error})
}
}
Api.js
export const createUserOrder = (data) => new Promise((resolve, reject) => {
api.post('/userOrders/', data, {headers: {'Content-Type': 'application/json'}})
.then((response) => {
if (!response.ok) {
reject(response)
} else {
resolve(data)
}
})
})
减速机:
case 'CREATE_USER_ORDER_SUCCEEDED':
if (action.newUserOrder) {
let newArray = state.slice()
newArray.push(action.newUserOrder)
return newArray
} else {
return state
}
答案 0 :(得分:1)
这感觉像是XY Problem。在任何时候,您都不应该在组件的生命周期函数/事件处理程序内部“等待”,而应该利用商店的当前状态。
如果我正确理解,这是您当前的流程:
您在React组件中调度了一个动作
CREATE_USER_ORDER
。您的callCreateUserOrder
传奇消耗了该动作。当您的创建订单传奇完成时,它会分派另一个“已完成”操作,您已经以CREATE_USER_ORDER_SUCCEEDED
的身份拥有该操作。
您现在应该添加的是处理CREATE_USER_ORDER_SUCCEEDED
的适当的化简/选择器:
此CREATE_USER_ORDER_SUCCEEDED
动作应由您的reducer处理,以创建一个新状态,在该状态中填充您状态中的某些“ orders”属性。可以通过选择器将其直接连接到您的组件,这时将重新渲染您的组件并填充this.props.userOrders
。
示例:
组件
class OrderList extends React.PureComponent {
static propTypes = {
userOrders: PropTypes.array.isRequired,
createOrder: PropTypes.func.isRequired,
}
addOrder() {
this.props.createOrder({...})
}
render() {
return (
<Wrapper>
<Button onClick={this.addOrder}>Add Order</Button>
<List>{this.props.userOrders.map(order => <Item>{order.name}</Item>)}</List>
</Wrapper>
)
}
}
const mapStateToProps = state => ({
userOrders: state.get('userOrders'),
})
const mapDispatchToProps = {
createOrder: () => ({ type: 'CREATE_ORDER', payload: {} }),
}
export default connect(mapStateToProps, mapDispatchToProps)(OrderList)
减速器
case 'CREATE_USER_ORDER_SUCCEEDED':
return state.update('userOrders',
orders => orders.concat([payload.newUserOrder])
)
如果您确实确实需要副作用,则将这些副作用添加到您的传奇中,或创建一个采取SUCCESS动作的新传奇。