1
0
mirror of https://github.com/matrix-org/matrix-js-sdk.git synced 2025-11-26 17:03:12 +03:00

displayname disambiguation fixes (#662)

* fix displayname=undefined being disambiguated and strip Zero Width chars
* also strip diaritics and whitespace

Signed-off-by: Michael Telatynski <7t3chguy@gmail.com>
This commit is contained in:
Michael Telatynski
2018-07-06 10:42:53 +01:00
committed by Luke Barnard
parent c4fe15400c
commit 7f50dd205f
3 changed files with 36 additions and 17 deletions

View File

@@ -229,18 +229,23 @@ function calculateDisplayName(member, event, roomState) {
return displayName; return displayName;
} }
// First check if the displayname is something we consider truthy
// after stripping it of zero width characters and padding spaces
const strippedDisplayName = utils.removeHiddenChars(displayName);
if (!strippedDisplayName) {
return selfUserId;
}
// Check if the name contains something that look like a mxid // Next check if the name contains something that look like a mxid
// If it does, it may be someone trying to impersonate someone else // If it does, it may be someone trying to impersonate someone else
// Show full mxid in this case // Show full mxid in this case
// Also show mxid if there are other people with the same displayname // Also show mxid if there are other people with the same displayname
// ignoring any zero width chars (unicode 200B-200D)
// if their displayname is made up of just zero width chars, show full mxid
let disambiguate = /@.+:.+/.test(displayName); let disambiguate = /@.+:.+/.test(displayName);
if (!disambiguate) { if (!disambiguate) {
const userIds = roomState.getUserIdsWithDisplayName(displayName); const userIds = roomState.getUserIdsWithDisplayName(strippedDisplayName);
const otherUsers = userIds.filter(function(u) { disambiguate = userIds.some((u) => u !== selfUserId);
return u !== selfUserId;
});
disambiguate = otherUsers.length > 0;
} }
if (disambiguate) { if (disambiguate) {

View File

@@ -494,22 +494,26 @@ function _updateDisplayNameCache(roomState, userId, displayName) {
// We clobber the user_id > name lookup but the name -> [user_id] lookup // We clobber the user_id > name lookup but the name -> [user_id] lookup
// means we need to remove that user ID from that array rather than nuking // means we need to remove that user ID from that array rather than nuking
// the lot. // the lot.
const existingUserIds = roomState._displayNameToUserIds[oldName] || []; const strippedOldName = utils.removeHiddenChars(oldName);
for (let i = 0; i < existingUserIds.length; i++) {
if (existingUserIds[i] === userId) { const existingUserIds = roomState._displayNameToUserIds[strippedOldName];
// remove this user ID from this array if (existingUserIds) {
existingUserIds.splice(i, 1); // remove this user ID from this array
i--; const filteredUserIDs = existingUserIds.filter((id) => id !== userId);
} roomState._displayNameToUserIds[strippedOldName] = filteredUserIDs;
} }
roomState._displayNameToUserIds[oldName] = existingUserIds;
} }
roomState._userIdsToDisplayNames[userId] = displayName; roomState._userIdsToDisplayNames[userId] = displayName;
if (!roomState._displayNameToUserIds[displayName]) {
roomState._displayNameToUserIds[displayName] = []; const strippedDisplayname = displayName && utils.removeHiddenChars(displayName);
// an empty stripped displayname (undefined/'') will be set to MXID in room-member.js
if (strippedDisplayname) {
if (!roomState._displayNameToUserIds[strippedDisplayname]) {
roomState._displayNameToUserIds[strippedDisplayname] = [];
}
roomState._displayNameToUserIds[strippedDisplayname].push(userId);
} }
roomState._displayNameToUserIds[displayName].push(userId);
} }
/** /**

View File

@@ -662,3 +662,13 @@ module.exports.inherits = function(ctor, superCtor) {
module.exports.isNumber = function(value) { module.exports.isNumber = function(value) {
return typeof value === 'number' && isFinite(value); return typeof value === 'number' && isFinite(value);
}; };
/**
* Removes zero width chars, diacritics and whitespace from the string
* @param {string} str the string to remove hidden characters from
* @return {string} a string with the hidden characters removed
*/
module.exports.removeHiddenChars = function(str) {
return str.normalize('NFD').replace(removeHiddenCharsRegex, '');
};
const removeHiddenCharsRegex = /[\u200B-\u200D\u0300-\u036f\uFEFF\s]/g;