* The 'beforeSave' trigger breaks requests using the dot notation for subdocuments (cf #567) * Convert 'var' to 'let' / 'const' * Convert 'var' to 'const'
This commit is contained in:
@@ -54,6 +54,12 @@ describe('rest create', () => {
|
|||||||
|
|
||||||
it('handles object and subdocument', done => {
|
it('handles object and subdocument', done => {
|
||||||
const obj = { subdoc: {foo: 'bar', wu: 'tan'} };
|
const obj = { subdoc: {foo: 'bar', wu: 'tan'} };
|
||||||
|
|
||||||
|
Parse.Cloud.beforeSave('MyClass', function(req, res) {
|
||||||
|
// this beforeSave trigger should do nothing but can mess with the object
|
||||||
|
res.success();
|
||||||
|
});
|
||||||
|
|
||||||
rest.create(config, auth.nobody(config), 'MyClass', obj)
|
rest.create(config, auth.nobody(config), 'MyClass', obj)
|
||||||
.then(() => database.adapter.find('MyClass', { fields: {} }, {}, {}))
|
.then(() => database.adapter.find('MyClass', { fields: {} }, {}, {}))
|
||||||
.then(results => {
|
.then(results => {
|
||||||
@@ -64,7 +70,7 @@ describe('rest create', () => {
|
|||||||
expect(mob.subdoc.wu).toBe('tan');
|
expect(mob.subdoc.wu).toBe('tan');
|
||||||
expect(typeof mob.objectId).toEqual('string');
|
expect(typeof mob.objectId).toEqual('string');
|
||||||
const obj = { 'subdoc.wu': 'clan' };
|
const obj = { 'subdoc.wu': 'clan' };
|
||||||
return rest.update(config, auth.nobody(config), 'MyClass', { objectId: mob.objectId }, obj)
|
return rest.update(config, auth.nobody(config), 'MyClass', { objectId: mob.objectId }, obj);
|
||||||
})
|
})
|
||||||
.then(() => database.adapter.find('MyClass', { fields: {} }, {}, {}))
|
.then(() => database.adapter.find('MyClass', { fields: {} }, {}, {}))
|
||||||
.then(results => {
|
.then(results => {
|
||||||
|
|||||||
@@ -153,12 +153,11 @@ RestWrite.prototype.runBeforeTrigger = function() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
let originalObject = null;
|
let originalObject = null;
|
||||||
const updatedObject = triggers.inflate(extraData, this.originalData);
|
const updatedObject = this.buildUpdatedObject(extraData);
|
||||||
if (this.query && this.query.objectId) {
|
if (this.query && this.query.objectId) {
|
||||||
// This is an update for existing object.
|
// This is an update for existing object.
|
||||||
originalObject = triggers.inflate(extraData, this.originalData);
|
originalObject = triggers.inflate(extraData, this.originalData);
|
||||||
}
|
}
|
||||||
updatedObject.set(this.sanitizedData());
|
|
||||||
|
|
||||||
return Promise.resolve().then(() => {
|
return Promise.resolve().then(() => {
|
||||||
return triggers.maybeRunTrigger(triggers.Types.beforeSave, this.auth, updatedObject, originalObject, this.config);
|
return triggers.maybeRunTrigger(triggers.Types.beforeSave, this.auth, updatedObject, originalObject, this.config);
|
||||||
@@ -1068,8 +1067,7 @@ RestWrite.prototype.runAfterTrigger = function() {
|
|||||||
|
|
||||||
// Build the inflated object, different from beforeSave, originalData is not empty
|
// Build the inflated object, different from beforeSave, originalData is not empty
|
||||||
// since developers can change data in the beforeSave.
|
// since developers can change data in the beforeSave.
|
||||||
const updatedObject = triggers.inflate(extraData, this.originalData);
|
const updatedObject = this.buildUpdatedObject(extraData);
|
||||||
updatedObject.set(this.sanitizedData());
|
|
||||||
updatedObject._handleSaveResponse(this.response.response, this.response.status || 200);
|
updatedObject._handleSaveResponse(this.response.response, this.response.status || 200);
|
||||||
|
|
||||||
// Notifiy LiveQueryServer if possible
|
// Notifiy LiveQueryServer if possible
|
||||||
@@ -1104,6 +1102,29 @@ RestWrite.prototype.sanitizedData = function() {
|
|||||||
return Parse._decode(undefined, data);
|
return Parse._decode(undefined, data);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Returns an updated copy of the object
|
||||||
|
RestWrite.prototype.buildUpdatedObject = function (extraData) {
|
||||||
|
const updatedObject = triggers.inflate(extraData, this.originalData);
|
||||||
|
Object.keys(this.data).reduce(function (data, key) {
|
||||||
|
if (key.indexOf(".") > 0) {
|
||||||
|
// subdocument key with dot notation ('x.y':v => 'x':{'y':v})
|
||||||
|
const splittedKey = key.split(".");
|
||||||
|
const parentProp = splittedKey[0];
|
||||||
|
let parentVal = updatedObject.get(parentProp);
|
||||||
|
if(typeof parentVal !== 'object') {
|
||||||
|
parentVal = {};
|
||||||
|
}
|
||||||
|
parentVal[splittedKey[1]] = data[key];
|
||||||
|
updatedObject.set(parentProp, parentVal);
|
||||||
|
delete data[key];
|
||||||
|
}
|
||||||
|
return data;
|
||||||
|
}, deepcopy(this.data));
|
||||||
|
|
||||||
|
updatedObject.set(this.sanitizedData());
|
||||||
|
return updatedObject;
|
||||||
|
};
|
||||||
|
|
||||||
RestWrite.prototype.cleanUserAuthData = function() {
|
RestWrite.prototype.cleanUserAuthData = function() {
|
||||||
if (this.response && this.response.response && this.className === '_User') {
|
if (this.response && this.response.response && this.className === '_User') {
|
||||||
const user = this.response.response;
|
const user = this.response.response;
|
||||||
|
|||||||
Reference in New Issue
Block a user