如何解决TS2721错误:无法调用可能为null的对象?
解决TS2721: Cannot invoke an object which is possibly 'null'错误
问题根源
你的useLatest钩子初始化时将ref的类型设为T | null,但实际上组件挂载后useLayoutEffect会立即把传入的value赋值给ref.current,且useOnClickOutside中handler是必填的非空函数参数,latestHandler.current理论上永远不会是null,但TypeScript无法自动推断这一点,因此抛出类型错误。
方案1:从根源优化useLatest类型(推荐)
修改useLatest的初始化值和类型定义,去掉null的可能——因为useLayoutEffect会在挂载时同步更新ref.current,初始值直接设为传入的value即可:
export const useLatest = <T>(value: T) => { // 直接用value初始化ref,类型为T而非T | null const ref = useRef<T>(value) useLayoutEffect(() => { ref.current = value }, [value]) return ref }
修改后,latestHandler的类型会变为React.MutableRefObject<(event: MouseEvent) => void>,调用latestHandler.current(event)时将不再触发类型错误。
方案2:调用时添加类型处理(无需修改useLatest)
如果无法修改useLatest的实现,可以在调用前通过以下方式处理null的类型提示:
可选链调用(最简洁)
latestHandler.current?.(event)
类型守卫
if (latestHandler.current) { latestHandler.current(event) }
非空断言(谨慎使用)
若你能确保latestHandler.current绝对不会为null,可以用非空断言跳过TypeScript的检查:
latestHandler.current!(event)
内容的提问来源于stack exchange,提问作者Max
相关产品推荐
相关产品推荐

