You need to enable JavaScript to run this app. React JSON Schema Form提交后如何自动聚焦首个校验错误的表单字段
优惠活动
大模型
产品
解决方案
定价
更多

React JSON Schema Form提交后如何自动聚焦首个校验错误的表单字段

React JSON Schema Form 提交后自动聚焦首个校验失败字段实现方案

以下是三种可直接落地的实现思路,可根据你的项目复杂度选择:

  • 方案1:使用内置onError回调+DOM选择器(轻量场景首选)
    rjsf的Form组件原生提供onError回调,提交校验失败时会触发,回调第一个入参为全量错误数组,默认返回的错误顺序和Schema定义的字段顺序完全一致。
    你可以直接取数组的第一个错误项,通过其property字段拿到对应字段的路径,将路径格式转换为rjsf默认生成的表单元素name属性规则(路径前缀/替换为root_,路径内的/替换为_,比如/username对应root_username),之后直接通过DOM选择器匹配元素调用focus()即可,示例逻辑如下:

    const handleFormError = (errors) => {
      if (!errors.length) return
      const firstErrorPath = errors[0].property
      // 转换为name属性对应值
      const fieldName = firstErrorPath.replace(/^\//, 'root_').replaceAll('/', '_')
      // 匹配第一个可输入元素聚焦
      const targetEl = document.querySelector(`[name="${fieldName}"]`)
      targetEl?.scrollIntoView({ behavior: 'smooth', block: 'center' })
      targetEl?.focus()
    }
    
  • 方案2:自定义字段组件绑定ref(稳定场景首选)
    如果你项目有自定义字段组件的需求,可在封装字段时统一存储所有字段的路径和对应DOM引用,在校验失败时直接通过引用聚焦,不受DOM结构变化影响:

    import { useRef, useEffect } from 'react'
    import Form from "@rjsf/core"
    import validator from "@rjsf/validator-ajv8"
    
    const MyForm = () => {
      // 全局存储所有字段的ref映射
      const fieldRefs = useRef({})
    
      // 封装自定义字段组件
      const WrapField = (FieldComponent) => (props) => {
        const fieldRef = useRef(null)
        // 挂载时存储路径和ref的映射
        useEffect(() => {
          fieldRefs.current[props.id] = fieldRef
          return () => delete fieldRefs.current[props.id]
        }, [props.id])
    
        return <div ref={fieldRef}><FieldComponent {...props} /></div>
      }
    
      // 校验失败回调
      const handleError = (errors) => {
        if (!errors.length) return
        const firstErrorId = errors[0].id
        fieldRefs.current[firstErrorId]?.current?.scrollIntoView({ behavior: 'smooth' })
        fieldRefs.current[firstErrorId]?.current?.querySelector('input,select,textarea')?.focus()
      }
    
      return (
        <Form
          schema={yourFormSchema}
          validator={validator}
          onError={handleError}
          fields={{
            StringField: WrapField(Form.defaultProps.fields.StringField),
            NumberField: WrapField(Form.defaultProps.fields.NumberField),
            BooleanField: WrapField(Form.defaultProps.fields.BooleanField)
          }}
        />
      )
    }
    
  • 方案3:结合transformErrors自定义聚焦优先级
    如果你需要调整聚焦的优先级(比如优先聚焦必填项错误,再聚焦格式错误),可以搭配Form组件的transformErrors属性,先对错误数组按自定义规则排序,之后onError回调中拿到的第一个错误就是你需要优先聚焦的字段。

注意:如果你使用的是rjsf的UI库适配版本(比如Ant Design、MUI适配包),自定义字段时需要对应替换适配包提供的默认字段组件,ref绑定位置需要对准实际的输入元素避免聚焦失效。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.11 23:42:01