diff --git a/packages/oui-field/src/field.controller.js b/packages/oui-field/src/field.controller.js index e11dac85..2b521a6f 100644 --- a/packages/oui-field/src/field.controller.js +++ b/packages/oui-field/src/field.controller.js @@ -38,7 +38,7 @@ export default class FieldController { this.ids = []; this.validationParameters = {}; this.invalid = false; - this.invalidOnBlur = false; + this.blurred = false; this.hasFocus = false; this.size = this.size || "auto"; } @@ -130,35 +130,28 @@ export default class FieldController { angular.element(controlElement).on("focus", () => { this.$timeout(() => { - this.hideErrors(controlElement, name); + this.form[name].$touched = false; this.hasFocus = true; }); }); } checkControlErrors (controlElement, name) { + this.blurred = true; if (this.form[name] && this.form[name].$invalid) { - this.invalidOnBlur = true; this.currentErrorField = name; } else { - this.invalidOnBlur = false; this.currentErrorField = null; } } - hideErrors (controlElement, name) { - this.form[name].$touched = false; - this.invalidOnBlur = false; - } - isErrorVisible () { if (!this.form) { return false; } this.checkAllErrors(); - return this.invalidOnBlur || // true if invalid after blur event - (this.form.$submitted && this.invalid && !this.hasFocus); // true if invalid after submit event + return this.invalid && !this.hasFocus && (this.blurred || this.form.$submitted); } checkAllErrors () { diff --git a/packages/oui-password/README.md b/packages/oui-password/README.md index 4647e5f0..ce116ee5 100644 --- a/packages/oui-password/README.md +++ b/packages/oui-password/README.md @@ -62,6 +62,32 @@ ``` +#### Confirm Validation + +Useful when you have a password field and a confirm password field. The confirm property takes the expression, the value of which should match with it's model value. + +```html:preview +
+ + + + Must contain between 8 and 30 characters + + + Have at least one number + + + Have at least capital letter + + + + + + + +
+``` + #### Custom strength feedback The feedback of password strength can be overridden by adding your custom feedback in `oui-password-strength`. @@ -105,6 +131,7 @@ It can also be globally changed with `ouiPasswordProvider` (see **Configuration* | `pattern` | string<regexp> | @? | yes | n/a | n/a | pattern of the model value | `required` | boolean | { }); }); + describe("ConfirmValidation", () => { + let form; + let passwords; + let password; + let confirmPassword; + let confirmPasswordController; + let passwordInput; + let confirmPasswordInput; + + beforeEach(() => { + form = TestUtils.compileTemplate(` +
+ + + + +
`); + + $timeout.flush(); + passwords = form.find("oui-password"); + password = angular.element(passwords[0]); + confirmPassword = angular.element(passwords[1]); + password.controller("ouiPassword"); + confirmPasswordController = confirmPassword.controller("ouiPassword"); + passwordInput = getInput(password); + confirmPasswordInput = getInput(confirmPassword); + }); + + it("should get an error 'confirm'", () => { + passwordInput.val("foobar"); + passwordInput.triggerHandler("input"); + confirmPasswordInput.val("foo"); + confirmPasswordInput.triggerHandler("input"); + + expect(confirmPasswordController.form.$error).toBeTruthy(); + expect(confirmPasswordController.form.$error.password).toBeTruthy(); + }); + + it("should not get an error if passwords match", () => { + passwordInput.val("foobar"); + passwordInput.triggerHandler("input"); + confirmPasswordInput.val("foobar"); + confirmPasswordInput.triggerHandler("input"); + + expect(confirmPasswordController.form.$error.password).toBeFalsy(); + }); + + it("should detect a change in the confirm property value and trigger validation", () => { + passwordInput.val("foobar"); + passwordInput.triggerHandler("input"); + confirmPasswordInput.val("foobar"); + confirmPasswordInput.triggerHandler("input"); + passwordInput.val("foobar123"); + passwordInput.triggerHandler("input"); + + expect(confirmPasswordController.form.$error).toBeTruthy(); + expect(confirmPasswordController.form.$error.password).toBeTruthy(); + }); + }); + describe("Strength", () => { const compileStrength = (score) => TestUtils.compileTemplate(` diff --git a/packages/oui-password/src/password.component.js b/packages/oui-password/src/password.component.js index 3575abbd..7c55090a 100644 --- a/packages/oui-password/src/password.component.js +++ b/packages/oui-password/src/password.component.js @@ -15,7 +15,8 @@ export default { minlength: " + this.$timeout(() => { this.$element .removeAttr("id") .removeAttr("name") - .addClass("oui-password") - ); + .addClass("oui-password"); + + if ("confirm" in this.$attrs) { + this.$scope.$watch( + () => this.confirm === this.model, + (value) => this.updateValidity("confirm", value) + ); + } + }); } }