From 0f318c93d37606dc1bf5e30974a2c248f61405c6 Mon Sep 17 00:00:00 2001 From: flogiston Date: Tue, 19 Jun 2018 14:39:49 +0200 Subject: [PATCH 1/2] add exclusive attribute validation mode --- specs/validate-spec.js | 10 ++++++++++ validate.js | 20 ++++++++++++++++++++ 2 files changed, 30 insertions(+) diff --git a/specs/validate-spec.js b/specs/validate-spec.js index f18f6fc..979434d 100644 --- a/specs/validate-spec.js +++ b/specs/validate-spec.js @@ -192,6 +192,16 @@ describe("validate", function() { ]); }); + it("does not allow undeclared attributes in exclusive mode", function() { + var attrs = {name: "Nicklas", age: 23} + , globalOptions = {exclusive: true} + , constraints = {name: true}; + expect(validate.runValidations(attrs, constraints, globalOptions)).toHaveItems([{ + attribute: "age", + error: "is not permitted (exclusive mode)" + }]); + }); + it("allows the options for an attribute to be a function", function() { var options = {pass: {option1: "value1"}} , attrs = {name: "Nicklas"} diff --git a/validate.js b/validate.js index 610d0bc..d56d77b 100644 --- a/validate.js +++ b/validate.js @@ -80,6 +80,7 @@ runValidations: function(attributes, constraints, options) { var results = [] , attr + , constraint , validatorName , value , validators @@ -91,6 +92,25 @@ attributes = v.collectFormValues(attributes); } + // In 'exclusive' mode, make sure that there's a constraint for each and + // every attribute. Nested attribute names are matched as well. + if (options.exclusive === true) { + for (attr in attributes) { + var declared = false; + for (constraint in constraints) { + if (constraint === attr || constraint.indexOf(attr + ".") === 0) { + declared = true; + } + } + if (!declared) { + results.push({ + attribute: attr, + error: "is not permitted (exclusive mode)", + }); + } + } + } + // Loops through each constraints, finds the correct validator and run it. for (attr in constraints) { value = v.getDeepObjectValue(attributes, attr); From 7fc33dc78eb19d009e0986cfc22716d48c867f9e Mon Sep 17 00:00:00 2001 From: flogiston Date: Wed, 19 Sep 2018 16:19:04 +0200 Subject: [PATCH 2/2] exclusive mode enhancements --- specs/validate-spec.js | 21 ++++++++++++++++----- validate.js | 6 +++++- 2 files changed, 21 insertions(+), 6 deletions(-) diff --git a/specs/validate-spec.js b/specs/validate-spec.js index 979434d..da5606a 100644 --- a/specs/validate-spec.js +++ b/specs/validate-spec.js @@ -193,13 +193,24 @@ describe("validate", function() { }); it("does not allow undeclared attributes in exclusive mode", function() { - var attrs = {name: "Nicklas", age: 23} + var attributes = {name: "Nicklas", age: 23, year: 2018} , globalOptions = {exclusive: true} , constraints = {name: true}; - expect(validate.runValidations(attrs, constraints, globalOptions)).toHaveItems([{ - attribute: "age", - error: "is not permitted (exclusive mode)" - }]); + expect(validate.runValidations(attributes, constraints, globalOptions)).toHaveItems([ + { + attribute: "age", + value: 23, + globalOptions: globalOptions, + attributes: attributes, + error: "is not permitted (exclusive mode)" + }, { + attribute: "year", + value: 2018, + globalOptions: globalOptions, + attributes: attributes, + error: "is not permitted (exclusive mode)" + } + ]); }); it("allows the options for an attribute to be a function", function() { diff --git a/validate.js b/validate.js index d56d77b..f0141a9 100644 --- a/validate.js +++ b/validate.js @@ -96,6 +96,7 @@ // every attribute. Nested attribute names are matched as well. if (options.exclusive === true) { for (attr in attributes) { + value = v.getDeepObjectValue(attributes, attr); var declared = false; for (constraint in constraints) { if (constraint === attr || constraint.indexOf(attr + ".") === 0) { @@ -105,7 +106,10 @@ if (!declared) { results.push({ attribute: attr, - error: "is not permitted (exclusive mode)", + value: value, + globalOptions: options, + attributes: attributes, + error: options.exclusiveErrorMessage || "is not permitted (exclusive mode)", }); } }