Input validation in Google Polymer
For validation settings, Google Polymer inputs (paper-input and others) have these properties
- required
- auto-validate
- error-message
- maxlength
- minlength
- pattern
- allowed-pattern
- validator
plus, this useful property to observe input state:
- invalid
and this method to execute validation:
- validate()
Input settings for validation
required — marks input as required (value length should be not zero)
minlength — the minimum number of characters required to be valid
maxlength — maximum number of characters allowed to type in
pattern — RegEx pattern to validate input value
<paper-input pattern="[A-Z]{2}[0-9]{6}"></paper-input>/**
* For this input “EN123456” is a valid value,
* but "EN123456 " or " EN123456" are invalid values
* because there are extra characters
* and value doesn't match a pattern
*/
allowed-pattern — a pattern to restrict characters allowed to type in
// accepts letters only
<paper-input allowed-pattern="[a-zA-Z]"></paper-input>// accepts digits only
<paper-input allowed-pattern="[0-9]"></paper-input>// accepts nothing, because one character cannot match this pattern
<paper-input allowed-pattern="[0-9][A-Z]"></paper-input>
auto-validate — to execute validation as input value changes
error-message — message to show below input when input value is invalid
validator — custom validator assigned to input (will be described below)
When validation is executed?
- if auto-validate is set — when input value changes
- when you call .validate() method of the input
- when you call .validate() method of the iron-form
- when you submit iron-form by calling .submit() or by clicking submit button
What is done during validation?
Input method .validate() does the following:
- it makes all necessary checks and returns true/false
- it updates “invalid” property of the input (true/false)
- when “invalid” changes — input style changes, error-message is displayed
This is how invalid input looks (of course you can change styling):
How to validate all inputs in a form?
Put your inputs inside iron-form
<form id="form" is="iron-form">
<paper-input id="name" pattern="[A-Z]{2}[0-9]{6}"></paper-input>
<paper-input pattern="[A-Z]{2}[0-9]{6}"></paper-input>
<paper-button on-tap="_submitForm">Submit</paper-button>
</form>
Iron-form has these useful methods:
.validate() — to execute validation on all inputs in the form (returns true/false)
.reset() — to reset all changes done in the form (resets values and validation statuses)
.submit() — to submit a form, with all validations checked
How to reset input state from invalid to default?
In single-page applications you sometimes need to reset input state if user navigates away from your form.
Iron-form has .reset() method, but inputs don’t have .reset() method. To reset input state, you should change “invalid” value to false.
this.$.name.invalid = false;
Custom validator
If you want to use some JavaScript function to validate your input value, you should create custom validator and provide it to the input.
Custom validator — it’s element which should have:
- Polymer.IronValidatorBehavior
- validate() method returning true/false
- validator-name assigned
This is example of custom-validator element:
<dom-module id="my-validator">
<script>
(function() {
'use strict'; Polymer({
is: ‘my-validator’,
behaviors: [
Polymer.IronValidatorBehavior
],
validate: function(value){
return value % 3 === 0;
}
}) })()
</script>
</dom-module>
and this is how this custom-validator can be assigned to an input:
<my-validator validator-name="validator1"></my-validator>
<paper-input validator="validator1"></paper-input>
As you see, validator-name identifies a validator, not ID.
One custom validator for many functions
There exists a practice to make custom-validator element without .validate() function, and to assign .validate() function in .attached().
So, you can use single cusom-validator element but replace its .validate() functions when validator is inserted into DOM.
Example:
<custom-validator id="v1" validator-name="validator1"></custom-validator>
...
<custom-validator id="v2" validator-name="validator2"></custom-validator>
....
attached: function(){
this.$.v1.validate = (value) => value % 3 == 0;
this.$.v2.validate = (value) => value % 5 == 0;
}
This is useful if you have some library with functions (or share functions between backend and frontend), and you don’t want to create a custom-validator for each of those functions.
…
That’s all for now.
Here are some examples of validations on CodePen:
Password and repeat-password validation in Google Polymer
Happy validating!
P.S. What I really miss in Google Polymer validations
In Angular 2, inputs can be not only valid and invalid. There, you can also know if input was touched/untouched and if it’s dirty or pristine (changed or not).
For example, to show green checkbox next to the input when user entered valid value, it’s not enough to know that “invalid” is false (maybe input was not validated yet, right?). Green checkbox should be shown only if input value was changed.
So, it would be great to have “dirty” property in inputs. Of course you can always extend paper-input yourself to introduce that.