There are multiple ways to construct a Map.
export function Map<K, V>(collection: Iterable<[K, V]>): Map<K, V>;
export function Map<V>(obj: {[key: string]: V}): Map<string, V>;
export function Map<K, V>(): Map<K, V>;
export function Map(): Map<any, any>;
The error on the first overload is expected because you definitely shouldn't match that one. Your object is closer to the second overload, but you don't match that overload automatically because it involves a string index signature which DashboardState does not have.
The quick and dirty solution here involves setting a generic on the Map function. As you can see, the second overload is the only one with just <V> instead of <K, V>. So you can match this overload by setting just a value type for the Map. In this case the value type of DashboardState is any.
state = Map<any>(defaultState)
The type support with this setup is extremely weak. The keys of state can be any string and the values can be absolutely anything. Why bother using Typescript at all if you can't get any useful information out of it?
I recommend using the official Redux Toolkit which has strong typescript support as well as support for immutability using Immer. And replace the any in your DashboardState with the actual types.
Edit:
After viewing your edit, I recommend that you use optional properties (number | undefined) instead of number | null since Map.get() includes undefined along with the expected value. So you would get number | null | undefined. If using optional properties then you don't actually need an initial state at all. You can use an empty Map.
We can also limit the keys to just the keys of DashboardState.
Use these utilities on any state type:
export type MapOf<T> = Map<keyof T, T[keyof T]>;
const createMap = <T,>(): MapOf<T> => Map<keyof T, T[keyof T]>();
For the dashboard:
export interface DashboardState {
componentId?: number;
dashboard?: number;
}
export default function (state = createMap<DashboardState>(), action): MapOf<DashboardState> {
switch (action.type) {
case dashboardsActionsTypes.SET_PROJECT_VIEW:
return state.set('componentId', action.payload);
case dashboardsActionsTypes.SET_DASHBOARD_TYPE:
return state.set('dashboard', action.payload);
default:
return state;
}
}
Mapis a ... map with getter and setters etc, regardless of what data you store in it. I guess your state would have to bedefaultState : Immutable.Map<string, any>