React Native+TS项目中特定页面如何声明Redux的user不可能为null?
针对该场景的四种可行方案
1. 路由层拦截+组件内兜底校验(最推荐)
在路由访问控制逻辑中提前判断user是否为null,未登录用户直接拦截跳转至登录页,无法进入Settings等需授权页面。同时在Settings组件开头加一层逻辑兜底,TS会自动将后续代码中的user类型收窄为User:
const Settings = () => { const user = useSelector(selectUser); // 该分支理论上永远不会触发,仅作为兜底校验 if (!user) { return <Redirect to="/sign-in" />; } // 此处访问user.id不会触发TS报错 return <Text>用户ID:{user.id}</Text> }
这种方案兼顾类型安全和线上鲁棒性,就算后续路由拦截逻辑出现疏漏,也不会出现空指针报错。
2. 封装专属授权hooks
如果有多个需要登录才能访问的页面,可以统一封装专用的hooks,避免每个页面重复写校验逻辑:
// 全局封装hooks const useAuthorizedUser = () => { const user = useSelector(selectUser); if (!user) { throw new Error("未登录状态下无法访问授权资源"); } return user; } // Settings页直接调用 const Settings = () => { const user = useAuthorizedUser(); // 返回值类型直接为User,无null可能 return <Text>用户ID:{user.id}</Text> }
3. 改造reselect选择器
针对授权场景单独封装selector,内部做非空校验,返回值直接定义为User类型:
const selectAuthorizedUser = createSelector( selectRootUser, // 原有的返回User|null的selector (user) => { if (!user) throw new Error("用户未登录"); return user; } )
所有需授权页面直接调用该selector即可,无需额外处理类型问题。
4. 非空断言(快速临时方案)
如果100%确认当前场景下user不可能为null,可以直接使用TS的非空断言操作符!告知编译器该值非空:
const userId = user!.id;
该方案改动量最小,但不建议大面积使用,避免后续业务逻辑变动后出现预期外的空指针问题。
内容的提问来源于stack exchange,提问作者Dennis S
相关产品推荐
相关产品推荐

