PropType.shape({}) 失败警告:无效类型

时间:2021-08-01 18:40:53

标签: reactjs react-redux axios react-proptypes

我正在尝试从 PropType 设置道具的 Redux-State,它是一个看起来像这样的对象:

sDate = {
        all_day: true,                               //bool
        category: "sCategory",                       //string
        created_at: "2021-07-31T10:06:02.545637Z",   //string
        description: "sDescribtion",                 //string
        end: Sat Jul 31 2021 14:05:00 GMT+0200       //Date
        id: 49,                                      //number
        start: Sat Jul 31 2021 16:05:00 GMT+0200     //Date
        title: "sTitle",                             //string
        type: "sType",                               //string
}

至少,在 axios.get 之前的 dispatch 请求函数中是这样的。我还可以读出组件内部对象的内容。我在函数组件中使用它,如下所示。

首先,我尝试将其设置为 PropType.object.isRequired,但收到警告

Warning: Failed prop type: Invalid prop `sDate` of type `array` supplied to `EditDate`, expected `object`.

更改为 PropType.array.isRequired 导致警告

Warning: Failed prop type: Invalid prop `sDate` of type `object` supplied to `EditDate`, expected `array`.

那时我决定使用 PropTypes.shape({})

下面,您可以看到具有当前 PropTypes 设置的功能组件

function EditDate(props) {

    useEffect(() => {
        props.getSingleDate(id)
    },[])

    const { id } = useParams();

    return (
        <Fragment>
         ...
        </Fragment>
    );
}

EditDate.propTypes = {
    getSingleDate: PropTypes.func.isRequired,
    deleteDate: PropTypes.func.isRequired,
    sDate: PropTypes.shape({
        all_day: PropTypes.bool.isRequired,
        category: PropTypes.string.isRequired,
        created_at: PropTypes.string,
        description: PropTypes.string.isRequired,
        end: PropTypes.instanceOf(Date).isRequired,
        id: PropTypes.number.isRequired,
        start: PropTypes.instanceOf(Date).isRequired,
        title: PropTypes.string.isRequired,
        type: PropTypes.string.isRequired,
    }),
};

const mapStateToProps = state => ({
    sDate: state.dateReducer.dates
});

export default connect(
    mapStateToProps,
    { getSingleDate, deleteDate }
)(EditDate);


我仍然收到警告

Warning: Failed prop type: Invalid prop `sDate` of type `array` supplied to `EditDate`, expected `object`.

我做错了什么?

我也尝试过更改 Redux-Reducer,因为它可能设置错误:

const initialState = {
    dates: []               //  <-- does this determin what React expects?
};

export default function(state = initialState, action) {
    switch (action.type) {
        case GET_DATES:
            return {
                ...state,
                dates: action.payload
            };
        case GET_SINGLE_DATE:
            state.dates = Object    //  <-- this had no effect in the matter discussed
            return {
                state,
                dates: action.payload
            };
            ...

在上面的示例中,在 case GET_DATES 中,action.payload 作为相应组件中的道具没有任何问题(在那里,PropTypes.array 有效)。


编辑:

这有效:

sDate: PropTypes.oneOfType([PropTypes.array, PropTypes.object]).isRequired,

谁能给我解释一下为什么? docs 有点含糊。


编辑 2:

我必须更正 Redux Reducer 中的一个逻辑错误:GET_DATESGET_SINGLE_DATE 确实应该在 Redux 状态中有自己的表示:

const initialState = {
    dates: [],                
    sDate: []                
};
...
...
        case GET_SINGLE_DATE:
            return {
                state,
                sDate: action.payload
            };
            ...

编辑 3:

正如下面的回答中所解释的,我不得不更改 Reducer 的 initialSate,i.o.使其正常工作:

const initialState = {
    dates: [],                
    sDate: {}      //now, the initial state is an object, too                
};

因此,要正确使用它:

EditDate.propTypes = {
...
  sDate: PropType.object.isRequired,
...
}

1 个答案:

答案 0 :(得分:1)

如果我理解得很好,我们有一个 date 变量,它是一个空数组作为初始状态。因此,在 api 调用发生之前,应用程序将理解此变量是一个数组。在 api 调用之后,我们正在接收一个对象并将数组替换为数据值。所以我们在这里改变了类型,这会产生警告。

使用时

sDate: PropTypes.oneOfType([PropTypes.array, PropTypes.object]).isRequired,

你只是说你对这个变量的两种类型都没有问题,这消除了警告,但这并不理想。

为了正确解决这个问题,你只需要把一个空对象作为初始状态,这样这个变量就会在api调用前后都是一个对象。