You've already forked matrix-js-sdk
mirror of
https://github.com/matrix-org/matrix-js-sdk.git
synced 2025-11-28 05:03:59 +03:00
Merge pull request #851 from matrix-org/travis/e2e-notifs
Calculate encrypted notification counts
This commit is contained in:
@@ -228,6 +228,32 @@ function MatrixClient(opts) {
|
|||||||
this._serverSupportsLazyLoading = null;
|
this._serverSupportsLazyLoading = null;
|
||||||
|
|
||||||
this._cachedCapabilities = null; // { capabilities: {}, lastUpdated: timestamp }
|
this._cachedCapabilities = null; // { capabilities: {}, lastUpdated: timestamp }
|
||||||
|
|
||||||
|
// The SDK doesn't really provide a clean way for events to recalculate the push
|
||||||
|
// actions for themselves, so we have to kinda help them out when they are encrypted.
|
||||||
|
// We do this so that push rules are correctly executed on events in their decrypted
|
||||||
|
// state, such as highlights when the user's name is mentioned.
|
||||||
|
this.on("Event.decrypted", (event) => {
|
||||||
|
const oldActions = event.getPushActions();
|
||||||
|
const actions = this._pushProcessor.actionsForEvent(event);
|
||||||
|
event.setPushActions(actions); // Might as well while we're here
|
||||||
|
|
||||||
|
// Ensure the unread counts are kept up to date if the event is encrypted
|
||||||
|
const oldHighlight = oldActions && oldActions.tweaks
|
||||||
|
? !!oldActions.tweaks.highlight : false;
|
||||||
|
const newHighlight = actions && actions.tweaks
|
||||||
|
? !!actions.tweaks.highlight : false;
|
||||||
|
if (oldHighlight !== newHighlight) {
|
||||||
|
const room = this.getRoom(event.getRoomId());
|
||||||
|
// TODO: Handle mentions received while the client is offline
|
||||||
|
// See also https://github.com/vector-im/riot-web/issues/9069
|
||||||
|
if (room && !room.hasUserReadEvent(this.getUserId(), event.getId())) {
|
||||||
|
const current = room.getUnreadNotificationCount("highlight");
|
||||||
|
const newCount = newHighlight ? current + 1 : current - 1;
|
||||||
|
room.setUnreadNotificationCount("highlight", newCount);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
});
|
||||||
}
|
}
|
||||||
utils.inherits(MatrixClient, EventEmitter);
|
utils.inherits(MatrixClient, EventEmitter);
|
||||||
utils.extend(MatrixClient.prototype, MatrixBaseApis.prototype);
|
utils.extend(MatrixClient.prototype, MatrixBaseApis.prototype);
|
||||||
|
|||||||
@@ -497,6 +497,14 @@ utils.extend(module.exports.MatrixEvent.prototype, {
|
|||||||
this._retryDecryption = false;
|
this._retryDecryption = false;
|
||||||
this._setClearData(res);
|
this._setClearData(res);
|
||||||
|
|
||||||
|
// Before we emit the event, clear the push actions so that they can be recalculated
|
||||||
|
// by relevant code. We do this because the clear event has now changed, making it
|
||||||
|
// so that existing rules can be re-run over the applicable properties. Stuff like
|
||||||
|
// highlighting when the user's name is mentioned rely on this happening. We also want
|
||||||
|
// to set the push actions before emitting so that any notification listeners don't
|
||||||
|
// pick up the wrong contents.
|
||||||
|
this.setPushActions(null);
|
||||||
|
|
||||||
this.emit("Event.decrypted", this, err);
|
this.emit("Event.decrypted", this, err);
|
||||||
|
|
||||||
return;
|
return;
|
||||||
@@ -537,6 +545,17 @@ utils.extend(module.exports.MatrixEvent.prototype, {
|
|||||||
decryptionResult.forwardingCurve25519KeyChain || [];
|
decryptionResult.forwardingCurve25519KeyChain || [];
|
||||||
},
|
},
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the cleartext content for this event. If the event is not encrypted,
|
||||||
|
* or encryption has not been completed, this will return null.
|
||||||
|
*
|
||||||
|
* @returns {Object} The cleartext (decrypted) content for the event
|
||||||
|
*/
|
||||||
|
getClearContent: function() {
|
||||||
|
const ev = this._clearEvent;
|
||||||
|
return ev && ev.content ? ev.content : null;
|
||||||
|
},
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Check if the event is encrypted.
|
* Check if the event is encrypted.
|
||||||
* @return {boolean} True if this event is encrypted.
|
* @return {boolean} True if this event is encrypted.
|
||||||
|
|||||||
@@ -1424,6 +1424,40 @@ Room.prototype.getEventReadUpTo = function(userId, ignoreSynthesized) {
|
|||||||
return receipts["m.read"][userId].eventId;
|
return receipts["m.read"][userId].eventId;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Determines if the given user has read a particular event ID with the known
|
||||||
|
* history of the room. This is not a definitive check as it relies only on
|
||||||
|
* what is available to the room at the time of execution.
|
||||||
|
* @param {String} userId The user ID to check the read state of.
|
||||||
|
* @param {String} eventId The event ID to check if the user read.
|
||||||
|
* @returns {Boolean} True if the user has read the event, false otherwise.
|
||||||
|
*/
|
||||||
|
Room.prototype.hasUserReadEvent = function(userId, eventId) {
|
||||||
|
const readUpToId = this.getEventReadUpTo(userId, false);
|
||||||
|
if (readUpToId === eventId) return true;
|
||||||
|
|
||||||
|
if (this.timeline.length
|
||||||
|
&& this.timeline[this.timeline.length - 1].getSender()
|
||||||
|
&& this.timeline[this.timeline.length - 1].getSender() === userId) {
|
||||||
|
// It doesn't matter where the event is in the timeline, the user has read
|
||||||
|
// it because they've sent the latest event.
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (let i = this.timeline.length - 1; i >= 0; --i) {
|
||||||
|
const ev = this.timeline[i];
|
||||||
|
|
||||||
|
// If we encounter the target event first, the user hasn't read it
|
||||||
|
// however if we encounter the readUpToId first then the user has read
|
||||||
|
// it. These rules apply because we're iterating bottom-up.
|
||||||
|
if (ev.getId() === eventId) return false;
|
||||||
|
if (ev.getId() === readUpToId) return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// We don't know if the user has read it, so assume not.
|
||||||
|
return false;
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get a list of receipts for the given event.
|
* Get a list of receipts for the given event.
|
||||||
* @param {MatrixEvent} event the event to get receipts for
|
* @param {MatrixEvent} event the event to get receipts for
|
||||||
|
|||||||
@@ -184,7 +184,10 @@ function PushProcessor(client) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const eventFulfillsDisplayNameCondition = function(cond, ev) {
|
const eventFulfillsDisplayNameCondition = function(cond, ev) {
|
||||||
const content = ev.getContent();
|
let content = ev.getContent();
|
||||||
|
if (ev.isEncrypted() && ev.getClearContent()) {
|
||||||
|
content = ev.getClearContent();
|
||||||
|
}
|
||||||
if (!content || !content.body || typeof content.body != 'string') {
|
if (!content || !content.body || typeof content.body != 'string') {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user