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

React Hook Form v7.39.4:跨文件获取useFieldArray的fields正确类型

React Hook Form useFieldArray 类型问题

我希望useFieldArray返回的fields具备正确类型(类似FieldArrayWithId<{name: string; age: number}, "users", "id">[]),这样就能正常映射并访问name和age属性。但在跨文件使用时,fields的类型始终是Record<"id", string>[],无法正确识别子属性。

我已经尝试过以下方案:

  • 在其他文件的useForm中指定泛型
  • 为fields强制断言正确类型
  • 将useFormContext中的control传入useFieldArray(尽管官方文档说明该参数为可选)

解决方案

1. 统一定义表单类型并在根组件useForm中明确指定

先在单独的类型文件(比如types.ts)里定义完整的表单结构:

export type User = {
  name: string;
  age: number;
};

export type FormValues = {
  users: User[];
};

在根组件初始化useForm时,严格传入这个泛型:

import { useForm } from "react-hook-form";
import { FormValues } from "./types";

const { control, register } = useForm<FormValues>({
  defaultValues: {
    users: [{ name: "", age: 0 }]
  }
});

2. 在子组件中为useFieldArray指定泛型

跨文件的子组件里使用useFieldArray时,必须显式传入表单值类型和字段名的泛型参数,确保类型推导正确:

import { useFieldArray, FieldArrayWithId } from "react-hook-form";
import { FormValues, User } from "./types";

const { fields, append, remove } = useFieldArray<FormValues, "users">(
  {
    control, // 必须传入根组件的control,确保上下文类型一致
    name: "users"
  }
);

// 此时fields的类型为FieldArrayWithId<User, "users", "id">[],可直接访问name和age
fields.map((field) => (
  <div key={field.id}>
    <input {...register(`users.${field.id}.name`)} />
    <input type="number" {...register(`users.${field.id}.age`)} />
  </div>
));

3. 依赖正确的上下文传递,避免类型断言

不要用as强制断言fields类型,这会掩盖潜在的类型问题。确保control是从根组件的useForm实例传递过来的(无论是通过props还是FormProvider),这样useFieldArray就能自动继承正确的类型。

如果使用FormProvider,确保根组件的control被正确注入:

import { FormProvider } from "react-hook-form";

// 根组件
const formMethods = useForm<FormValues>({ /* 默认值配置 */ });

return (
  <FormProvider {...formMethods}>
    <UserList />
  </FormProvider>
);

// 子组件UserList
import { useFormContext, useFieldArray } from "react-hook-form";
import { FormValues } from "./types";

const { control } = useFormContext<FormValues>();
const { fields } = useFieldArray<FormValues, "users">({ control, name: "users" });

这样处理后,fields就能正确推导为包含name、age和id的类型数组,无需手动断言。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.11 15:30:49