简体   繁体   中英

How to descturcture an object in Typescript when properties are optional?

I have a generic component which has some optional properties, I need to destructure props but I get errors

    interface IScenarioPageProps extends IScenarioStateWithDispatch {
    isOverlayVisible?: boolean;
    renderOverlayContent?: () => void;
}

const Page = (props: IStepStateWithDispatch | IScenarioPageProps | ITaskStateWithDispatch) => {
    const { taskState, stepState, isOverlayVisible, renderOverlayContent } = props;
    const { selectedTaskId, selectedTask } = taskState;
    const { selectedStepId, selectedStep } = stepState;

    const style = StyleSheet.create({
        content: {
            'background-color': getTheme().palette.white,
            height: '100vh'
        }
    });

    return (
        <div className={css(style.content)}>
            {isOverlayVisible && <Modal>{renderOverlayContent()}</Modal>}
        </div>
    );
};

export default Page;

How can I destructure those optional properties without getting Typescript error?

在此处输入图片说明

Because the Page component uses the renderOverlayContent prop regardless and the prop isn't presented in the IStepStateWithDispatch or ITaskStateWithDispatch type (that's the reason of the error), I can make a assumption that you want the Page component to require all the props of the interfaces IStepStateWithDispatch , IScenarioPageProps and ITaskStateWithDispatch .

If my assumption is correct, then you need to replace | with & in the props type declaration. It will tell TypeScript that the props object has the properties from all the interfaces.

const Page = (props: IStepStateWithDispatch & IScenarioPageProps & ITaskStateWithDispatch) => {
    // ...
}

If my assumption is not correct (the component is polymorphic), then you need to check that the renderOverlayContent prop is given and then use it:

// ...

// const {renderOverlayContent} = props; // Remove this

return (
    <div className={css(style.content)}>
        {isOverlayVisible &&
            <Modal>
                {'renderOverlayContent' in props && props.renderOverlayContent && props.renderOverlayContent()}
            </Modal>
        }
    </div>
);

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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