Fixes #1275. `Include` filter transforms fields property into array. (#1276)

* Fixes#1275 Transform *fields* property into array

`Include` filter takes into consideration string property
'fields' and transforms it into an array containing this string.

* Added error handling for `include` filter.

* ExecTasksWithInterLeave now contains a try-catch block
 in order to catch any unexpected errors.

* LinkManyToMany now checks if *modelToIdName* exists on
 *target* before continuing.

* Added unit test for *include* with string fields
This commit is contained in:
Nick Oikonomou 2017-03-22 16:03:36 +02:00 committed by Sakib Hasan
parent 77c4cd7b01
commit b3a7bc521d
2 changed files with 36 additions and 5 deletions

View File

@ -97,12 +97,16 @@ function execTasksWithInterLeave(tasks, callback) {
// Context Switch BEFORE Heavy Computation
process.nextTick(function() {
// Heavy Computation
async.parallel(tasks, function(err, info) {
// Context Switch AFTER Heavy Computation
process.nextTick(function() {
callback(err, info);
try {
async.parallel(tasks, function(err, info) {
// Context Switch AFTER Heavy Computation
process.nextTick(function() {
callback(err, info);
});
});
});
} catch (err) {
callback(err);
}
});
}
@ -328,6 +332,10 @@ Inclusion.include = function(objects, include, options, cb) {
filter.where = filter.where || {};
// if fields are specified, make sure target foreign key is present
var fields = filter.fields;
if (typeof fields === 'string') {
// transform string into array containing this string
filter.fields = fields = [fields];
}
if (Array.isArray(fields) && fields.indexOf(relation.keyTo) === -1) {
fields.push(relation.keyTo);
} else if (isPlainObject(fields) && !fields[relation.keyTo]) {
@ -481,6 +489,11 @@ Inclusion.include = function(objects, include, options, cb) {
async.each(targets, linkManyToMany, next);
function linkManyToMany(target, next) {
var targetId = target[modelToIdName];
if (!targetId) {
var err = new Error(g.f('LinkManyToMany received target that doesn\'t contain required "%s"',
modelToIdName));
return next(err);
}
var objList = targetObjsMap[targetId.toString()];
async.each(objList, function(obj, next) {
if (!obj) return next();

View File

@ -835,6 +835,24 @@ describe('relations', function() {
});
});
context('findById with include filter that contains string fields', function() {
it('should accept string and convert it to array', function(done) {
var includeFilter = {include: {relation: 'patients', scope: {fields: 'name'}}};
var physicianId = physician.id;
Physician.findById(physicianId, includeFilter, function(err, result) {
should.not.exist(err);
should.exist(result);
result.id.should.eql(physicianId);
should.exist(result.patients);
result.patients().should.be.an.instanceOf(Array);
should.exist(result.patients()[0]);
should.exist(result.patients()[0].name);
should.not.exist(result.patients()[0].age);
done();
});
});
});
function createSampleData(done) {
Physician.create(function(err, result) {
result.patients.create({name: 'a', age: '10'}, function(err, p) {