Stack Overflow is a community of 4.7 million programmers, just like you, helping each other.

Join them; it only takes a minute:

Sign up
Join the Stack Overflow community to:
  1. Ask programming questions
  2. Answer and help your peers
  3. Get recognized for your expertise

Is it feasible and not particularly arduous to create a validation framework that could be used in the following manner:

var myValidations = 
[
 {   'A',
      'This is required',
       function(item) {return item != null;}
    },
    {
     'B',
      "Max 10 chars",
       function(item) {return item.length <=10 && item.length >0;}
    },
    {
     'C',
      'Must start with Z',
       function(item) {return item[0] == 'Z'}
    }];

    $scope.model.Message.AddValidation('A');
    $scope.model.Message.AddValidation('C');

    $scope.onSave = function()
    {
        if(!$scope.model.IsValid)
        {
            // $scope.model.errors
        }

    }

<input type="text" ng-model="model.Message"/>

What might be involved to get a basic implementation going?

Perhaps there are existing AngularJS Validation frameworks with similar usage concepts I've yet to stumble upon?

share|improve this question
2  
Why not to use ng-form that allows dynamic validation and on fields you can have ng-required, also you have standard min, max for input fields, and use regex validation for thi item[0] == 'Z' type of verifications? – Diana R Sep 17 '15 at 19:26
2  
Yes, AngularJS already provides a validation framework to do what you are thinking. – pixelbits Sep 17 '15 at 19:40
    
Use docs.angularjs.org/guide/forms . If you need to implement your model of validator (defined on js), you can to create directives using $compile phase to convert to angular form validation. – Joaozito Polo Sep 17 '15 at 19:59
    
I suppose I am looking for an approach that forgoes the use of Angular Directives and allows me to place validators directly to my model. This then allows me to dynamically bind validation to form elements. – puri Sep 18 '15 at 10:47

This is how you would do it using the latest version of angular, and building custom validation directives that use AngularJS's validation framework:

Step 1: Add Some Style

This is to make things look nice...

<!-- Optional theme -->
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap-theme.min.css">

<!-- Latest compiled and minified JavaScript -->
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/js/bootstrap.min.js"></script>

<style>
  ul {
    margin: 0;
    padding:0;
  }
</style>

Step 2: Add AngularJS Libraries

You need the core AngularJS libraries and ngMessages:

<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.6/angular.min.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.6/angular-messages.min.js"></script>

Step 3: Define your Validation Directives

Yes, I know there are already pre-defined AngularJS directives for "required" and "max length", but this is an SO answer and it's important that you know how to define ones yourself.

app.directive('rqrd', function() {
  return {
    restrict: 'A',
    require: 'ngModel',
    link: function(scope, element, attr, ngModel) {
      ngModel.$validators.rqrd = function(modelValue, viewValue) {
        var value = modelValue || viewValue;
        return value != null && value != undefined && value != '';
      }
    }
  }
});

app.directive('max', function() {
  return {
    restrict: 'A',
    require: 'ngModel',
    link: function(scope, element, attr, ngModel) {
      var maxValue = parseInt(attr.max);
      ngModel.$validators.max = function(modelValue, viewValue) {
        var value = modelValue || viewValue;
        return value.length > 0 && value.length <= maxValue;
      }
    }
  } 
});

app.directive('startsWith', function() {
  return {
    restrict: 'A',
    require: 'ngModel',
    link: function(scope, element, attr, ngModel) {
      ngModel.$validators.startsWith = function(modelValue, viewValue) {
        var value = modelValue || viewValue;
        return value && value.length > 0 && value.indexOf(attr.startsWith) == 0;
      }
    }
  } 
});

Step 4: Use your Validation Directives

<form name="form">

  Favorite Color   <br />
  <input name="color" ng-model="color" rqrd max="10"  />  
  <ul ng-messages="form.color.$error">
     <li ng-message="rqrd" class="label label-danger">This is required</li>
     <li ng-message="max" class="label label-danger">Max 10 chars</li>
  </ul> 
  Name <br />
  <input name="name" ng-model="name" starts-with="Z"  /> 
    <ul ng-messages="form.name.$error">
     <li ng-message="rqrd" class="label label-danger">Please enter an Age</li>
     <li ng-message="startsWith" class="label label-danger">Must start with Z</li>
  </ul> 

</form>

Checking that Form is Valid

if ($scope.form.$valid) {
   ...
}

    var app = angular.module('app', ['ngMessages']);

    app.controller('ctrl', function($scope) {
       
    });

    app.directive('rqrd', function() {
      return {
        restrict: 'A',
        require: 'ngModel',
        link: function(scope, element, attr, ngModel) {
          ngModel.$validators.rqrd = function(modelValue, viewValue) {
            var value = modelValue || viewValue;
            return value != null && value != undefined && value != '';
          }
        }
      }
    });

    app.directive('max', function() {
      return {
        restrict: 'A',
        require: 'ngModel',
        link: function(scope, element, attr, ngModel) {
          var maxValue = parseInt(attr.max);
          ngModel.$validators.max = function(modelValue, viewValue) {
            var value = modelValue || viewValue;
            return value.length > 0 && value.length <= maxValue;
          }
        }
      } 
    });

    app.directive('startsWith', function() {
      return {
        restrict: 'A',
        require: 'ngModel',
        link: function(scope, element, attr, ngModel) {
          ngModel.$validators.startsWith = function(modelValue, viewValue) {
            var value = modelValue || viewValue;
            return value && value.length > 0 && value.indexOf(attr.startsWith) == 0;
          }
        }
      } 
    });
    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.6/angular.min.js"></script>
    <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.4.6/angular-messages.min.js"></script>
    <!-- Latest compiled and minified CSS -->
    <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap.min.css">

    <!-- Optional theme -->
    <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/css/bootstrap-theme.min.css">

    <!-- Latest compiled and minified JavaScript -->
    <script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.5/js/bootstrap.min.js"></script>

    <style>
      ul {
        margin: 0;
        padding:0;
      }
    </style>

    <h3>Example heading </h3>
    <div ng-app="app" ng-controller="ctrl">
    <form name="form">

      Favorite Color   <br />
      <input name="color" ng-model="color" rqrd max="10"  />  
      <ul ng-messages="form.color.$error">
         <li ng-message="rqrd" class="label label-danger">This is required</li>
         <li ng-message="max" class="label label-danger">Max 10 chars</li>
      </ul> 
      Name <br />
      <input name="name" ng-model="name" starts-with="Z"  /> 
        <ul ng-messages="form.name.$error">
         <li ng-message="rqrd" class="label label-danger">Please enter an Age</li>
         <li ng-message="startsWith" class="label label-danger">Must start with Z</li>
      </ul> 
    </form>
      
    </div>

share|improve this answer

Angular already has a validation framework built in, which includes capabilities to add custom validations. This is done by creating custom directives which define validation functions, then adding those directives as attributes to your input. IE from the Angular example, we create this custom integer directive:

app.directive('integer', function() {
  return {
    require: 'ngModel',
    link: function(scope, elm, attrs, ctrl) {
      ctrl.$validators.integer = function(modelValue, viewValue) {
        if (ctrl.$isEmpty(modelValue)) {
          // consider empty models to be valid
          return true;
        }

        if (INTEGER_REGEXP.test(viewValue)) {
          // it is valid
          return true;
        }

        // it is invalid
        return false;
      };
    }
  };
});

Then add it to our input:

<input type="number" ng-model="size" name="size"
           min="0" max="10" integer />{{size}}<br />

And we can then access its validation status by querying form.size.$error.integer

share|improve this answer

A very nice framework in github https://github.com/turinggroup/angular-validator

<div class="col-sm-10">


<input  type = "text"
 name = "blur"
 validate-on="blur"
  class = "form-control"
ng-model = "form.blur"
  ng-pattern="/regex/"
  invalid-message="'You must enter the word `regex`'"
  required-message="'Yo! This field is required..'"
  required></div>

Demo here

Another well detailed example here

share|improve this answer
    
Does this validation works with Dropdown control because i am using it but it does not works on dropdown control. – Learning Mar 30 at 5:57

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.