将Typescript与React-Redux一起使用时出现类型错误

将Typescript与React-Redux一起使用时出现类型错误

问题描述:

我正在尝试使用带有typescript的react-redux,当我尝试使用connect()和mapStateToProps注入道具时遇到类型错误.

I am trying to use react-redux with typescript and I'm getting a type error when I try to inject props using connect() and mapStateToProps.

我的组件看起来像这样:

My component looks like this:

function mapStateToProps(state) {
    return {
        counter: state.counter
    };
}

function mapDispatchToProps(dispatch) {
    return {
        incr: () => {
            dispatch({type: 'INCR', by: 2});
        },
        decr: () => {
            dispatch({type: 'INCR', by: -1});
        }
    };
}




export default class Counter extends React.Component<HelloProps, any> {
    render() {
        return (
          <div>
              <p>
                  <label>Counter: </label>
                  <b>#{this.props.counter}</b>
              </p>
              <button onClick={e => this.props.incr() }>INCREMENT</button>
              <span style={{ padding: "0 5px" }}/>
              <button onClick={e => this.props.decr() }>DECREMENT</button>
        );
    }
}


export default connect(mapStateToProps, mapDispatchToProps)(Counter);

商店看起来像这样

let store = createStore(
    (state:HelloState, action:HelloAction) => {
        switch (action.type) {
            case 'INCR':
                return {counter: state.counter + action.by};
            default:
                return state;
        }
    },

最后,我将类型定义为:

Finally, I have defined my types to be:

interface HelloProps {
    counter?: number;
    incr?: () => any;
    decr?: () => any;
}

interface HelloState { 
    counter:number;
}

interface HelloAction { 
    type:string, 
    by:number;
}

当我尝试编译代码时,出现以下错误:

When I try and compile the code I get the following error:

(39,61): error TS2345: Argument of type 'typeof Counter' is not assignable to parameter of type 'ComponentClass<{ counter: any; } & { incr: () => void; decr: () => void; }> | StatelessComponent<...'.
  Type 'typeof Counter' is not assignable to type 'StatelessComponent<{ counter: any; } & { incr: () => void; decr: () => void; }>'.
    Type 'typeof Counter' provides no match for the signature '(props?: { counter: any; } & { incr: () => void; decr: () => void; }, context?: any): ReactElement<any>' 

有趣的是,即使代码抛出类型错误,它仍然可以正常工作.此外,将组件的prop接口更改为any也可以解决该问题.似乎类型系统无法理解这两个映射功能将两个对象合并在一起.

Interestingly the code still works even though it throws the type error. Also, changing the component's prop interface to any also solves the issue. It seems like the type system doesn't understand that the two objects are merged by the two mapped functions.

我在此Github上倒数第二个帖子中找到了答案

I found the answer in the second to last post on this Github issue. Without the type parameter on both the mapStateToProps and/or mapDispatchToProps or on connect it will produce an intersection of the return types of the two map functions.