From 37fed3062ccc3ef1dfd49a9fc53318e72b3e4aff Mon Sep 17 00:00:00 2001 From: Manuel <5673677+mtrezza@users.noreply.github.com> Date: Tue, 20 Sep 2022 02:23:49 +0200 Subject: [PATCH] fix: session object properties can be updated by foreign user; this fixes a security vulnerability in which a foreign user can write to the session object of another user if the session object ID is known; the fix prevents writing to foreign session objects ([GHSA-6w4q-23cf-j9jp](https://github.com/parse-community/parse-server/security/advisories/GHSA-6w4q-23cf-j9jp)) [skip release] (#8180) --- spec/ParseSession.spec.js | 28 ++++++++++++++++++++++++++++ src/RestWrite.js | 14 ++++++++++++++ 2 files changed, 42 insertions(+) diff --git a/spec/ParseSession.spec.js b/spec/ParseSession.spec.js index 084f141e08..a85be1a95e 100644 --- a/spec/ParseSession.spec.js +++ b/spec/ParseSession.spec.js @@ -3,6 +3,7 @@ // 'use strict'; +const request = require('../lib/request'); function setupTestUsers() { const user1 = new Parse.User(); @@ -135,4 +136,31 @@ describe('Parse.Session', () => { fail(err); }); }); + + it('cannot edit session with known ID', async () => { + await setupTestUsers(); + const [first, second] = await new Parse.Query(Parse.Session).find({ useMasterKey: true }); + const headers = { + 'X-Parse-Application-Id': 'test', + 'X-Parse-Rest-API-Key': 'rest', + 'X-Parse-Session-Token': second.get('sessionToken'), + 'Content-Type': 'application/json', + }; + const firstUser = first.get('user').id; + const secondUser = second.get('user').id; + const e = await request({ + method: 'PUT', + headers, + url: `http://localhost:8378/1/sessions/${first.id}`, + body: JSON.stringify({ + foo: 'bar', + user: { __type: 'Pointer', className: '_User', objectId: secondUser }, + }), + }).catch(e => e.data); + expect(e.code).toBe(Parse.Error.OBJECT_NOT_FOUND); + expect(e.error).toBe('Object not found.'); + await Parse.Object.fetchAll([first, second], { useMasterKey: true }); + expect(first.get('user').id).toBe(firstUser); + expect(second.get('user').id).toBe(secondUser); + }); }); diff --git a/src/RestWrite.js b/src/RestWrite.js index 31b9c22552..9cb735fa40 100644 --- a/src/RestWrite.js +++ b/src/RestWrite.js @@ -1019,6 +1019,20 @@ RestWrite.prototype.handleSession = function () { } else if (this.data.sessionToken) { throw new Parse.Error(Parse.Error.INVALID_KEY_NAME); } + if (!this.auth.isMaster) { + this.query = { + $and: [ + this.query, + { + user: { + __type: 'Pointer', + className: '_User', + objectId: this.auth.user.id, + }, + }, + ], + }; + } } if (!this.query && !this.auth.isMaster) {