Writing form components using Async-validator

Source: Internet
Author: User
Tags emit
This article mainly introduces the method of using Async-validator to write Form components, small series feel very good, and now share to everyone, but also for everyone to do a reference. Follow the small series together to see it, hope to help everyone.

In front-end development, the validation of forms is a very common feature, and some UI libraries such as ant.design and element UI implement a form component that has a checksum capability. Async-validator is a library that can perform asynchronous validation of data, and the Form component of Ant.design and Element UI uses Async-validator. This article briefly introduces the basic usage of async-validator and the use of the library to implement a simple verification function of the Form component.

1. Basic usage of Async-validator

The function of the async-validator is to verify that the data is legitimate and to give a hint based on the validation rules.

Here's a demonstration of the most basic usage of async-validator.


Import asyncvalidator from ' async-validator '//Check rule const DESCRIPTOR = {Username: [{  required:true,  message: ' Please fill in Write user name '}, {  min:3,  max:10,  message: ' Username length 3-10 '}]}//constructs a validatorconst validator = new Asyncvalida based on the validation rules Tor (descriptor) const DATA = {username: ' username '}validator.validate (model, (errors, fields) = {Console.log (errors )})

When the data does not conform to the validation rules, in the Validator.validate callback function, you can get the corresponding error message.

We can write a custom checksum function to validate the data when the validation rules that are common in async-validator do not meet the requirements. A simple check function is as follows.


function validatedata (rule, value, callback) {Let err if (value = = = ' xxxx ') {  err = ' does not conform to spec '} callback (err)}const de Scriptor = {complex: [  {  validator:validatedata  }]}const validator = new Asyncvalidator (descriptor)

Async-validator supports asynchronous validation of data, so when you write a custom check function, the callback in the checksum function is called, regardless of whether the checksum is passed.

2. Writing Form components and FormItem components

Now that you know how to use async-validator, how do you combine this library with the Form component that you want to write?

Implementation ideas

Describe the implementation idea in a picture.

Form components

The Form component should be a container containing an indefinite number of FormItem or other elements. You can use Vue's built-in slot components to represent the contents of a Form.

The Form component also needs to know how many FormItem components are included that require validation. In general, the communication of a parent-child component is implemented by binding an event on a subassembly, but the slot is used here to not hear the child component's events. This allows you to listen for events through $on on the form component, FormItem the custom events that trigger the Form component before mounting or destroying it.

According to this idea, we first write the Form component.


<template> <form class= "V-form" > <slot></slot> </form> </template><script >import asyncvalidator from ' async-validator ' export default {name: ' V-form ', componentname: ' Vform ',//through $options. Co   Mponentname to find the form component data () {return {fields: [],//field: {prop, El}, save FormItem information. Formerror: {}}}, computed: {formrules () {Const DESCRIPTOR = {} This.fields.forEach (({prop}) + = {if (!  Array.isarray (This.rules[prop])) {Console.warn (' Prop for ${prop} ' does not exist or its value is not an array ') FormItem] = [{   Required:true}] return} Descriptor[prop] = This.rules[prop]}) return descriptor}, Formvalues () {   Return This.fields.reduce ((data, {prop}) = = {Data[prop] = This.model[prop] Return data}, {})}}, methods: { Validate (callback) {Const VALIDATOR = new Asyncvalidator (this.formrules) validator.validate (This.formvalues, (Erro RS) = = {Let Formerror = {} if (Errors && erRors.length) {Errors.foreach (({message, field}) = {Formerror[field] = message})} else {FormEr Ror = {}} this.formerror = Formerror//Let the order of the error messages be the same as the order of the form components const ERRINFO = [] This.fields.forEach ({prop,  El}, Index) = {if (Formerror[prop]) {Errinfo.push (Formerror[prop])}}) callback (Errinfo)}) }, Props: {model:object, Rules:object}, created () {this. $on (' Form.addfield ', (field) = {if (field) {T  His.fields = [... this.fields, Field]}}) this. $on (' Form.removefield ', (field) = {if (field) {This.fields = This.fields.filter (({prop}) = Prop!== Field.prop)})}}</script>

FormItem components

The FormItem component is much simpler, first to find the Form component that contains it. Next, you can calculate the corresponding error message based on the formerror.


<template> <p class= "Form-item" >  <label:for= "prop" class= "Form-item-label" v-if= "label" >   {{label}}  </label>  <p class= "form-item-content" >   <slot></slot>  </p> </p></template><script>export Default {name: ' Form-item ', computed: {  form () {   Let parent = the $parent while   (parent $options. ComponentName!== ' Vform ') {    parent = parent. $parent   }< C12/>return parent  },  Fielderror () {   if (!this.prop) {    return '   }   const FORMERROR = This.form.formError   return Formerror[this.prop] | | "}  , props: {  prop:string,  label:string}}</script>

FormItem also needs to trigger some custom events for the Form component in mounted and Beforedestroy hooks.


<script>export default {//... methods: {  dispatchevent (eventName, params) {   if (typeof this.form!== ' obj ECT ' &&!this.form $emit) {    console.error (' Formitem must be within the form component ')    return   }   this.form. $emit ( EventName, params)  }}, mounted () {  if (this.prop) {   this.dispatchevent (' Form.addfield ', {    prop: This.prop,    el:this. $el   })  }, Beforedestroy () {  if (this.prop) {   this.dispatchevent (' Form.removefield ', {    prop:this.prop   })  }}}</script>

Finally, create a new index.js to export the well-written components.


Import Vform from './form.vue ' import FormItem from './formitem.vue ' export {vform, FormItem}

3. How to use

The check function for the form is in the form component. By $ref, you can access the Form component and call the Validate function to obtain the appropriate checksum information.

Here's how to use it:


<template> <v-form:model= "FormData": rules= "Rules" ref= "form" >  <form-item label= "phone number" prop= "Tel" >   <input type= "Tel" maxlength= "one" v-model.trim= "Formdata.tel"/>  </form-item>  < Button @click = "Handlesubmit" > Save </button> </v-form></template><script> Import {vform,  FormItem} from './common/form ' export default {  data () {   return {    formData: {     Tel: '    },    rules: {     Tel: [      {required:true, message: ' Your phone number is not entered '},      {pattern:/^1[34578]\d{9}$/, message: ' Your mobile phone number entered incorrectly '}< c13/>]}}  ,  methods: {   Handlesubmit () {this    . $refs. Form.validate (errs = {     Console.log (errs)}    )}   , Components  : {   vform,   FormItem  }}</script >

Click here for the complete code.

4. Summary

This paper introduces briefly the usage of Async-validator, and realizes a Form component with calibration function. There are a lot of deficiencies in the form form that is implemented here: (1) The verification is only available when the form is submitted. (2) The FormItem component should also adjust the UI based on the results of the verification, giving the appropriate hints. Therefore, the Form component is more suitable for use on mobile side with less interaction.

According to the implementation of this idea, according to the application scenario, you can write a custom higher Form component.

Related Article

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.