简体   繁体   English

如何使用 reselect createStructuredSelector function 和 typescript?

[英]How to use reselect createStructuredSelector function with typescript?

I am trying to build an react redux typescript app.我正在尝试构建一个反应 redux typescript 应用程序。

I am using reslect library to create selectors.我正在使用 reslect 库来创建选择器。

I am getting an error while using createStructuredSlectore.使用 createStructuredSlectore 时出现错误。 Please find the error beolow.请在下面查找错误。

Error: No overload matches this call错误:没有重载匹配此调用

Please find the code below:请在下面找到代码:

import React from 'react';
import { connect } from 'react-redux';
import { createStructuredSelector } from 'reselect';

import { toggleDropDown } from '../../redux/cart/cart.actions';
import { selectItemCount } from '../../redux/cart/cart.selectors';

import { ReactComponent as ShoppingIcon } from '../../assets/11.2 shopping-bag.svg.svg';

import './cart-icon.component.scss';

interface ICartIconProps {
    toggleDropDown: () => void;
    itemCount: number;
}

const CartIcon: React.FC<ICartIconProps> = ({toggleDropDown, itemCount}) => (
    <div className='cart-icon' onClick={toggleDropDown}>
        <ShoppingIcon className='shopping-icon'/>
        <span className='item-count'>{itemCount}</span>
    </div>
)

const mapDispatchToProps = (dispatch: import('redux').Dispatch) => ({
    toggleDropDown: () => dispatch(toggleDropDown())
})

// If I use Below code its working fine
// const mapStateToProps = (state: AppState) => ({
//     itemCount: selectItemCount(state)
// })

// Iam getiing error here with below code
const mapStateToProps = createStructuredSelector({
    itemCount: selectItemCount,
})



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

Slectors.ts选择器.ts

import { createSelector } from 'reselect'

import { AppState } from '../store'
import { ShopItem } from '../../models/collection.model'

const selectCart = (state: AppState) => state.cart

export const selectCartItems = createSelector(
  [selectCart],
  cart => cart.cartItems
);

export const selectHidden = createSelector(
  [selectCart],
  cart => cart.hidden
);

export const selectItemCount = createSelector(
  [selectCartItems],
  (cartItems: ShopItem[]) => {
    return cartItems.reduce(
      (accumulatedValue, cartItem) =>
        accumulatedValue + (cartItem.quantity as number),
      0
    )
  }
);

cart.reducer.ts购物车.reducer.ts

import { CartActionsTypes } from "./cart.types";
import { addItemToCart } from "./cart.utils";

const INITIAL_STATE = {
    hidden:  true,
    cartItems: []
};

const cartReducer = (state = INITIAL_STATE, action) => {
    switch (action.type) {
        case CartActionsTypes.TOGGLE_CART_DROPDOWN:
            return {
                ...state,
                hidden: !state.hidden
            }
        case CartActionsTypes.ADD_ITEM:
            return {
                ...state,
                cartItems: addItemToCart(state.cartItems, action.payload)
            }    
        default:
            return state;
    }
}

export default cartReducer;

also It is good to have an example.也有一个例子很好。

What you need to do is pass the correct props to createStructuredSelector() .您需要做的是将正确的道具传递给createStructuredSelector() Simply export the type from the selectors.只需从选择器中导出类型。

selectors.ts选择器.ts

export type ItemCount = ReturnType<typeof selectItemCount>;

Change the interface to a union type and give it to the CartIcon componenent.将接口更改为联合类型并将其提供给 CartIcon 组件。

CartIcon.tsx购物车图标.tsx

import { ItemsCount } from 'selectors';

type CartIconProps = ItemCount & {
    toggleDropdown: () => object
};

Now there shouldn't be any overload from the created selector.现在创建的选择器不应该有任何过载。

const mapStateToProps = createStructuredSelector<AppState, ItemCount>({
    itemCount: selectItemCount,
})

in selector.js file you export itemCount name but in your main file import selectItemCount from selectors.在 selector.js 文件中导出 itemCount 名称,但在主文件中从选择器中导入 selectItemCount。 you should change itemCount name in selector.js to selectItemCount like this:您应该将 selector.js 中的 itemCount 名称更改为 selectItemCount,如下所示:

export const selectItemCount = createSelector([cartItems], (cartItems) => {
    return cartItems.reduce((accumulatedValue, cartItem) => accumulatedValue + cartItem.quantity, 0);
});

OR: you should change your import selectors like this:或者:您应该像这样更改导入选择器:

import { itemCount } from '../../redux/cart/cart.selectors';

const mapStateToProps = createStructuredSelector({
    itemCount: itemCount,
})

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM