it('should fail setting schema permissions with invalid key', done => { let object = new Parse.Object('AClass'); object.save().then(() => { request.put({ url: 'http://localhost:8378/1/schemas/AClass', headers: masterKeyHeaders, json: true, body: { classLevelPermissions: { find: { '*': true }, create: { 'role:admin': true }, dummy: { 'some': true } } } }, (error, response, body) => { expect(error).toEqual(null); expect(body.code).toEqual(107); expect(body.error).toEqual('dummy is not a valid operation for class level permissions'); done(); }); }); });
}, (error, response, body) => { expect(body).toEqual({ className: 'HasAllPOD', fields: { //Default fields ACL: {type: 'ACL'}, createdAt: {type: 'Date'}, updatedAt: {type: 'Date'}, objectId: {type: 'String'}, //Custom fields aBool: {type: 'Boolean'}, aDate: {type: 'Date'}, aObject: {type: 'Object'}, aArray: {type: 'Array'}, aGeoPoint: {type: 'GeoPoint'}, aFile: {type: 'File'}, aNewNumber: {type: 'Number'}, aNewString: {type: 'String'}, aNewPointer: {type: 'Pointer', targetClass: 'HasAllPOD'}, aNewRelation: {type: 'Relation', targetClass: 'HasAllPOD'}, }, classLevelPermissions: defaultClassLevelPermissions }); var obj2 = new Parse.Object('HasAllPOD'); obj2.set('aNewPointer', obj1); var relation = obj2.relation('aNewRelation'); relation.add(obj1); obj2.save().then(done); //Just need to make sure saving works on the new object. });
it('allows you to delete and add a geopoint in the same request', done => { var obj = new Parse.Object('NewClass'); obj.set('geo1', new Parse.GeoPoint({latitude: 0, longitude: 0})); obj.save() .then(() => { request.put({ url: 'http://localhost:8378/1/schemas/NewClass', headers: masterKeyHeaders, json: true, body: { fields: { geo2: {type: 'GeoPoint'}, geo1: {__op: 'Delete'} } } }, (error, response, body) => { expect(dd(body, { "className": "NewClass", "fields": { "ACL": {"type": "ACL"}, "createdAt": {"type": "Date"}, "objectId": {"type": "String"}, "updatedAt": {"type": "Date"}, "geo2": {"type": "GeoPoint"}, }, classLevelPermissions: defaultClassLevelPermissions })).toEqual(undefined); done(); }); }) });
obj1.save().then(savedObj1 => { var obj2 = new Parse.Object('HasPointersAndRelations'); obj2.set('aPointer', savedObj1); var relation = obj2.relation('aRelation'); relation.add(obj1); return obj2.save(); }).then(() => {
}, (error, response, body) => { expect(error).toEqual(null); let object = new Parse.Object('AClass'); object.set('hello', 'world'); return object.save().then(() => { done(); }, (err) => { fail('should be able to add a field'); done(); }) })
}, (error, response, body) => { expect(error).toEqual(null); let object = new Parse.Object('AClass'); object.set('hello', 'world'); return object.save().then(() => { fail('should not be able to add a field'); done(); }, (err) => { expect(err.message).toEqual('Permission denied for this action.'); done(); }) })
it('deletes collections including join tables', done => { var obj = new Parse.Object('MyClass'); obj.set('data', 'data'); obj.save() .then(() => { var obj2 = new Parse.Object('MyOtherClass'); var relation = obj2.relation('aRelation'); relation.add(obj); return obj2.save(); }) .then(obj2 => obj2.destroy()) .then(() => { request.del({ url: 'http://localhost:8378/1/schemas/MyOtherClass', headers: masterKeyHeaders, json: true, }, (error, response, body) => { expect(response.statusCode).toEqual(200); expect(response.body).toEqual({}); config.database.collectionExists('_Join:aRelation:MyOtherClass').then(exists => { if (exists) { fail('Relation collection should be deleted.'); done(); } return config.database.collectionExists('MyOtherClass'); }).then(exists => { if (exists) { fail('Class collection should be deleted.'); done(); } }).then(() => { request.get({ url: 'http://localhost:8378/1/schemas/MyOtherClass', headers: masterKeyHeaders, json: true, }, (error, response, body) => { //Expect _SCHEMA entry to be gone. expect(response.statusCode).toEqual(400); expect(body.code).toEqual(Parse.Error.INVALID_CLASS_NAME); expect(body.error).toEqual('Class MyOtherClass does not exist.'); done(); }); }); }); }).then(() => { }, error => { fail(error); done(); }); });
it("should not mask information in non _User class", (done) => { let obj = new Parse.Object('users'); obj.set('password', 'pw'); obj.save().then(() => { let winstonLoggerAdapter = new WinstonLoggerAdapter(); return winstonLoggerAdapter.query({ from: new Date(Date.now() - 500), size: 100, level: 'verbose' }); }).then((results) => { expect(results[1].body.password).toEqual("pw"); done(); }); });
it("should not mask information in non _User class", (done) => { let obj = new Parse.Object('users'); obj.set('password', 'pw'); obj.save().then(() => { let fileLoggerAdapter = new FileLoggerAdapter(); return fileLoggerAdapter.query({ from: new Date(Date.now() - 500), size: 100, level: 'verbose' }); }).then((results) => { expect(results[1].message.includes('"password": "******"')).toEqual(true); done(); }); });
var hasAllPODobject = () => { var obj = new Parse.Object('HasAllPOD'); obj.set('aNumber', 5); obj.set('aString', 'string'); obj.set('aBool', true); obj.set('aDate', new Date()); obj.set('aObject', {k1: 'value', k2: true, k3: 5}); obj.set('aArray', ['contents', true, 5]); obj.set('aGeoPoint', new Parse.GeoPoint({latitude: 0, longitude: 0})); obj.set('aFile', new Parse.File('f.txt', { base64: 'V29ya2luZyBhdCBQYXJzZSBpcyBncmVhdCE=' })); var objACL = new Parse.ACL(); objACL.setPublicWriteAccess(false); obj.setACL(objACL); return obj; };
.then(response => { if (response && response.results && response.results.length) { const firstResult = response.results[0]; firstResult.className = className; if (className === '_Session' && !auth.isMaster) { if (!auth.user || firstResult.user.objectId !== auth.user.id) { throw new Parse.Error( Parse.Error.INVALID_SESSION_TOKEN, 'Invalid session token' ); } } var cacheAdapter = config.cacheController; cacheAdapter.user.del(firstResult.sessionToken); inflatedObject = Parse.Object.fromJSON(firstResult); return triggers.maybeRunTrigger( triggers.Types.beforeDelete, auth, inflatedObject, null, config ); } throw new Parse.Error( Parse.Error.OBJECT_NOT_FOUND, 'Object not found for delete.' ); });
exports.addScore = function(req, res) { var Answers = Parse.Object.extend('Answers'); var query = new Parse.Query(Answers); query.equalTo('username', req.body.username); query.equalTo('mode', req.body.mode); query.first({ success: function (result) { result.set('score', req.body.score); result.save().then(function (result) { res.status(200).end(); }, function (err) { console.log(err); res.status(500).end(); }); } , error: function (error) { console.log(error); res.status(500).end(); } }); };
it('regression test for #2246', done => { let profile = new Parse.Object('UserProfile'); let user = new Parse.User(); function initialize() { return user.save({ username: '******', password: '******' }).then(() => { return profile.save({user}).then(() => { return user.save({ userProfile: profile }, {useMasterKey: true}); }); }); } initialize().then(() => { return setPermissionsOnClass('UserProfile', { 'readUserFields': ['user'], 'writeUserFields': ['user'] }, true); }).then(() => { return Parse.User.logIn('user', 'password') }).then(() => { let query = new Parse.Query('_User'); query.include('userProfile'); return query.get(user.id); }).then((user) => { expect(user.get('userProfile')).not.toBeUndefined(); done(); }, (err) => { jfail(err); done(); }); });
}).then(() => { return profile.save({user}).then(() => { return user.save({ userProfile: profile }, {useMasterKey: true}); }); });
// Converts a REST-format object to a Parse.Object // data is either className or an object function inflate(data, restObject) { var copy = typeof data == 'object' ? data : {className: data}; for (var key in restObject) { copy[key] = restObject[key]; } return Parse.Object.fromJSON(copy); }
return config.cacheController.user.get(sessionToken).then(function (userJSON) { if (userJSON) { var cachedUser = Parse.Object.fromJSON(userJSON); return Promise.resolve(new Auth({ config: config, isMaster: false, installationId: installationId, user: cachedUser })); } var restOptions = { limit: 1, include: 'user' }; var query = new RestQuery(config, master(config), '_Session', { sessionToken: sessionToken }, restOptions); return query.execute().then(function (response) { var results = response.results; if (results.length !== 1 || !results[0]['user']) { throw new Parse.Error(Parse.Error.INVALID_SESSION_TOKEN, 'invalid session token'); } var now = new Date(), expiresAt = results[0].expiresAt ? new Date(results[0].expiresAt.iso) : undefined; if (expiresAt < now) { throw new Parse.Error(Parse.Error.INVALID_SESSION_TOKEN, 'Session token is expired.'); } var obj = results[0]['user']; delete obj.password; obj['className'] = '_User'; obj['sessionToken'] = sessionToken; config.cacheController.user.put(sessionToken, obj); var userObject = Parse.Object.fromJSON(obj); return new Auth({ config: config, isMaster: false, installationId: installationId, user: userObject }); }); });
return find(config, auth, className, { objectId: objectId }).then(function (response) { if (response && response.results && response.results.length) { response.results[0].className = className; cache.clearUser(response.results[0].sessionToken); inflatedObject = Parse.Object.fromJSON(response.results[0]); return triggers.maybeRunTrigger('beforeDelete', auth, inflatedObject); } throw new Parse.Error(Parse.Error.OBJECT_NOT_FOUND, 'Object not found for delete.'); });
return query.execute().then(function (response) { var results = response.results; if (results.length !== 1) { throw new Parse.Error(Parse.Error.INVALID_SESSION_TOKEN, 'invalid legacy session token'); } var obj = results[0]; obj.className = '_User'; var userObject = Parse.Object.fromJSON(obj); return new Auth({ config: config, isMaster: false, installationId: installationId, user: userObject }); });
setTimeout(function() { stateCount = 0; brewing = false; var CoffeeObject = Parse.Object.extend("Coffee"); var coffeeObject = new CoffeeObject(); coffeeObject.save({cups: 7}); io.emit('brew_update', JSON.stringify({ "brewing": brewing })); request(hubotDomain + '/donecoffee'); // Ping hubot webhook that the coffee is ready }, 240000);
return find(config, _Auth2.default.master(config), className, { objectId: objectId }).then(function (response) { if (response && response.results && response.results.length) { response.results[0].className = className; _cache2.default.users.remove(response.results[0].sessionToken); inflatedObject = Parse.Object.fromJSON(response.results[0]); // Notify LiveQuery server if possible config.liveQueryController.onAfterDelete(inflatedObject.className, inflatedObject); return triggers.maybeRunTrigger(triggers.Types.beforeDelete, auth, inflatedObject, null, config); } throw new Parse.Error(Parse.Error.OBJECT_NOT_FOUND, 'Object not found for delete.'); });
.then((response) => { if (response && response.results && response.results.length) { response.results[0].className = className; cache.users.remove(response.results[0].sessionToken); inflatedObject = Parse.Object.fromJSON(response.results[0]); // Notify LiveQuery server if possible config.liveQueryController.onAfterDelete(inflatedObject.className, inflatedObject); return triggers.maybeRunTrigger(triggers.Types.beforeDelete, auth, inflatedObject, null, config.applicationId); } throw new Parse.Error(Parse.Error.OBJECT_NOT_FOUND, 'Object not found for delete.'); });
return query.execute().then((response) => { var results = response.results; if (results.length !== 1 || !results[0]['user']) { return nobody(config); } var obj = results[0]['user']; delete obj.password; obj['className'] = 'users'; obj['sessionToken'] = sessionToken; var userObject = Parse.Object.fromJSON(obj); cache.setUser(sessionToken, userObject); return new Auth(config, false, userObject); });
it('refuses to add two geopoints', done => { var obj = new Parse.Object('NewClass'); obj.set('aString', 'aString'); obj.save() .then(() => { request.put({ url: 'http://localhost:8378/1/schemas/NewClass', headers: masterKeyHeaders, json: true, body: { fields: { newGeo1: {type: 'GeoPoint'}, newGeo2: {type: 'GeoPoint'}, } } }, (error, response, body) => { expect(response.statusCode).toEqual(400); expect(body.code).toEqual(Parse.Error.INCORRECT_TYPE); expect(body.error).toEqual('currently, only one GeoPoint field may exist in an object. Adding newGeo2 when newGeo1 already exists.'); done(); }); }); });
exports.getAnswers = function (req, res) { var Answers = Parse.Object.extend('Answers'); var query = new Parse.Query(Answers); query.equalTo('mode', req.params.mode); query.descending('score'); query.find({ success: function (results) { res.json(results); } , error: function (error) { console.log(error); res.status(500).end(); } }); };
app.get('/stats', function(req, res){ var now = new Date().getTime(); if (cacheExpires <= now) { // Minimal cache solution var CoffeeObject = Parse.Object.extend("Coffee"); var queryObject = new Parse.Query(CoffeeObject); queryObject.limit(10000); queryObject.find({ success: function (results) { var overDays = {}; var overWeekdays = {}; var totCups = 0; console.log(results.length); for (var i = 0; i < results.length; i++) { var cups = results[i].get('cups'); var d = new Date(results[i].createdAt); var dateStr = d.getFullYear() + '-' + ('0' + d.getMonth()).slice(-2) + '-' + ('0' + d.getDate()).slice(-2); if (overDays[dateStr] === undefined) { overDays[dateStr] = 0; } if (overWeekdays[d.getDay()] === undefined) { overWeekdays[d.getDay()] = 0; } totCups += cups; overDays[dateStr] += cups; overWeekdays[d.getDay()] += cups; var coffeeArr = []; } cache = {overDays: overDays, overWeekdays: overWeekdays, totCups: totCups}; cacheExpires = new Date().getTime() + 1000 * 60 * 60; // Cache the parse data for 60 minutes res.render('stats', {data: cache }); }, error: function (error) { alert("Error: " + error.code + " " + error.message); } }); } else { res.render('stats', {data: cache }); } });
return query.execute().then(function (response) { var results = response.results; if (results.length !== 1 || !results[0]['user']) { throw new Parse.Error(Parse.Error.INVALID_SESSION_TOKEN, 'invalid session token'); } var now = new Date(), expiresAt = results[0].expiresAt ? new Date(results[0].expiresAt.iso) : undefined; if (expiresAt < now) { throw new Parse.Error(Parse.Error.INVALID_SESSION_TOKEN, 'Session token is expired.'); } var obj = results[0]['user']; delete obj.password; obj['className'] = '_User'; obj['sessionToken'] = sessionToken; config.cacheController.user.put(sessionToken, obj); var userObject = Parse.Object.fromJSON(obj); return new Auth({ config: config, isMaster: false, installationId: installationId, user: userObject }); });
exports.getUser = function(req, res) { var Answers = Parse.Object.extend('Answers'); var query = new Parse.Query(Answers); query.equalTo('username', req.params.user); query.equalTo('mode', req.params.mode); query.first({ success: function (result) { res.json(result); } , error: function (error) { console.log(error); res.status(500).end(); } }); };
return query.execute().then((response) => { var results = response.results; if (results.length !== 1 || !results[0]['user']) { return nobody(config); } var now = new Date(), expiresAt = new Date(results[0].expiresAt.iso); if(expiresAt < now) { throw new Parse.Error(Parse.Error.INVALID_SESSION_TOKEN, 'Session token is expired.'); } var obj = results[0]['user']; delete obj.password; obj['className'] = '_User'; obj['sessionToken'] = sessionToken; let userObject = Parse.Object.fromJSON(obj); cache.users.set(sessionToken, userObject); return new Auth({ config, isMaster: false, installationId, user: userObject }); });
exports.addAnswer = function(req, res) { var Answers = Parse.Object.extend('Answers'); var query = new Parse.Query(Answers); query.equalTo('username', req.body.username); query.equalTo('mode', req.body.mode); query.first({ success: function (result) { if (req.body.question == "training1") { req.body.question = 0; } else if (req.body.question == "training2") { req.body.question = 1; } else { req.body.question = parseInt(req.body.question) + 1; } result.attributes.answers[req.body.question] = req.body.answer; result.set('answers', result.attributes.answers); result.save().then(function (result) { res.status(200).end(); }, function (err) { console.log(err); res.status(500).end(); }); } , error: function (error) { console.log(error); res.status(500).end(); } }); };
exports.getQuestion = function(req, res) { var Questions = Parse.Object.extend('Questions'); var query = new Parse.Query(Questions); query.equalTo('questionNumber', parseInt(req.params.id)); query.equalTo('mode', req.params.mode); query.first({ success: function (results) { res.json(results); } , error: function (error) { console.log(error); res.status(500).end(); } }); };