LeetCode-OpenSource/rxjs-hooks

VoidableCallback typing

wmaurer opened this issue · 2 comments

I'm having problems with the typing for useEventCallback. I can't seem to pass a discriminated union as EventValue to the callback function:

import { useCallback } from 'react';
import { useEventCallback } from 'rxjs-hooks';
import { withLatestFrom, map } from 'rxjs/operators';

type State = number;
type Action = { type: 'add'; n: number } | { type: 'multiply'; n: number };

const reducer = <State, Action>(state: State, _action: Action) => state;

export const Cmpnt = () => {
    const [dispatch] = useEventCallback<Action, State>(
        (event$, state$) =>
            event$.pipe(
                withLatestFrom(state$),
                map(([action, state]) => reducer(state, action)),
            ),
        0,
    );

    const onAddClicked = useCallback((n: number) => dispatch({ type: 'add', n }), [dispatch]);
};

Here I'm getting the following Typescript error when calling the dispatch function:

Type '"add"' is not assignable to type '"add" & "multiply"'.
  Type '"add"' is not assignable to type '"multiply"'.ts(2322)

When I change the definition of VoidableCallback to:

declare type VoidableCallback<EventValue> = (val: EventValue) => void;

... then I have no problems. It seems that the more complex type definition here is wrong?

I have a fix for this, see PR #43

v0.4.2 available