Skip to content

Commit 02e1a55

Browse files
committed
Moves transform to MongoTransform
- Adds ACL query injection in MongoTransform
1 parent 325d09c commit 02e1a55

File tree

6 files changed

+46
-35
lines changed

6 files changed

+46
-35
lines changed

spec/transform.spec.js renamed to spec/MongoTransform.spec.js

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
// These tests are unit tests designed to only test transform.js.
22

3-
var transform = require('../src/transform');
3+
var transform = require('../src/Adapters/Storage/Mongo/MongoTransform');
44

55
var dummySchema = {
66
data: {},

src/Adapters/Storage/Mongo/MongoSchemaCollection.js

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11

22
import MongoCollection from './MongoCollection';
3+
import * as transform from './MongoTransform';
34

45
function mongoFieldToParseSchemaField(type) {
56
if (type[0] === '*') {
@@ -138,6 +139,10 @@ class MongoSchemaCollection {
138139
upsertSchema(name: string, query: string, update) {
139140
return this._collection.upsertOne(_mongoSchemaQueryFromNameQuery(name, query), update);
140141
}
142+
143+
get transform() {
144+
return transform;
145+
}
141146
}
142147

143148
// Exported for testing reasons and because we haven't moved all mongo schema format

src/Adapters/Storage/Mongo/MongoStorageAdapter.js

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11

22
import MongoCollection from './MongoCollection';
33
import MongoSchemaCollection from './MongoSchemaCollection';
4-
import {parse as parseUrl, format as formatUrl} from '../../../vendor/mongodbUrl';
4+
import { parse as parseUrl, format as formatUrl } from '../../../vendor/mongodbUrl';
5+
import * as transform from './MongoTransform';
56

67
let mongodb = require('mongodb');
78
let MongoClient = mongodb.MongoClient;
@@ -78,6 +79,10 @@ export class MongoStorageAdapter {
7879
});
7980
});
8081
}
82+
83+
get transform() {
84+
return transform;
85+
}
8186
}
8287

8388
export default MongoStorageAdapter;

src/transform.js renamed to src/Adapters/Storage/Mongo/MongoTransform.js

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -738,6 +738,27 @@ function untransformObject(schema, className, mongoObject, isNestedObject = fals
738738
}
739739
}
740740

741+
function addWriteACL(mongoWhere, acl) {
742+
var writePerms = [
743+
{_wperm: {'$exists': false}}
744+
];
745+
for (var entry of acl) {
746+
writePerms.push({_wperm: {'$in': [entry]}});
747+
}
748+
return {'$and': [mongoWhere, {'$or': writePerms}]};
749+
}
750+
751+
function addReadACL(mongoWhere, acl) {
752+
var orParts = [
753+
{"_rperm" : { "$exists": false }},
754+
{"_rperm" : { "$in" : ["*"]}}
755+
];
756+
for (var entry of acl) {
757+
orParts.push({"_rperm" : { "$in" : [entry]}});
758+
}
759+
return {'$and': [mongoWhere, {'$or': orParts}]};
760+
}
761+
741762
var DateCoder = {
742763
JSONToDatabase(json) {
743764
return new Date(json.iso);
@@ -831,5 +852,7 @@ module.exports = {
831852
transformCreate: transformCreate,
832853
transformUpdate: transformUpdate,
833854
transformWhere: transformWhere,
855+
addReadACL: addReadACL,
856+
addWriteACL: addWriteACL,
834857
untransformObject: untransformObject
835858
};

src/Controllers/DatabaseController.js

Lines changed: 10 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@ var mongodb = require('mongodb');
77
var Parse = require('parse/node').Parse;
88

99
var Schema = require('./../Schema');
10-
var transform = require('./../transform');
1110
const deepcopy = require('deepcopy');
1211

1312
// options can contain:
@@ -122,7 +121,7 @@ DatabaseController.prototype.validateObject = function(className, object, query,
122121
// Filters out any data that shouldn't be on this REST-formatted object.
123122
DatabaseController.prototype.untransformObject = function(
124123
schema, isMaster, aclGroup, className, mongoObject) {
125-
var object = transform.untransformObject(schema, className, mongoObject);
124+
var object = this.adapter.transform.untransformObject(schema, className, mongoObject);
126125

127126
if (className !== '_User') {
128127
return object;
@@ -168,17 +167,11 @@ DatabaseController.prototype.update = function(className, query, update, options
168167
.then(() => this.handleRelationUpdates(className, query.objectId, update))
169168
.then(() => this.adaptiveCollection(className))
170169
.then(collection => {
171-
var mongoWhere = transform.transformWhere(schema, className, query);
170+
var mongoWhere = this.adapter.transform.transformWhere(schema, className, query);
172171
if (options.acl) {
173-
var writePerms = [
174-
{_wperm: {'$exists': false}}
175-
];
176-
for (var entry of options.acl) {
177-
writePerms.push({_wperm: {'$in': [entry]}});
178-
}
179-
mongoWhere = {'$and': [mongoWhere, {'$or': writePerms}]};
172+
mongoWhere = this.adapter.transform.addWriteACL(mongoWhere, options.acl);
180173
}
181-
mongoUpdate = transform.transformUpdate(schema, className, update);
174+
mongoUpdate = this.adapter.transform.transformUpdate(schema, className, update);
182175
return collection.findOneAndUpdate(mongoWhere, mongoUpdate);
183176
})
184177
.then(result => {
@@ -305,16 +298,9 @@ DatabaseController.prototype.destroy = function(className, query, options = {})
305298
})
306299
.then(() => this.adaptiveCollection(className))
307300
.then(collection => {
308-
let mongoWhere = transform.transformWhere(schema, className, query);
309-
301+
let mongoWhere = this.adapter.transform.transformWhere(schema, className, query, options);
310302
if (options.acl) {
311-
var writePerms = [
312-
{ _wperm: { '$exists': false } }
313-
];
314-
for (var entry of options.acl) {
315-
writePerms.push({ _wperm: { '$in': [entry] } });
316-
}
317-
mongoWhere = { '$and': [mongoWhere, { '$or': writePerms }] };
303+
mongoWhere = this.adapter.transform.addWriteACL(mongoWhere, options.acl);
318304
}
319305
return collection.deleteMany(mongoWhere);
320306
})
@@ -350,7 +336,7 @@ DatabaseController.prototype.create = function(className, object, options) {
350336
.then(() => this.handleRelationUpdates(className, null, object))
351337
.then(() => this.adaptiveCollection(className))
352338
.then(coll => {
353-
var mongoObject = transform.transformCreate(schema, className, object);
339+
var mongoObject = this.adapter.transform.transformCreate(schema, className, object);
354340
return coll.insertOne(mongoObject);
355341
})
356342
.then(result => {
@@ -609,7 +595,7 @@ DatabaseController.prototype.find = function(className, query, options = {}) {
609595
if (options.sort) {
610596
mongoOptions.sort = {};
611597
for (let key in options.sort) {
612-
let mongoKey = transform.transformKey(schema, className, key);
598+
let mongoKey = this.adapter.transform.transformKey(schema, className, key);
613599
mongoOptions.sort[mongoKey] = options.sort[key];
614600
}
615601
}
@@ -626,16 +612,9 @@ DatabaseController.prototype.find = function(className, query, options = {}) {
626612
.then(() => this.reduceInRelation(className, query, schema))
627613
.then(() => this.adaptiveCollection(className))
628614
.then(collection => {
629-
let mongoWhere = transform.transformWhere(schema, className, query);
615+
let mongoWhere = this.adapter.transform.transformWhere(schema, className, query);
630616
if (!isMaster) {
631-
let orParts = [
632-
{"_rperm" : { "$exists": false }},
633-
{"_rperm" : { "$in" : ["*"]}}
634-
];
635-
for (let acl of aclGroup) {
636-
orParts.push({"_rperm" : { "$in" : [acl]}});
637-
}
638-
mongoWhere = {'$and': [mongoWhere, {'$or': orParts}]};
617+
mongoWhere = this.adapter.transform.addReadACL(mongoWhere, aclGroup);
639618
}
640619
if (options.count) {
641620
delete mongoOptions.limit;

src/Schema.js

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,6 @@
1515
// TODO: hide all schema logic inside the database adapter.
1616

1717
var Parse = require('parse/node').Parse;
18-
var transform = require('./transform');
1918
import MongoSchemaCollection from './Adapters/Storage/Mongo/MongoSchemaCollection';
2019
import _ from 'lodash';
2120

@@ -398,7 +397,7 @@ class Schema {
398397
// If 'freeze' is true, refuse to update the schema for this field.
399398
validateField(className, fieldName, type, freeze) {
400399
// Just to check that the fieldName is valid
401-
transform.transformKey(this, className, fieldName);
400+
this._collection.transform.transformKey(this, className, fieldName);
402401

403402
if( fieldName.indexOf(".") > 0 ) {
404403
// subdocument key (x.y) => ok if x is of type 'object'

0 commit comments

Comments
 (0)