redux-thunkのthen
たとえばTodo listに一つアイテムを追加・編集・削除した後、
改めてサーバーにRetrieve Listをしたい場合ありますよね。
redux-thunkはこういう感じができます:
const createActionCreator = (item) => {
return dispatch => {
return axios
.post('api/todo', item)
.then(response => {...}) // 割愛します
}
}
const retrieveActionCreator = () => {
return dispatch => {
return axios
.get('api/todo')
.then(response => {...}) // 割愛します
}
}
// どこかで
dispatch(createActionCreator(newItem))
.then(() => {
dispatch(retrieveActionCreator())
})
// ちなみに
dispatch(createActionCreator(newItem))
dispatch(retrieveActionCreator())
// こういう風に書くと、両者ともAsync Callなのでどれが先に完成するのかは保証できませんので。
// 上みたいにthenを使う必要はあります。
useDispatchのdispatchを使うとできなくなる
言語:Typescript
JSだと多分エラー出ないですね。
import { useDispatch } from 'react-redux';
const dispatch = useDispatch()
dispatch(createActionCreator(newItem))
.then(() => { // このthenでエラーが出ます
dispatch(retrieveActionCreator())
})
Property 'then' does not exist on type '...'
みたいなエラーが出ますね。
type
はactionCreator
のreturn type
なので人によっては違いますが。
解決法
多分react-reduxがredux-thunkのdispatch
の型を知らないので、type check
が通ってない気がします。
storeHelper.ts
import { ThunkDispatch } from 'redux-thunk';
import { Action } from 'redux';
import { useDispatch } from 'react-redux';
import { SystemState } from 'features/systemState';
// このSystemStateは自分で定義したReduxのStore構成、詳細は割愛します
// Todo Listだと { items: {name: string ,finished: boolean}[] } みたいな
export type ReduxDispatch = ThunkDispatch<SystemState, any, Action>;
export function useReduxDispatch(): ReduxDispatch {
return useDispatch<ReduxDispatch>();
}
元のファイルで:
import { useReduxDispatch } from './storeHelper'
const dispatch = useReduxDispatch()
dispatch(createActionCreator(newItem))
.then(() => { // できました
dispatch(retrieveActionCreator())
})
終わりに
ご指摘がございましたら、コメントを頂けるとありがたいです。
もしお役に立ちましたらいいねを貰えると嬉しいです。