Skip to content

Instantly share code, notes, and snippets.

@AshleyGrant
Forked from lstarky/app.html
Last active February 28, 2017 22:32
Show Gist options
  • Save AshleyGrant/6f3a0c1522f41bf2915a8c22d7098bd9 to your computer and use it in GitHub Desktop.
Save AshleyGrant/6f3a0c1522f41bf2915a8c22d7098bd9 to your computer and use it in GitHub Desktop.
Aurelia Validation with JSON rules
<template>
<form role="form" class="form-horizontal" with.bind="user">
<div class="form-group">
<label class="col-sm-2 control-label">First Name</label>
<div class="col-sm-3">
<input value.bind="firstName & validate" type="text" placeholder="first name" class="form-control">
</div>
</div>
<div class="form-group">
<label class="col-sm-2 control-label">Last Name</label>
<div class="col-sm-3">
<input value.bind="lastName & validate" type="text" placeholder="last name" class="form-control">
</div>
</div>
<div class="form-group">
<label class="col-sm-2 control-label">Email</label>
<div class="col-sm-3">
<input value.bind="email & validate" type="text" placeholder="email" class="form-control">
</div>
</div>
</form>
</template>
import {transient, inject, NewInstance, computedFrom} from 'aurelia-framework';
import {ValidationRules, ValidationController, validateTrigger} from 'aurelia-validation';
import {BootstrapFormRenderer} from './bootstrap-form-renderer';
@inject(NewInstance.of(ValidationController))
export class App {
user = {
firstName: 'Ashley',
lastName: 'Grant',
email: 'test@example.com'
}
constructor(validationController) {
this.validationController = validationController;
this.validationController.validateTrigger = validateTrigger.change;
this.validationController.addRenderer(new BootstrapFormRenderer());
}
attached() {
ValidationRules.fromJSON(rules)
.on(this.user);
this.validationController.reset();
}
}
const rules ={
"firstName": {
"displayName": "First Name",
"required": "true",
"minLength": "3",
"maxLength": "10"
},
"lastName": {
"displayName": "Last Name",
"required": "true",
"minLength": "3",
"maxLength": "10"
},
"email": {
"displayName": "Email",
"required": "true",
"email": "true"
}
};
ValidationRules.fromJSON = function(json){
let validator = ValidationRules;
for(let property of Object.keys(json)) {
validator = validator.ensure(property);
const ruleSet = json[property];
for(const ruleName of Object.keys(ruleSet)) {
validator = validator[ruleName](ruleSet[ruleName]);
}
}
return validator;
}
import {
ValidationRenderer,
RenderInstruction,
ValidateResult
} from 'aurelia-validation';
export class BootstrapFormRenderer {
render(instruction: RenderInstruction) {
for (let { result, elements } of instruction.unrender) {
for (let element of elements) {
this.remove(element, result);
}
}
for (let { result, elements } of instruction.render) {
for (let element of elements) {
this.add(element, result);
}
}
}
add(element: Element, result: ValidateResult) {
if (result.valid) {
return;
}
const formGroup = element.closest('.form-group');
if (!formGroup) {
return;
}
// add the has-error class to the enclosing form-group div
formGroup.classList.add('has-error');
// add help-block
const message = document.createElement('span');
message.className = 'help-block validation-message';
message.textContent = result.message;
message.id = `validation-message-${result.id}`;
formGroup.appendChild(message);
}
remove(element: Element, result: ValidateResult) {
if (result.valid) {
return;
}
const formGroup = element.closest('.form-group');
if (!formGroup) {
return;
}
// remove help-block
const message = formGroup.querySelector(`#validation-message-${result.id}`);
if (message) {
formGroup.removeChild(message);
// remove the has-error class from the enclosing form-group div
if (formGroup.querySelectorAll('.help-block.validation-message').length === 0) {
formGroup.classList.remove('has-error');
}
}
}
}
<html>
<head>
<title>Aurelia</title>
<meta name="viewport" content="width=device-width, initial-scale=1">
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-1q8mTJOASx8j1Au+a5WDVnPi2lkFfwwEAa8hDDdjZlpLegxhjVME1fgjWPGmkzs7" crossorigin="anonymous">
<style>
registration-form {
display: block;
max-width: 300px;
margin-left: auto;
margin-right: auto;
}
</style>
</head>
<body aurelia-app="main">
<h1>Loading...</h1>
<script src="https://jdanyow.github.io/rjs-bundle/node_modules/requirejs/require.js"></script>
<script src="https://jdanyow.github.io/rjs-bundle/config.js"></script>
<script src="https://jdanyow.github.io/rjs-bundle/bundles/aurelia.js"></script>
<script src="https://jdanyow.github.io/rjs-bundle/bundles/babel.js"></script>
<script>
require(['aurelia-bootstrapper']);
</script>
</body>
</html>
export function configure(aurelia) {
aurelia.use
.standardConfiguration()
.developmentLogging()
.plugin('aurelia-validation');
aurelia.start().then(() => aurelia.setRoot());
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment