Showing posts with label angular-validation. Show all posts
Showing posts with label angular-validation. Show all posts
angular-validation

angular-validation

June 27, 2017
Client-side Validation should be simple and clean.
Don't let Client-side Validation dirty your controller.

Setup your Validation on config phase by using some rules (example) If you prefer schema over html attributes , try angular-validation-schema (Demo) And add Validation in your view only. angularjs 1.2.x support to version angular-validation 1.2.x
angularjs 1.3.x support after version angular-validation 1.3.x
angularjs 1.4.x support after version angular-validation 1.4.x

Requirement

AngularJS 1.2.x (for angular-validation 1.2.x)
AngularJS 1.3.x (for angular-validation 1.3.x)
AngularJS 1.4.x (for angular-validation 1.4.x)

DEMO

http://hueitan.github.io/angular-validation/

Install

Install with npm
 npm install angular-validation  
or with bower
 bower install angular-validation  

Using angular-validation

 <script src="dist/angular-validation.js"></script>  
 <script src="dist/angular-validation-rule.js"></script>  
 angular.module('yourApp', ['validation']);  
 // OR including your validation rule  
 angular.module('yourApp', ['validation', 'validation.rule']);  

Writing your First Code

 <form name="Form">  
   <div class="row">  
     <div>  
       <label>Required</label>  
       <input type="text" name="required" ng-model="form.required" validator="required">  
     </div>  
     <div>  
       <label>Url</label>  
       <input type="text" name="url" ng-model="form.url" validator="required, url">  
     </div>  
     <button validation-submit="Form" ng-click="next()">Submit</button>  
     <button validation-reset="Form">Reset</button>  
   </div>  
 </form>  

API


Add Valid Message (error, success) for validation required

required-error-message and required-success-message
 <label>Required</label>  
 <input type="text"  
     name="require"  
     ng-model="form.required"  
     validator="required"  
     required-error-message="Required"  
     required-success-message="Good Required"/>  
     <!-- or you can try  
     required-error-message="{{ RequiredMsg }}"  
     -->  

Add Valid Message (error, success) for validation email

email-error-message and email-success-message
 <label>Email</label>  
 <input type="text"  
     name="email"  
     ng-model="form.email"  
     validator="email"  
     email-error-message="Error Email"  
     email-success-message="Good Email"/>  

Use Default Valid Message

You don't need to give valid message - the valid/invalid message will be automatically placed next to your input element.
 <label>Number</label>  
 <input type="text" name="number" ng-model="form.number" validator="number"/>  

Use Custom Default Valid/Invalid Message

You can customize the default valid/invalid message that will be automatically placed next to your input element.
 <script>  
   $validationProvider.setDefaultMsg({  
     minlength: {  
       error: function (element, attrs, param) {  
         return 'A minimum of ' + param + ' characters is required.';  
       }  
     }  
     , maxlength: {  
       error: function (element, attrs, param) {  
         return 'A maximum of ' + param + ' characters is required.';  
       }  
     }  
   });  
 </script>  
 <label>Username</label>  
 <input type="text" name="username" ng-model="form.username" validator="minlength=5"/>  

Use a custom Valid Message

You can also add a custom validation message by using message-id attribute. It allows you to place a valid/invalid message wherever you want, a target element must specify an id attribute that matches with a value of the message-id.
 <label>Number</label>  
 <input type="text" name="number" ng-model="form.number" validator="number" message-id="message"/>  
 <span id="message"></span>  

Use a validation group

You can also add a validation-group directive to group many elements into a group. The group will be considered as valid if and only if one of them is valid. Otherwise, the group will be marked as invalid. A valid/invalid message will be placed inside an element that contains an id attribute with the same name as provided to the directive validation-group.
 <label>Validation group</label>  
 <!-- Group both of these elements inside the contact group -->  
 <input type="text" name="email" ng-model="email" validator="required" validation-group="contact">   
 <input type="number" name="telephone" ng-model="telephone" vaalidator="number" validation-group="contact">  
 <!-- The message will be placed in side the span element -->  
 <span id="contact"></span>  

Don't show the Valid Message no-validation-message="true"

 <label>Number</label>  
 <input type="text" name="number" ng-model="form.number" validator="number" no-validation-message="true"/>  
 <!-- or {{ your.Scope.Name }} -->  
 <input type="text" name="number" ng-model="form.number" validator="number" no-validation-message="{{ noValidationMessage }}"/>  

Add Valid Callback Function, invalid-callback & valid-callback

 <label>Required (Invalid Callback alert)</label>  
 <input type="text" name="requiredCallback" ng-model="form.requiredCallback" validator="required" invalid-callback='error("Must be Required");'/>  

Select the validation method watch blur submit submit-only, default as watch

validationProvider.validate(form).success(callback).error(callback) use callback to continue your submit
 <label>Watch method</label>  
 <input type="text" name="number" ng-model="form.number" validator="number" valid-method="watch"/>  
 <input type="text" name="number" ng-model="form.number" validator="number"/>  
 <label>Blur method</label>  
 <input type="text" name="number" ng-model="form.number" validator="number" valid-method="blur"/>  
 <!-- or try ng-model-options="{ updateOn: 'blur' }" -->  
 <input type="text" name="number" ng-model="form.number" validator="number" ng-model-options="{ updateOn: 'blur' }"/>  
 <label>Submit method</label>  
 <form name="Form">  
   <input type="text" name="number" ng-model="form.number" validator="number" valid-method="submit"/>  
   <button ng-click="form.submit(Form)"></button>  
 </form>  
 <label>Submit Only method</label>  
 <form name="Form">  
   <input type="text" name="number" ng-model="form.number" validator="number" valid-method="submit-only"/>  
   <button ng-click="form.submit(Form)"></button>  
 </form>  
 <script>  
   // ... validate method, it will check `checkValid(Form)`  
   $scope.form = {  
     submit: function (form) {  
       $validationProvider.validate(form)  
         .success(successCallback)  
         .error(errorCallback);  
     }  
   };  
   // ...  
 </script>  
 <!-- In angular validation 1.2.0  
    More easy, more clean in your js code -->  
 <form name="Form">  
   <input type="text" name="number" ng-model="form.number" validator="number" valid-method="submit-only"/>  
   <button validation-submit="Form" ng-click="form.submit()"></button>  
 </form>  
 <script>  
   // Don't need include $validationProvider.validate() anymore  
   $scope.form = {  
     submit: function () {  
       // your ng-click success callback  
     }  
   };  
 </script>  
 <!-- Clean, right ? -->  

Setup a new Validation setExpression() setDefaultMsg() with RegExp or Function in config phase

 <!-- View -->  
 <label>IP address (Custom setup the new validator - RegExp)</label>  
 <input type="text" name="ip" ng-model="form.ip" validator="ip"/>  
 <label>Huei (Custom setup the new validator - Function)</label>  
 <input type="text" name="huei" ng-model="form.huei" validator="huei"/>  
 <label>Kuaisheng (Custom setup the new validator - Function)</label>  
 <input type="text" name="kuaisheng" ng-model="form.kuaisheng" validator="kuaisheng"/>  
 // your module  
 angular.module('yourApp', ['validation'])  
   .config(['$validationProvider', function ($validationProvider) {  
     // Setup `ip` validation  
     var expression = {  
       ip: /^(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$/  
     };  
     var validMsg = {  
       ip: {  
         error: 'This isn\'t ip address',  
         success: 'It\'s ip'  
       }  
     };  
     $validationProvider.setExpression(expression) // set expression  
              .setDefaultMsg(validMsg); // set valid message  
     // Setup `huei` validation  
     $validationProvider  
       .setExpression({  
         huei: function (value, scope, element, attrs) {  
           return value === 'Huei Tan';  
           // or you can do  
           return $q.all([obj]).then(function () {  
           // ...  
             return true;  
           })  
         }  
       })  
       .setDefaultMsg({  
         huei: {  
           error: 'This should be Huei Tan',  
           success: 'Thanks!'  
         }  
       });  
     // Setup `kuaisheng` validation  
     $validationProvider  
       .setExpression({  
         kuaisheng: function(value, scope, element, attrs, param) {  
          var errorStr = [  
           'errorStr1',  
           'errorStr2'  
          ];  
          var len = errorStr.length;  
          for (var i = len - 1; i >= 0; i--) {  
           if (value.indexOf(errorStr[i]) > -1) {  
            return {  
             result: false,  
             message: 'input should not include ' + errorStr[i]  
            };  
           }  
          }  
          return {  
           result: true,  
           message: ''  
          };  
         }  
       })  
       .setDefaultMsg({  
         kuaisheng: {  
          error: 'valid is error',  
          success: 'Thanks!'  
         }  
       });  
   }]);  
 Check form whether valid, return true if valid. checkValid()  
 Reset the specific Form. reset()  
 <form name="Form">  
   ...  
   <!-- Check the entire form valid from angular-validation `valid` -->  
   <button ng-disabled="!form.checkValid()"></button>  
   <!-- or Check the specific form(Form) valid from angular `$valid` -->  
   <button ng-disabled="!form.checkValid(Form)"></button>  
   <!-- Reset the specific Form -->  
   <button ng-click="form.reset(Form)"></button>  
   <!-- Clean Reset (angular validation 1.2.0) -->  
   <button validation-reset="Form"></button>  
 </form>  
   // ... checkValid  
   $scope.form.checkValid = validationProvider.checkValid;  
   // ... reset  
   $scope.form.reset = function (form) {  
     validationProvider.reset(form);  
   };  
   // ... angular validation 1.2.0 reset  
   $scope.form.reset = function () {  
     // Don't need include validationProvider.reset();  
     // Focus on your ng-click action  
   };  

Set the valid/invalid message style CSS

 <span><p class="validation-valid">Your valid message here<p></span>  
 <span><p class="validation-invalid">Your invalid message here<p></span>  
 .validation-valid {  
   <!-- valid style -->  
 }  
 .validation-invalid {  
   <!-- invalid style -->  
 }  

Custom the valid/invalid message style HTML in .config()

setErrorHTML(func) setSuccessHTML(func), input should be a function and given parameter which is the valid/invalid message declared in getDefaultMsg(),and finally return the HTML code
 // your angular  
 .config(['$validationProvider', function ($validationProvider) {  
   $validationProvider.setErrorHTML(function (msg, element, attrs) {  
     // remember to return your HTML  
     // eg: return '<p class="invalid">' + msg + '</p>';  
     // or using filter  
     // eg: return '<p class="invalid">{{"' + msg + '"| lowercase}}</p>';  
   });  
   $validationProvider.setSuccessHTML(function (msg, element, attrs) {  
     // eg: return '<p class="valid">' + msg + '</p>';  
     // or using filter  
     // eg: return '<p class="valid">{{"' + msg + '"| lowercase}}</p>';  
   });  
 }]);  

disable/enable show success/error message

default: true Easily disable success/error message
 // your angular  
 .config(['$validationProvider', function ($validationProvider) {  
   $validationProvider.showSuccessMessage = false; // or true(default)  
   $validationProvider.showErrorMessage = false; // or true(default)  
 }]);  

Multiple validators

Use commas to separate multiple validators.
 <input type="text" validator="required, url" name="url" ng-model="form.url"/>  

Validator parameters

The built in maxlength and minlength validators use parameters to configure the limits. For example:
 <input type="text" name="username" ng-model="form.username" validator="maxlength=6"/>  
You can use parameters in your custom validators in the same way. You can access this parameter in the validation expression like so:
 <input type="text" name="code" ng-model="form.code" validator="isstring=test"/>  
 // your module  
 angular.module('yourApp', ['validation'])  
   .config(['$validationProvider', function ($validationProvider) {  
     // Setup `isstring` validation  
     $validationProvider  
       .setExpression({  
         isstring: function (value, scope, element, attrs, param) {  
           return value === param;  
         }  
       })  
       .setDefaultMsg({  
         isstring: {  
           error: 'This is not what we wanted!',  
           success: 'Thanks!'  
         }  
       });  
   }]);  

Customizable Initial Validation

Intial Validation for the input false. You can make it to true!
 <!-- default false -->  
 <input type="text" name="firstName" ng-model="firstName" validator="required"/>  
 <!-- set to true -->  
 <input type="text" name="firstName" ng-model="firstName" validator="required" initial-validity="true"/>  

Custom Error/Success Message Function

html Declare your valid and invalid callback functions. Make sure to pass the message param.
 <input type="text" ng-model="name" name="inputName" validator="required" valid-callback="validationValidHandler(message)" invalid-callback="validationInvalidHandler(message)">  
Javascript Now you can call your own function and have access to the message.
 scope.validationValidHandler = function(message){  
  // you now have access to the error message  
  displayMessage(message, 'success');  
 };  
 scope.validationInvalidHandler = function(message){  
  // you now have access to the error message  
  displayMessage(message, 'error');  
 };  

Setup a global valid/invalid/reset callback in config phase

 // your module  
 angular.module('yourApp', ['validation'])  
   .config(['$validationProvider', function ($validationProvider) {      
           $validationProvider.validCallback = function(element) {  
                element.parents('.validator-container:first').removeClass('has-error').addClass('has-success-tick');  
           };  
           $validationProvider.invalidCallback = function(element) {  
                element.parents('.validator-container:first').removeClass('has-success-tick').addClass('has-error');  
           };  
           $validationProvider.resetCallback = function(element) {  
                element.parents('.validator-container:first').removeClass('has-error');  
           };  
   }]);  

Setup Message Element in config phase

WHY
 <div>  
   <label>  
     <input type="text" name="fullName" validator="required" />  
   </label>  
   <!-- I WANT MY MESSAGE ELEMENT HERE INSTEAD AFTER input -->  
 </div>  
HOW n this case, I can use message-id attribute as a "get a job done" solution. Because, If you choose this solution It will increase your effort of manually putting message-id and define your own Message Element.
You can use addMsgElement as a better solution to centralize & automate your configurations.
 // your module  
 angular.module('yourApp', ['validation'])  
   .config(['$validationProvider', function ($validationProvider) {  
     /**  
     * Add your Msg Element  
     * @param {DOMElement} element - Your input element  
     * @return void  
     */  
     $validationProvider.addMsgElement = function(element) {  
       // Insert my own Msg Element  
       $(element).parent().append('<span></span>');  
     };  
     /**  
     * Function to help validator get your Msg Element  
     * @param {DOMElement} element - Your input element  
     * @return {DOMElement}  
     */  
     $validationProvider.getMsgElement = function(element) {  
       return $(element).parent().children().last();  
     };  
   }]);  


Note: Special thanks to Huei Tan

Disclaimer: The blog is created to share angular directives information to geek, curious Angular Developers.