Skip to content

Commit 404eed8

Browse files
committed
Uses one query for installation dedup
1 parent 9bf21ef commit 404eed8

File tree

1 file changed

+56
-38
lines changed

1 file changed

+56
-38
lines changed

src/RestWrite.js

Lines changed: 56 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -581,65 +581,83 @@ RestWrite.prototype.handleInstallation = function() {
581581
var promise = Promise.resolve();
582582

583583
var idMatch; // Will be a match on either objectId or installationId
584+
var objectIdMatch;
585+
var installationIdMatch;
584586
var deviceTokenMatches = [];
585587

588+
// Instead of issuing 3 reads, let's do it with one OR.
589+
let orQueries = [];
586590
if (this.query && this.query.objectId) {
587-
promise = promise.then(() => {
588-
return this.config.database.find('_Installation', {
591+
orQueries.push({
589592
objectId: this.query.objectId
590-
}, {}).then((results) => {
591-
if (!results.length) {
592-
throw new Parse.Error(Parse.Error.OBJECT_NOT_FOUND,
593+
});
594+
}
595+
if (this.data.installationId) {
596+
orQueries.push({
597+
'installationId': this.data.installationId
598+
});
599+
}
600+
if (this.data.deviceToken) {
601+
orQueries.push({'deviceToken': this.data.deviceToken});
602+
}
603+
604+
if (orQueries.length == 0) {
605+
return;
606+
}
607+
608+
promise = promise.then(() => {
609+
return this.config.database.find('_Installation', {
610+
'$or': orQueries
611+
}, {});
612+
}).then((results) => {
613+
results.forEach((result) => {
614+
if (this.query && this.query.objectId && result.objectId == this.query.objectId) {
615+
objectIdMatch = result;
616+
}
617+
if (result.installationId == this.data.installationId) {
618+
installationIdMatch = result;
619+
}
620+
if (result.deviceToken == this.data.deviceToken) {
621+
deviceTokenMatches.push(result);
622+
}
623+
});
624+
625+
// Sanity checks when running a query
626+
if (this.query && this.query.objectId) {
627+
if (!objectIdMatch) {
628+
throw new Parse.Error(Parse.Error.OBJECT_NOT_FOUND,
593629
'Object not found for update.');
594-
}
595-
idMatch = results[0];
596-
if (this.data.installationId && idMatch.installationId &&
597-
this.data.installationId !== idMatch.installationId) {
630+
}
631+
if (this.data.installationId && objectIdMatch.installationId &&
632+
this.data.installationId !== objectIdMatch.installationId) {
598633
throw new Parse.Error(136,
599634
'installationId may not be changed in this ' +
600635
'operation');
601636
}
602-
if (this.data.deviceToken && idMatch.deviceToken &&
603-
this.data.deviceToken !== idMatch.deviceToken &&
604-
!this.data.installationId && !idMatch.installationId) {
637+
if (this.data.deviceToken && objectIdMatch.deviceToken &&
638+
this.data.deviceToken !== objectIdMatch.deviceToken &&
639+
!this.data.installationId && !objectIdMatch.installationId) {
605640
throw new Parse.Error(136,
606641
'deviceToken may not be changed in this ' +
607642
'operation');
608643
}
609644
if (this.data.deviceType && this.data.deviceType &&
610-
this.data.deviceType !== idMatch.deviceType) {
645+
this.data.deviceType !== objectIdMatch.deviceType) {
611646
throw new Parse.Error(136,
612647
'deviceType may not be changed in this ' +
613648
'operation');
614649
}
615-
return;
616-
});
617-
});
618-
}
619-
620-
// Check if we already have installations for the installationId/deviceToken
621-
promise = promise.then(() => {
622-
if (this.data.installationId) {
623-
return this.config.database.find('_Installation', {
624-
'installationId': this.data.installationId
625-
});
626-
}
627-
return Promise.resolve([]);
628-
}).then((results) => {
629-
if (results && results.length) {
630-
// We only take the first match by installationId
631-
idMatch = results[0];
632650
}
633-
if (this.data.deviceToken) {
634-
return this.config.database.find(
635-
'_Installation',
636-
{'deviceToken': this.data.deviceToken});
651+
652+
if (this.query && this.query.objectId && objectIdMatch) {
653+
idMatch = objectIdMatch;
637654
}
638-
return Promise.resolve([]);
639-
}).then((results) => {
640-
if (results) {
641-
deviceTokenMatches = results;
655+
656+
if (this.data.installationId && installationIdMatch) {
657+
idMatch = installationIdMatch;
642658
}
659+
660+
}).then(() => {
643661
if (!idMatch) {
644662
if (!deviceTokenMatches.length) {
645663
return;

0 commit comments

Comments
 (0)