alamid-schema
Advanced tools
Comparing version 0.3.1 to 0.4.0
{ | ||
"name": "alamid-schema", | ||
"version": "0.3.1", | ||
"version": "0.4.0", | ||
"description": "Extendable mongoose-like schemas for node.js and the browser", | ||
@@ -30,9 +30,11 @@ "main": "lib/Schema.js", | ||
"dependencies": { | ||
"value": "0.3.x" | ||
"value": "0.3.x", | ||
"when": "^3.7.3" | ||
}, | ||
"devDependencies": { | ||
"chai": "1.x", | ||
"mocha": "1.x", | ||
"chai-spies": "0.5.x" | ||
"chai": "^3.0.0", | ||
"chai-as-promised": "^5.1.0", | ||
"chai-spies": "^0.7.0", | ||
"mocha": "^2.2.5" | ||
} | ||
} |
"use strict"; | ||
if (typeof Promise === "undefined") { | ||
require("when/es6-shim/Promise"); | ||
} | ||
var value = require("value"), | ||
@@ -109,3 +113,4 @@ defaultValidators = require("./validators.js"); | ||
* @param {Object} model | ||
* @param {Function} callback | ||
* @param {Function=} callback | ||
* @returns {Promise} | ||
*/ | ||
@@ -121,33 +126,45 @@ Schema.prototype.validate = function (model, callback) { | ||
if(value(model).notTypeOf(Object)) { | ||
if (value(model).notTypeOf(Object)) { | ||
throw new TypeError("Model must be an object"); | ||
} | ||
if(!this.validators) { | ||
if (!this.validators) { | ||
throw new Error("Validators not defined: Have you registered the validate plugin before any schema definitions?"); | ||
} | ||
if (this.keys.length === 0) { | ||
setTimeout(function () { | ||
callback(result); | ||
}, 0); | ||
var promise = new Promise(function (resolve, reject) { | ||
if (self.keys.length === 0) { | ||
setTimeout(function () { | ||
resolve(result); | ||
}, 0); | ||
} | ||
return; | ||
} | ||
self.keys.forEach(function (key) { | ||
pending++; | ||
runValidation(self.validators[key], model[key], model, function (failedFields) { | ||
pending--; | ||
this.keys.forEach(function (key) { | ||
pending++; | ||
runValidation(self.validators[key], model[key], model, function (res) { | ||
pending--; | ||
if (failedFields.length > 0) { | ||
result.result = false; | ||
result.failedFields[key] = failedFields; | ||
} | ||
if (res.length > 0) { | ||
result.result = false; | ||
result.failedFields[key] = res; | ||
} | ||
//was final call | ||
if (pending === 0) { | ||
if (result.result === false) { | ||
reject(result); | ||
return; | ||
} | ||
if (pending === 0) { | ||
callback(result); | ||
} | ||
resolve(result); | ||
} | ||
}); | ||
}); | ||
}); | ||
if (!callback || typeof callback !== "function") { | ||
return promise; | ||
} | ||
promise.then(callback, callback); | ||
}; | ||
@@ -154,0 +171,0 @@ } |
@@ -8,2 +8,3 @@ alamid-schema | ||
[![dependencies](https://david-dm.org/peerigon/alamid-schema.svg)](http://david-dm.org/peerigon/alamid-schema) | ||
[![devDependency Status](https://david-dm.org/peerigon/alamid-schema/dev-status.svg)](https://david-dm.org/peerigon/alamid-schema#info=devDependencies) | ||
@@ -142,25 +143,2 @@ If you like [mongoose](http://mongoosejs.com/) schemas and you want to use them standalone, **alamid-schema** is the right module for you. | ||
### Schema Subsets | ||
If you need a subset of a schema containing only certain properties, you can use `Schema.fields()` . | ||
```javascript | ||
var Panda = new Schema("Panda", { | ||
name: String, | ||
age: Number, | ||
color: String | ||
}); | ||
var SubsetPanda = Panda.fields("name", "age"); | ||
``` | ||
equals... | ||
```javascript | ||
var Panda = new Schema("Panda", { | ||
name: String, | ||
age: Number | ||
}); | ||
``` | ||
### Plugin: Validation | ||
@@ -293,2 +271,15 @@ | ||
### Promises | ||
Instead of using a callback it is possible to return a Promise instead. | ||
```javascript | ||
PandaSchema.validate(panda) | ||
.then(function (res) { | ||
// ... | ||
}); | ||
``` | ||
We included an [ES2015 shim](https://github.com/cujojs/when/tree/master/es6-shim) in case you are using Node.js < 0.12 or a browser without native Promise support. | ||
## API | ||
@@ -302,3 +293,3 @@ | ||
#### .fields(key1: Array|String, key2?: String, key3?: String, ...) | ||
#### .only(key1: Array|String, key2?: String, key3?: String, ...) | ||
@@ -342,2 +333,2 @@ Returns a subset with the given keys of the current schema. You may pass an array with keys or just the keys as arguments. | ||
Callback will be called with a validation object with `result` (Boolean) and `failedFields` (Object). | ||
Callback will be called with a validation object with `result` (Boolean) and `failedFields` (Object). |
@@ -5,3 +5,4 @@ "use strict"; | ||
expect = chai.expect, | ||
spies = require('chai-spies'); | ||
spies = require('chai-spies'), | ||
chaiAsPromised = require("chai-as-promised"); | ||
@@ -13,2 +14,3 @@ var Schema = require("../lib/Schema.js"), | ||
chai.use(spies); | ||
chai.use(chaiAsPromised); | ||
chai.Assertion.includeStack = true; | ||
@@ -172,11 +174,26 @@ | ||
it("should throw an error if model is not an object", function() { | ||
it("should throw an error if model is not an object", function () { | ||
var schema = new Schema({}); | ||
expect(function() { schema.validate(null, function() {}); }).to.throw(TypeError); | ||
expect(function() { schema.validate(undefined, function() {}); }).to.throw(TypeError); | ||
expect(function() { schema.validate("", function() {}); }).to.throw(TypeError); | ||
expect(function() { schema.validate(12, function() {}); }).to.throw(TypeError); | ||
expect(function () { | ||
schema.validate(null, function () { | ||
}); | ||
}).to.throw(TypeError); | ||
expect(function () { | ||
schema.validate(undefined, function () { | ||
}); | ||
}).to.throw(TypeError); | ||
expect(function () { | ||
schema.validate("", function () { | ||
}); | ||
}).to.throw(TypeError); | ||
expect(function () { | ||
schema.validate(12, function () { | ||
}); | ||
}).to.throw(TypeError); | ||
expect(function() { schema.validate({}, function() {}); }).to.not.throw(TypeError); | ||
expect(function () { | ||
schema.validate({}, function () { | ||
}); | ||
}).to.not.throw(TypeError); | ||
}); | ||
@@ -204,3 +221,3 @@ | ||
schema.validate({ age: 18 }, function (validation) { | ||
schema.validate({age: 18}, function (validation) { | ||
expect(validation.result).to.eql(true); | ||
@@ -224,3 +241,3 @@ expect(validation.failedFields).to.eql({}); | ||
schema.validate({ age: 18 }, function (validation) { | ||
schema.validate({age: 18}, function (validation) { | ||
expect(validation.result).to.eql(true); | ||
@@ -232,2 +249,52 @@ expect(validation.failedFields).to.eql({}); | ||
describe("Promise signature", function () { | ||
before(function () { | ||
schema = new Schema({ | ||
age: { | ||
type: Number, | ||
min: 3 | ||
} | ||
}); | ||
}); | ||
it("should return a promise if no callback is given", function () { | ||
expect(schema.validate({age: 2})).to.be.a("promise"); | ||
}); | ||
it("should resolve if validation succeeds", function () { | ||
schema = new Schema({ | ||
age: { | ||
type: Number, | ||
min: 3 | ||
} | ||
}); | ||
return schema.validate({age: 4}) | ||
.then(function(validation) { | ||
expect(validation).to.eql({result: true, model: { age: 4 }, failedFields: {}}); | ||
}); | ||
}); | ||
it("should reject if validation fails", function () { | ||
schema = new Schema({ | ||
age: { | ||
type: Number, | ||
min: 5 | ||
} | ||
}); | ||
return schema.validate({age: 1}) | ||
.then(function() { | ||
throw new Error("Should not resolve"); | ||
}) | ||
.catch(function(validation) { | ||
expect(validation).to.eql({result: false, model: { age: 1 }, failedFields: {age: ["min"]}}); | ||
}); | ||
}); | ||
}); | ||
describe("mixed validators", function () { | ||
@@ -256,3 +323,3 @@ | ||
schema.validate({ age: 18 }, function (validation) { | ||
schema.validate({age: 18}, function (validation) { | ||
expect(asyncSpy).to.have.been.called.once(); | ||
@@ -277,3 +344,3 @@ expect(syncSpy).to.have.been.called.once(); | ||
schema.validate({ age: 6 }, function (validation) { | ||
schema.validate({age: 6}, function (validation) { | ||
expect(asyncSpy).to.have.been.called.once(); | ||
@@ -302,3 +369,3 @@ expect(syncSpy).to.have.been.called.once(); | ||
schema.validate({ age: 6 }, function (validation) { | ||
schema.validate({age: 6}, function (validation) { | ||
expect(asyncSpy).to.have.been.called.once(); | ||
@@ -313,6 +380,6 @@ expect(syncSpy).to.have.been.called.once(); | ||
it("should fail if the sync validator fails & async passes", function (done) { | ||
var asyncSpy = chai.spy(function(age, callback) { | ||
var asyncSpy = chai.spy(function (age, callback) { | ||
callback(true); | ||
}), | ||
syncSpy = chai.spy(function(age) { | ||
syncSpy = chai.spy(function (age) { | ||
return "fail-sync"; | ||
@@ -328,3 +395,3 @@ }); | ||
schema.validate({ age: 8 }, function (validation) { | ||
schema.validate({age: 8}, function (validation) { | ||
expect(asyncSpy).to.have.been.called.once(); | ||
@@ -331,0 +398,0 @@ expect(syncSpy).to.have.been.called.once(); |
Sorry, the diff of this file is not supported yet
50295
1147
2
4
330
+ Addedwhen@^3.7.3
+ Addedwhen@3.7.8(transitive)