Recursively cast props on fromDb for memory conn.

In the fromDb step, nested properties weren't being hydrated properly.
This caused an issue with the ability to search on such properties as
Dates. The properties would be hydrated as a String type, and as such,
it was impossible to properly query on them.
This commit is contained in:
nVitius 2017-04-28 15:58:45 -07:00
parent 8ebccb65d1
commit 3df1826730
2 changed files with 77 additions and 35 deletions

View File

@ -351,28 +351,46 @@ Memory.prototype.fromDb = function(model, data) {
data = deserialize(data);
var props = this._models[model].properties;
for (var key in data) {
var val = data[key];
if (val === undefined || val === null) {
continue;
}
if (props[key]) {
switch (props[key].type.name) {
case 'Date':
val = new Date(val.toString().replace(/GMT.*$/, 'GMT'));
break;
case 'Boolean':
val = Boolean(val);
break;
case 'Number':
val = Number(val);
break;
}
}
data[key] = val;
data[key] = this._castPropertyValue(key, data[key], props);
}
return data;
};
Memory.prototype._castPropertyValue = function(prop, val, props) {
var self = this;
if (val === undefined || val === null || !props[prop]) {
return val;
}
if (Array.isArray(val)) {
return val.map(function(val) {
return self._castPropertyValue(prop, val, props);
});
}
var isArray = Array.isArray(props[prop].type);
var propType = isArray ? props[prop].type[0] : props[prop].type;
switch (propType.name) {
case 'Date':
val = new Date(val.toString().replace(/GMT.*$/, 'GMT'));
break;
case 'Boolean':
val = Boolean(val);
break;
case 'Number':
val = Number(val);
break;
case 'ModelConstructor':
for (var subProp in val) {
val[subProp] = this._castPropertyValue(subProp, val[subProp], propType.definition.properties);
}
break;
}
return val;
};
function getValue(obj, path) {
if (obj == null) {
return undefined;

View File

@ -157,6 +157,7 @@ describe('Memory connector', function() {
city: String,
state: String,
zipCode: String,
since: Date,
tags: [
{
tag: String,
@ -166,6 +167,7 @@ describe('Memory connector', function() {
friends: [
{
name: String,
since: Date,
},
],
});
@ -294,8 +296,7 @@ describe('Memory connector', function() {
});
});
it('should successfully extract 2 users using implied and & and',
function(done) {
it('should successfully extract 2 users using implied and & and', function(done) {
User.find({
where: {
name: 'John Lennon',
@ -435,15 +436,14 @@ describe('Memory connector', function() {
});
});
it('should work when a regex is provided without the regexp operator',
function(done) {
User.find({where: {name: /John.*/i}}, function(err, users) {
should.not.exist(err);
users.length.should.equal(1);
users[0].name.should.equal('John Lennon');
done();
});
});
it('should work when a regex is provided without the regexp operator', function(done) {
User.find({where: {name: /John.*/i}}, function(err, users) {
should.not.exist(err);
users.length.should.equal(1);
users[0].name.should.equal('John Lennon');
done();
});
});
it('should support the regexp operator with regex strings', function(done) {
User.find({where: {name: {regexp: '^J'}}}, function(err, users) {
@ -516,6 +516,28 @@ describe('Memory connector', function() {
});
});
it('should support date as nested property in query', function(done) {
var d = new Date('2017-01-01');
User.find({where: {'address.since': d}},
function(err, users) {
should.not.exist(err);
users.length.should.be.equal(1);
users[0].address.since.should.be.eql(d);
done();
});
});
it('should support date as array property in query', function(done) {
var d = new Date('1960-01-01');
User.find({where: {'friends.since': d}},
function(err, users) {
should.not.exist(err);
users.length.should.be.equal(2);
users[0].friends[0].since.should.be.eql(d);
done();
});
});
it('should deserialize values after saving in upsert', function(done) {
User.findOne({where: {seq: 1}}, function(err, paul) {
User.updateOrCreate({id: paul.id, name: 'Sir Paul McCartney'},
@ -553,15 +575,16 @@ describe('Memory connector', function() {
city: 'San Jose',
state: 'CA',
zipCode: '95131',
since: new Date('2017-01-01'),
tags: [
{tag: 'business'},
{tag: 'rent'},
],
},
friends: [
{name: 'Paul McCartney'},
{name: 'George Harrison'},
{name: 'Ringo Starr'},
{name: 'Paul McCartney', since: new Date('1960-01-01')},
{name: 'George Harrison', since: new Date('1960-01-01')},
{name: 'Ringo Starr', since: new Date('1960-01-01')},
],
children: ['Sean', 'Julian'],
},
@ -578,11 +601,12 @@ describe('Memory connector', function() {
city: 'San Mateo',
state: 'CA',
zipCode: '94065',
since: new Date('2017-02-01'),
},
friends: [
{name: 'John Lennon'},
{name: 'George Harrison'},
{name: 'Ringo Starr'},
{name: 'John Lennon', since: new Date('1960-01-01')},
{name: 'George Harrison', since: new Date('1960-01-01')},
{name: 'Ringo Starr', since: new Date('1960-01-01')},
],
children: ['Stella', 'Mary', 'Heather', 'Beatrice', 'James'],
},