组件解构时Discriminating Union出现类型错误求助
解决联合类型组件解构时的TS属性不存在错误
你定义的IInfoBoxProps是WithAction和WithoutAction的联合类型,直接解构时TS会报错,核心原因是:customActionComponent、actionComponentPosition、actionBtnText、clickHandler这些属性仅存在于WithAction接口中,WithoutAction里完全没有,TS无法确定这些属性一定存在;另外你给isActionBtnRequired设置默认值true也不合理——联合类型里这个字段是明确的true或false,并非可选属性。
解决思路与步骤
- 用
isActionBtnRequired做类型守卫,自动区分两种类型的props - 仅在对应分支中访问专属属性,避免跨分支访问不存在的字段
- 将默认值设置在对应分支内,遵循TS的类型检查规则
修改后的完整代码
import * as React from "react"; import { ReactNode } from "react"; import "./styles.css"; interface WithAction { isActionBtnRequired: true; content: string; containerClass?: string; customActionComponent?: ReactNode; actionComponentPosition?: ActionComponentPosition; actionBtnText?: string; clickHandler?: () => void; } interface WithoutAction { isActionBtnRequired: false; content: string; containerClass?: string; } type IInfoBoxProps = WithAction | WithoutAction; type ActionComponentPosition = "floating-right" | "next-to-content"; export const App = (props: IInfoBoxProps) => { // 先解构所有分支共有的属性 const { containerClass = "", content, isActionBtnRequired } = props; // 类型守卫:处理需要操作组件的情况 if (isActionBtnRequired) { // TS自动收窄props为WithAction类型,可安全解构专属属性 const { customActionComponent = null, actionComponentPosition = "floating-right", actionBtnText = "", clickHandler } = props; const renderActionBtn = (): ReactNode => customActionComponent ? customActionComponent : ( <button onClick={clickHandler} className="info-box-action-button"> {actionBtnText} </button> ); return ( <div className={`info-box-container ${containerClass}`}> <div className="info-box-section"> <span className="info-box-icon">icon</span> <div className={`${ actionComponentPosition === "floating-right" ? "info-box-text-stretch" : "info-box-text" }`} > <span>{content}</span> </div> {renderActionBtn()} </div> </div> ); } else { // 处理不需要操作组件的情况 return ( <div className={`info-box-container ${containerClass}`}> <div className="info-box-section"> <span className="info-box-icon">icon</span> <div className="info-box-text"> <span>{content}</span> </div> </div> </div> ); } };
关键细节说明
- 类型守卫的作用:当判断
isActionBtnRequired === true时,TS会自动将props的类型收窄为WithAction,此时解构该接口的专属属性不会触发类型错误。 - 分支化渲染:将两种场景的渲染逻辑拆分,既符合TS的类型规则,也让代码逻辑更清晰。
- 默认值的合理放置:仅在
WithAction分支内设置该类型专属属性的默认值,避免全局解构时访问不存在的字段。
内容的提问来源于stack exchange,提问作者user16860065
相关产品推荐
相关产品推荐

