Make mentions more permissive

This commit is contained in:
Joscha 2023-01-31 10:36:18 +01:00
parent 632760cfb9
commit a5a6f121bd

View file

@ -53,13 +53,6 @@ pub fn hue(emoji: &Emoji, nick: &str) -> u8 {
hue_without_removing_emoji(&emoji.remove(nick)) hue_without_removing_emoji(&emoji.remove(nick))
} }
fn delimits_mention(c: char) -> bool {
match c {
',' | '.' | '!' | '?' | ';' | '&' | '<' | '>' | '\'' | '"' => true,
_ => c.is_whitespace(),
}
}
/// Normalize a nick to a form that can be compared against other nicks. /// Normalize a nick to a form that can be compared against other nicks.
/// ///
/// This normalization is less aggressive than the nick hue normalization. It is /// This normalization is less aggressive than the nick hue normalization. It is
@ -73,11 +66,7 @@ fn delimits_mention(c: char) -> bool {
/// ///
/// The steps performed are as follows: /// The steps performed are as follows:
/// ///
/// 1. Remove all whitespace characters as well as the characters /// 1. Apply [`mention`]
/// `,`, `.`, `!`, `?`, `;`, `&`, `<`, `>`, `'`, `"`.
/// All of these are used by the [frontend to delimit mentions][0].
/// The `>` character was confirmed to delimit mentions via experimentation.
///
/// 2. Convert to NFKC /// 2. Convert to NFKC
/// 3. Case fold /// 3. Case fold
/// ///
@ -87,13 +76,19 @@ fn delimits_mention(c: char) -> bool {
/// ///
/// [0]: https://github.com/euphoria-io/heim/blob/978c921063e6b06012fc8d16d9fbf1b3a0be1191/client/lib/stores/chat.js#L14 /// [0]: https://github.com/euphoria-io/heim/blob/978c921063e6b06012fc8d16d9fbf1b3a0be1191/client/lib/stores/chat.js#L14
pub fn normalize(nick: &str) -> String { pub fn normalize(nick: &str) -> String {
nick.chars() mention(nick) // Step 1
.filter(|c| !delimits_mention(*c)) // Step 1
.nfkc() // Step 2 .nfkc() // Step 2
.default_case_fold() // Step 3 .default_case_fold() // Step 3
.collect() .collect()
} }
fn is_non_whitespace_delimiter(c: char) -> bool {
matches!(
c,
',' | '.' | '!' | '?' | ';' | '&' | '<' | '>' | '\'' | '"'
)
}
/// Compute a mentionable version of a nick while remaining as close to the /// Compute a mentionable version of a nick while remaining as close to the
/// original as possible. /// original as possible.
/// ///
@ -101,7 +96,20 @@ pub fn normalize(nick: &str) -> String {
/// highlight as a mention in the official euphoria client. It should ping any /// highlight as a mention in the official euphoria client. It should ping any
/// people using the original nick. It might also ping other people. /// people using the original nick. It might also ping other people.
/// ///
/// This function performs step 1 of [`normalize`]. /// In the official euphoria client, mentions are non-whitespace characters
/// delimited by whitespace and any of the following characters:
///
/// `,`, `.`, `!`, `?`, `;`, `&`, `<`, `>`, `'`, `"`.
///
/// The first character of a mention may be a delimiting character.
pub fn mention(nick: &str) -> String { pub fn mention(nick: &str) -> String {
nick.replace(delimits_mention, "") let mut nick = nick.chars().filter(|c| !c.is_whitespace());
let mut result = String::new();
if let Some(c) = nick.next() {
result.push(c);
}
for c in nick.filter(|c| !is_non_whitespace_delimiter(*c)) {
result.push(c);
}
result
} }