深入掌握ant-design的form异步校验(一)

简介: 本文适合对ant-design的表单校验感兴趣的小伙伴阅读~

一、前言


本文基于开源项目:

https://github1s.com/ant-design/ant-design

https://github.com/yiminghe/async-validator

很多小伙伴对antd的form表单校验不是很清楚,有些时候写了一些校验规则然后不是自己想要实现的效果、或者不清楚校验规则是什么无从写起。

下面我们一起来学习学习form的校验~


二、validateFields


广东靓仔从文档找了个demo,代码如下:


<Form form={form} initialValues={{ aaa: '2' }}>
  <Form.Item name="aaa">
    <Input
      onChange={async () => {
        await sleep(0);
        try {
          await form.validateFields();
        } catch (e) {
        // do nothing
      }
     }}
    />
  </Form.Item>
<Form>


我们来看看validateFields的返回示例:

validateFields()
  .then(values => {
    /*
  values:
    {
      username: 'username',
      password: 'password',
    }
  */
  })
  .catch(errorInfo => {
    /*
    errorInfo:
      {
        values: {
          username: 'username',
          password: 'password',
        },
        errorFields: [
          { name: ['password'], errors: ['Please input your Password!'] },
        ],
        outOfDate: false,
      }
    */
  });

AntDesign的表单校验是基于async-validator,是支持异步校验的。  


三、async-validator介绍


官方介绍:Validate form asynchronous.简单理解:async-validator是一个表单的异步验证的第三方库。


安装

npm i async-validator


使用

它基本用法包括定义描述符,将它分配给模式并将要验证的对象和回调函数传递给validate模式的方法:


import Schema from 'async-validator';
const descriptor = {
  name: {
    type: 'string',
    required: true,
    validator: (rule, value) => value === 'muji',
  },
  age: {
    type: 'number',
    asyncValidator: (rule, value) => {
      return new Promise((resolve, reject) => {
        if (value < 18) {
          // reject错误信息
          reject('too young');
        } else {
          resolve();
        }
      });
    },
  },
};
const validator = new Schema(descriptor);
validator.validate({ name: 'muji' }, (errors, fields) => {
  if (errors) {
    // 验证失败,errors 是一个包含所有错误的数组
    // fields 是一个以字段名称为键的对象
    // errors per field
    return handleErrors(errors, fields);
  }
  // 这里则是验证通过
});
// PROMISE USAGE
validator.validate({ name: 'muji', age: 16 }).then(() => {
  // 验证通过或没有错误消息
}).catch(({ errors, fields }) => {
  return handleErrors(errors, fields);
});


简单梳理下:传入验证规则对象,可以新建一个验证器对象验证器对象的validate方法用于验证数据是否符合验证规则。


Validate有三个参数:

  • source:要验证的对象(必需)。
  • options:描述验证处理选项的对象(可选)。
  • callback:验证完成时调用的回调函数(可选)。


可以看出Validate返回了一个Promise 对象


rules规则

function(rule, value, callback, source, options)
  • rule:源描述符中的验证规则,对应于正在验证的字段名称。它总是被分配一个field带有被验证字段名称的属性。
  • value:正在验证的源对象属性的值。
  • callback:验证完成后调用的回调函数。它期望传递一个Error实例数组来指示验证失败。如果检查是同步的,可以直接返回一个falseorErrorError Array
  • source:传递给validate方法的源对象。
  • options:其他选项。
  • options.messages:包含验证错误消息的对象,将与 defaultMessages 深度合并。


传递给validateasyncValidate传递给验证函数的选项,以便在验证函数中引用瞬态数据(例如模型引用)。但是,保留了一些选项名称;如果使用选项对象的这些属性,它们将被覆盖。保留的属性messagesexceptionerror


我们经常写rules为对象数组,针对单个字段的多个验证规则进很有用:

const descriptor = {
  email: [
    { type: 'string', required: true, pattern: Schema.pattern.email },
    { 
      validator(rule, value, callback, source, options) {
        const errors = [];
        // 测试邮箱地址是否已经存在于数据库中
        // 如果确实则将验证错误添加到错误数组
        return errors;
      },
    },
  ],
};


type类型

可以使用的类型如下:

  • string: 必须是类型stringThis is the default type.
  • number: 必须是类型number
  • boolean: 必须是类型boolean
  • method: 必须是类型function
  • regexp: 必须是RegExp创建新的时不产生异常的实例或字符串RegExp
  • integer: 必须是类型number和整数。
  • float: 必须是类型number和浮点数。
  • array: 必须是由 确定的数组Array.isArray
  • object: 必须是 typeobject而不是Array.isArray
  • enum: 值必须存在于enum.
  • date:值必须是有效的,由Date
  • url: 必须是类型url
  • hex: 必须是类型hex
  • email: 必须是类型email
  • any: 可以是任何类型。

asyncValidator异步验证器

我们可以自定义指定字段的异步验证功能,代码如下:

const fields = {
  asyncField: {
    asyncValidator(rule, value, callback) {
      ajax({
        url: 'xx',
        value: value,
      }).then(function(data) {
        callback();
      }, function(error) {
        callback(new Error(error));
      });
    },
  },
  promiseField: {
    asyncValidator(rule, value) {
      return ajax({
        url: 'xx',
        value: value,
      });
    },
  },
};


validator验证器

我们可以为指定字段自定义验证功能,代码如下:

const fields = {
  field: {
    validator(rule, value, callback) {
      return value === 'test';
    },
    message: 'Value is not equal to "test".',
  },
  field2: {
    validator(rule, value, callback) {
      return new Error(`${value} is not equal to 'test'.`);
    },
  },
  arrField: {
    validator(rule, value) {
      return [
        new Error('Message 1'),
        new Error('Message 2'),
      ];
    },
  },
};


四、总结


   在我们阅读完官方文档后,我们一定会进行更深层次的学习,比如看下框架底层是如何运行的,以及源码的阅读。


  这里广东靓仔给下一些小建议:

  • 在看源码前,我们先去官方文档复习下框架设计理念、源码分层设计
  • 阅读下框架官方开发人员写的相关文章
  • 借助框架的调用栈来进行源码的阅读,通过这个执行流程,我们就完整的对源码进行了一个初步的了解
  • 接下来再对源码执行过程中涉及的所有函数逻辑梳理一遍
相关文章
|
JavaScript 前端开发 容器
Vue antdv 下拉菜单不跟着滚动走(getPopupContainer 使用)
Vue antdv 下拉菜单不跟着滚动走(getPopupContainer 使用)
2082 0
|
前端开发
websocket的心跳机制
websocket的心跳机制
1655 3
|
JavaScript 前端开发 容器
Vue生成PDF文件攻略:html2canvas与jspdf联手,中文乱码与自动换行难题攻克
Vue生成PDF文件攻略:html2canvas与jspdf联手,中文乱码与自动换行难题攻克
2198 0
|
JavaScript
vue2路由懒加载解决import引入报错问题
本文介绍了在Vue2项目中实现路由懒加载的方法,并解决了使用import语句进行懒加载时报错的问题。通过安装`babel-plugin-syntax-dynamic-import`插件并在项目的`.bablerc`文件中配置,可以成功实现路由组件的按需加载。同时,文章还提到了使用`webpackChunkName`为懒加载的组件指定单独的chunk名称,以避免所有组件被打包到同一个js文件中。
1121 4
|
JavaScript 前端开发
JS中find的用法
JS中find的用法
561 0
|
JavaScript UED
以 Vue 3 项目为例,多个请求下如何全局封装 Loading 的展示与关闭?其中大有学问!
以 Vue 3 项目为例,多个请求下如何全局封装 Loading 的展示与关闭?其中大有学问!
|
JavaScript
js将数组转为字符串用逗号隔开,字符串转数组
js将数组转为字符串用逗号隔开,字符串转数组
661 1
|
JavaScript API 索引
js中的reduce()方法 讲解 和实现
`reduce()` 方法对数组元素依次应用一个回调函数,将结果累计并最终返回单一值。语法为 `reduce(callback(accumulator, currentValue, currentIndex, array), initialValue)`。参数包括累计器(初次为初始值或首元素)、当前元素值、索引及数组自身。此方法需返回值供下一轮迭代使用。常见应用场景包括计算数组总和与平均值、统计元素频率、过滤与转换数组内容及去除重复项等。例如,可通过 `reduce()` 快速计算 `[1, 2, 3, 4, 5]` 的总和或对对象属性值求和。此外,还可自定义实现 `reduce()` 方法
6834 1
|
JSON JavaScript 前端开发
dayjs 中文文档
dayjs 中文文档
1664 0

热门文章

最新文章