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

react-hook-form无法校验带defaultValue的react-select控件问题

问题根因

这个问题是react-hook-form结合react-select封装时的典型配置问题,核心原因是react-select的选中值结构、react-hook-form的字段存储值结构、校验规则预期结构三者不匹配,或者初始默认值没有正确同步到react-hook-form的校验状态池。

对应解决方案

1. 统一值结构(最常见场景)

react-select默认接收/返回的选中值是和选项一致的{label: string, value: any}结构,如果你的表单defaultValues里对应字段只存了原始值(比如仅存value字段的字符串/数字),就会出现初始校验识别不到有效值的问题:

  • 优先在表单初始化的defaultValues中直接传入完整的{label, value}结构值,和react-select的返回结构对齐:
const { control, trigger } = useForm({
  defaultValues: {
    // 错误写法:selectField: '1'
    selectField: { label: '默认选项', value: '1' }
  }
})
  • 如果业务逻辑要求只能存储原始值,需要在Controller的render回调中做双向映射:
<Controller
  name="selectField"
  control={control}
  rules={{ required: '请选择选项' }}
  render={({ field }) => (
    <Select
      options={yourOptions}
      // 把form存储的原始值映射为react-select需要的option结构
      value={yourOptions.find(opt => opt.value === field.value)}
      // 选择时仅把value原始值回传给form
      onChange={(val) => field.onChange(val?.value)}
      onBlur={field.onBlur}
    />
  )}
/>

2. 修正字段绑定逻辑

不要给react-select单独设置defaultValue属性,所有默认值统一由react-hook-form的defaultValues声明,通过Controller自动同步,避免两边默认值不一致导致的状态断层。

3. 对齐校验规则

如果使用zod/yup等校验schema,需要确保规则和字段存储的结构匹配:

  • 存完整{label, value}对象时,校验规则要对应声明对象结构:
const formSchema = z.object({
  selectField: z.object({
    label: z.string(),
    value: z.string()
  }, { required_error: '请选择选项' })
})
  • 存原始值时,直接校验对应类型的非空即可:
const formSchema = z.object({
  selectField: z.string({ required_error: '请选择选项' }).nonempty()
})

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.02 03:57:03