Development environment : react + typescript + connected-react-router
What I intended : I want to use the router action asynchronously in the user action. So when login is complete I want my application to go to the main screen.
Error Message : Argument of type 'CallHistoryMethodAction<[string, unknown?]>' is not assignable to parameter of type 'UserActionType'
Error code :
export const login = (data: { id: string; password: string }) => async (
dispatch: Dispatch<UserActionType>,
): Promise<void> => {
await dispatch(loginRequest());
try {
const result = await apis.usersApi.login(data);
if (!result.data || !result.data.id) {
throw Error();
}
await dispatch(loginSuccess(result.data));
sessionStorage.setItem('mi', result.data.id);
await dispatch(actions.router.push('/')); <- ts error!
} catch (error) {
console.dir(error);
if (!error.response) {
await dispatch(loginFailure('서버 요청을 확인 해 주세요'));
}
if (error.response.status === 400) {
await dispatch(loginFailure('id 혹은 password를 확인 해 주세요'));
} else {
await dispatch(loginFailure('로그인 할 수 없습니다'));
}
}
};
UserActionType code :
import * as ActionTypes from '../rootActionTypes';
export interface IApiKey {
id?: number;
api_key?: string;
expire_date?: string | null;
}
export interface IUser {
id: number;
username: string;
email: string;
first_name: string;
last_name: string;
is_staff: boolean;
last_login: string;
date_joined: string;
api_keys?: Array<IApiKey>;
}
export interface IPolicyPWState {
id: number;
config_name: string;
config_data: string;
}
export interface IUserState {
user: IUser;
userLists: Array<IUser>;
userList: IUser;
isLoading: boolean;
addedUser: boolean;
deletedUser: boolean;
isRefreshAPI: boolean;
pwPolicy: Array<IPolicyPWState>;
error: string;
}
// login action type
interface loginRequestAction {
type: typeof ActionTypes.LOGIN_REQUEST;
}
interface loginSuccessAction {
type: typeof ActionTypes.LOGIN_SUCCESS;
data: IUser;
}
interface loginFailureAction {
type: typeof ActionTypes.LOGIN_FAILURE;
data: string;
}
...
export type UserActionType =
| loginRequestAction
| loginSuccessAction
| loginFailureAction
...
;
Root Reducer code :
import { connectRouter, RouterState } from 'connected-react-router';
import { History } from 'history';
import { combineReducers, Reducer } from 'redux';
import user from './users/reducers';
import board from './board/reducers';
import api from './api/reducers';
import { IUserState } from './users/users.types';
import { IBoardState } from './board/board.types';
export interface RootState {
user: IUserState;
router: RouterState;
board: IBoardState;
api: any;
}
const createRootReducer = (history: History): Reducer<RootState> =>
combineReducers({
router: connectRouter(history),
user,
board,
api,
});
export { createRootReducer };
Questions : How do I create a Rootaction including a router action?