You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何调用自定义React Hook返回的函数?排查Invalid hook call错误

问题原因

你的代码存在3处核心错误,直接触发了你遇到的两个异常:

  • 调用自定义Hook时违反React Hook规则:你定义的Hook名称为useCheckUnique,调用时错写为CheckUnique,且没有在函数组件顶层作用域调用,直接触发*Invalid hook call. Hooks can only be called inside of the body of a function component.*报错,同时导致返回值异常(出现嵌套函数的对象而非预期的校验函数)。
  • Hook入参类型定义错误:param: keyof typeof self写法完全不成立,self被定义为number | string类型,不存在可提取的属性键,会导致类型校验失效。
  • 传参逻辑错误:你定义的校验逻辑里是对比x.id !== self,但调用时传入的第三个参数是整个item对象而非item.id,会导致唯一性判断逻辑永远不成立。
修正方案
  1. 严格遵循React Hook调用规则:所有use开头的自定义Hook,必须在函数组件/自定义Hook的顶层作用域调用,不能放在回调、条件判断、循环里调用,调用时不能省略use前缀。
  2. 修正Hook的入参类型定义,用泛型约束数组元素类型,保证param参数是数组元素的合法字段。
  3. 调用Hook时第三个参数传入当前编辑项的id,而非整个项对象;用useCallback包裹校验函数,避免每次组件渲染生成新的函数引用,触发不必要的重渲染。
修正后完整代码

自定义Hook定义

import { useCallback } from 'react';
// 按项目实际路径引入useSnack
// import { useSnack } from '@/hooks/useSnack';

export const useCheckUnique = <T extends { id?: string | number }>(
  items: T[],
  param: keyof T,
  currentId: string | number,
) => {
  const { showToast } = useSnack();

  const isUnique = useCallback((currentValue: T[keyof T]) => {
    const isExist = items.some(item => item[param] === currentValue && item.id !== currentId);
    if (isExist) {
      showToast({
        text: `wizard:${String(param)}_NOT_UNIQUE`,
        variant: 'danger',
      });
      return false;
    }
    return true;
  }, [items, param, currentId, showToast]);

  return isUnique;
};

组件内调用示例

// 以下代码写在函数组件的顶层作用域,不要写在update等回调函数内
const items = [{id:1, value: 2}, {id:2, value:7}, {id:3, value: 9}];
const currentEditItem = {id:2, value:7};
// 正确调用Hook:注意use前缀,第三个参数传id而非整个对象
const checkValueAvailable = useCheckUnique(items, 'value', currentEditItem.id);

// 渲染部分
<EntityFieldsetItem
  title="example"
  value={value}
  update={(newValue) => {
    if (checkValueAvailable(newValue)) {
      // 执行正常更新逻辑
    }
  }}
/>

内容的提问来源于stack exchange,提问作者coolps811

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.01 22:36:36