Skip to content
46 changes: 46 additions & 0 deletions spec/ParseQuery.Aggregate.spec.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
'use strict';
const Parse = require('parse/node');
const request = require('../lib/request');
const Config = require('../lib/Config');

const masterKeyHeaders = {
'X-Parse-Application-Id': 'test',
Expand Down Expand Up @@ -1428,4 +1429,49 @@ describe('Parse.Query Aggregate testing', () => {
});
}
);

it_only_db('mongo')('geoNear with location query', async () => {
// Create geo index which is required for `geoNear` query
const database = Config.get(Parse.applicationId).database;
const schema = await new Parse.Schema('GeoObject').save();
await database.adapter.ensureIndex(
'GeoObject',
schema,
['location'],
'geoIndex',
false,
'2dsphere'
);
// Create objects
const GeoObject = Parse.Object.extend('GeoObject');
const obj1 = new GeoObject({ value: 1, location: new Parse.GeoPoint(1, 1), date: new Date(1) });
const obj2 = new GeoObject({ value: 2, location: new Parse.GeoPoint(2, 1), date: new Date(2) });
const obj3 = new GeoObject({ value: 3, location: new Parse.GeoPoint(3, 1), date: new Date(3) });
await Parse.Object.saveAll([obj1, obj2, obj3]);
// Create query
const pipeline = [
{
geoNear: {
near: {
type: 'Point',
coordinates: [1, 1]
},
key: 'location',
spherical: true,
distanceField: 'dist',
query: {
date: {
$gte: new Date(2)
}
}
}
}
];
const query = new Parse.Query(GeoObject);
const results = await query.aggregate(pipeline);
// Check results
expect(results.length).toEqual(2);
expect(results[0].value).toEqual(2);
expect(results[1].value).toEqual(3);
});
});
8 changes: 6 additions & 2 deletions src/Adapters/Storage/Mongo/MongoStorageAdapter.js
Original file line number Diff line number Diff line change
Expand Up @@ -682,15 +682,16 @@ export class MongoStorageAdapter implements StorageAdapter {
schema: SchemaType,
fieldNames: string[],
indexName: ?string,
caseInsensitive: boolean = false
caseInsensitive: boolean = false,
indexType: any = 1
): Promise<any> {
schema = convertParseSchemaToMongoSchema(schema);
const indexCreationRequest = {};
const mongoFieldNames = fieldNames.map(fieldName =>
transformKey(className, fieldName, schema)
);
mongoFieldNames.forEach(fieldName => {
indexCreationRequest[fieldName] = 1;
indexCreationRequest[fieldName] = indexType;
});

const defaultOptions: Object = { background: true, sparse: true };
Expand Down Expand Up @@ -843,6 +844,9 @@ export class MongoStorageAdapter implements StorageAdapter {
stage.$project
);
}
if (stage.$geoNear) {
stage.$geoNear.query = this._parseAggregateArgs(schema, stage.$geoNear.query);
}
return stage;
});
readPreference = this._parseReadPreference(readPreference);
Expand Down
3 changes: 2 additions & 1 deletion src/Adapters/Storage/StorageAdapter.js
Original file line number Diff line number Diff line change
Expand Up @@ -92,7 +92,8 @@ export interface StorageAdapter {
schema: SchemaType,
fieldNames: string[],
indexName?: string,
caseSensitive?: boolean
caseSensitive?: boolean,
indexType?: any
): Promise<any>;
ensureUniqueness(
className: string,
Expand Down