diff --git a/jid/CHANGELOG.md b/jid/CHANGELOG.md index 111cb8cb..ef233e9a 100644 --- a/jid/CHANGELOG.md +++ b/jid/CHANGELOG.md @@ -8,6 +8,7 @@ Unreleased * Additions - Parsing invalid JIDs with stringprep feature no longer results in panic, returning Error with NodePrep, NamePrep or ResourcePrep variant instead (#84) + - Parsing already-normalized JIDs with stringprep is much faster, about 20 times. - JID parts are now typed as NodePart, DomainPart and ResourcePart ; once part into those types, JID operations cannot fail - BareJid::with_resource appends a ResourcePart to a BareJid to produce a FullJid (#204) diff --git a/jid/Cargo.toml b/jid/Cargo.toml index 5758c644..63dea0d9 100644 --- a/jid/Cargo.toml +++ b/jid/Cargo.toml @@ -22,4 +22,4 @@ gitlab = { repository = "xmpp-rs/xmpp-rs" } memchr = "2.5" minidom = { version = "0.15", optional = true } serde = { version = "1.0", features = ["derive"], optional = true } -stringprep = "0.1.2" +stringprep = "0.1.3" diff --git a/jid/src/inner.rs b/jid/src/inner.rs index e124b42e..644e4c25 100644 --- a/jid/src/inner.rs +++ b/jid/src/inner.rs @@ -13,6 +13,7 @@ use crate::Error; use core::num::NonZeroU16; use memchr::memchr; +use std::borrow::Cow; use std::str::FromStr; use stringprep::{nameprep, nodeprep, resourceprep}; @@ -57,7 +58,12 @@ impl InnerJid { orig_at = Some(node.len()); orig_slash = Some(node.len() + domain.len() + 1); - format!("{node}@{domain}/{resource}") + match (node, domain, resource) { + (Cow::Borrowed(_), Cow::Borrowed(_), Cow::Borrowed(_)) => { + unnormalized.to_string() + } + (node, domain, resource) => format!("{node}@{domain}/{resource}"), + } } (Some(at), None) => { let node = nodeprep(&unnormalized[..at]).map_err(|_| Error::NodePrep)?; @@ -67,7 +73,10 @@ impl InnerJid { length_check(domain.len(), Error::DomainEmpty, Error::DomainTooLong)?; orig_at = Some(node.len()); - format!("{node}@{domain}") + match (node, domain) { + (Cow::Borrowed(_), Cow::Borrowed(_)) => unnormalized.to_string(), + (node, domain) => format!("{node}@{domain}"), + } } (None, Some(slash)) => { let domain = nameprep(&unnormalized[..slash]).map_err(|_| Error::NamePrep)?; @@ -78,7 +87,10 @@ impl InnerJid { length_check(resource.len(), Error::ResourceEmpty, Error::ResourceTooLong)?; orig_slash = Some(domain.len()); - format!("{domain}/{resource}") + match (domain, resource) { + (Cow::Borrowed(_), Cow::Borrowed(_)) => unnormalized.to_string(), + (domain, resource) => format!("{domain}/{resource}"), + } } (None, None) => { let domain = nameprep(unnormalized).map_err(|_| Error::NamePrep)?;