From 299294daffd366631bafefb4915c51c383e38aab Mon Sep 17 00:00:00 2001 From: Bruno Windels Date: Thu, 24 Jun 2021 14:24:22 +0200 Subject: [PATCH] prevent re(d)action in left/kicked room --- .../session/room/timeline/tiles/BaseMessageTile.js | 8 ++++++++ src/matrix/room/timeline/PowerLevels.js | 8 ++++++-- src/matrix/room/timeline/Timeline.js | 12 +++++++----- 3 files changed, 21 insertions(+), 7 deletions(-) diff --git a/src/domain/session/room/timeline/tiles/BaseMessageTile.js b/src/domain/session/room/timeline/tiles/BaseMessageTile.js index ba0198fe..897804bb 100644 --- a/src/domain/session/room/timeline/tiles/BaseMessageTile.js +++ b/src/domain/session/room/timeline/tiles/BaseMessageTile.js @@ -124,6 +124,10 @@ export class BaseMessageTile extends SimpleTile { react(key, log = null) { return this.logger.wrapOrRun(log, "react", async log => { + if (!this.canReact) { + log.set("powerlevel_lacking", true); + return; + } if (this._entry.haveAnnotation(key)) { log.set("already_reacted", true); return; @@ -140,6 +144,10 @@ export class BaseMessageTile extends SimpleTile { redactReaction(key, log = null) { return this.logger.wrapOrRun(log, "redactReaction", async log => { + if (!this._powerLevels.canRedactFromSender(this._ownMember.userId)) { + log.set("powerlevel_lacking", true); + return; + } if (!this._entry.haveAnnotation(key)) { log.set("not_yet_reacted", true); return; diff --git a/src/matrix/room/timeline/PowerLevels.js b/src/matrix/room/timeline/PowerLevels.js index f2315c38..26e5db1d 100644 --- a/src/matrix/room/timeline/PowerLevels.js +++ b/src/matrix/room/timeline/PowerLevels.js @@ -15,14 +15,15 @@ limitations under the License. */ export class PowerLevels { - constructor({powerLevelEvent, createEvent, ownUserId}) { + constructor({powerLevelEvent, createEvent, ownUserId, membership}) { this._plEvent = powerLevelEvent; this._createEvent = createEvent; this._ownUserId = ownUserId; + this._membership = membership; } canRedactFromSender(userId) { - if (userId === this._ownUserId) { + if (userId === this._ownUserId && this._membership === "join") { return true; } else { return this.canRedact; @@ -38,6 +39,9 @@ export class PowerLevels { } get _myLevel() { + if (this._membership !== "join") { + return Number.MIN_SAFE_INTEGER; + } return this._getUserLevel(this._ownUserId); } diff --git a/src/matrix/room/timeline/Timeline.js b/src/matrix/room/timeline/Timeline.js index 8fd84075..3d82a284 100644 --- a/src/matrix/room/timeline/Timeline.js +++ b/src/matrix/room/timeline/Timeline.js @@ -66,7 +66,7 @@ export class Timeline { // as they should only populate once the view subscribes to it // if they are populated already, the sender profile would be empty - this._powerLevels = await this._loadPowerLevels(txn); + this._powerLevels = await this._loadPowerLevels(membership, txn); // 30 seems to be a good amount to fill the entire screen const readerRequest = this._disposables.track(this._timelineReader.readFromEnd(30, txn, log)); try { @@ -78,23 +78,25 @@ export class Timeline { // txn should be assumed to have finished here, as decryption will close it. } - async _loadPowerLevels(txn) { + async _loadPowerLevels(membership, txn) { // TODO: update power levels as state is updated const powerLevelsState = await txn.roomState.get(this._roomId, "m.room.power_levels", ""); if (powerLevelsState) { return new PowerLevels({ powerLevelEvent: powerLevelsState.event, - ownUserId: this._ownMember.userId + ownUserId: this._ownMember.userId, + membership }); } const createState = await txn.roomState.get(this._roomId, "m.room.create", ""); if (createState) { return new PowerLevels({ createEvent: createState.event, - ownUserId: this._ownMember.userId + ownUserId: this._ownMember.userId, + membership }); } else { - return new PowerLevels({ownUserId: this._ownMember.userId}); + return new PowerLevels({ownUserId: this._ownMember.userId, membership}); } }