fix(rustproxy-routing): reduce hot-path allocations in routing, metrics, and proxy protocol handling
This commit is contained in:
@@ -6,25 +6,28 @@
|
||||
/// - `example.com` exact match
|
||||
/// - `**.example.com` matches any depth of subdomain
|
||||
pub fn domain_matches(pattern: &str, domain: &str) -> bool {
|
||||
let pattern = pattern.trim().to_lowercase();
|
||||
let domain = domain.trim().to_lowercase();
|
||||
let pattern = pattern.trim();
|
||||
let domain = domain.trim();
|
||||
|
||||
if pattern == "*" {
|
||||
return true;
|
||||
}
|
||||
|
||||
if pattern == domain {
|
||||
if pattern.eq_ignore_ascii_case(domain) {
|
||||
return true;
|
||||
}
|
||||
|
||||
// Wildcard patterns
|
||||
if pattern.starts_with("*.") {
|
||||
if pattern.starts_with("*.") || pattern.starts_with("*.") {
|
||||
let suffix = &pattern[2..]; // e.g., "example.com"
|
||||
// Match exact parent or any single-level subdomain
|
||||
if domain == suffix {
|
||||
if domain.eq_ignore_ascii_case(suffix) {
|
||||
return true;
|
||||
}
|
||||
if domain.ends_with(&format!(".{}", suffix)) {
|
||||
if domain.len() > suffix.len() + 1
|
||||
&& domain.as_bytes()[domain.len() - suffix.len() - 1] == b'.'
|
||||
&& domain[domain.len() - suffix.len()..].eq_ignore_ascii_case(suffix)
|
||||
{
|
||||
// Check it's a single level subdomain for `*.`
|
||||
let prefix = &domain[..domain.len() - suffix.len() - 1];
|
||||
return !prefix.contains('.');
|
||||
@@ -35,11 +38,22 @@ pub fn domain_matches(pattern: &str, domain: &str) -> bool {
|
||||
if pattern.starts_with("**.") {
|
||||
let suffix = &pattern[3..];
|
||||
// Match exact parent or any depth of subdomain
|
||||
return domain == suffix || domain.ends_with(&format!(".{}", suffix));
|
||||
if domain.eq_ignore_ascii_case(suffix) {
|
||||
return true;
|
||||
}
|
||||
if domain.len() > suffix.len() + 1
|
||||
&& domain.as_bytes()[domain.len() - suffix.len() - 1] == b'.'
|
||||
&& domain[domain.len() - suffix.len()..].eq_ignore_ascii_case(suffix)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
// Use glob-match for more complex patterns
|
||||
glob_match::glob_match(&pattern, &domain)
|
||||
// Use glob-match for more complex patterns (case-insensitive via lowercasing)
|
||||
let pattern_lower = pattern.to_lowercase();
|
||||
let domain_lower = domain.to_lowercase();
|
||||
glob_match::glob_match(&pattern_lower, &domain_lower)
|
||||
}
|
||||
|
||||
/// Check if a domain matches any of the given patterns.
|
||||
|
||||
@@ -60,6 +60,16 @@ impl RouteManager {
|
||||
manager
|
||||
}
|
||||
|
||||
/// Check if any route on the given port uses header matching.
|
||||
/// Used to skip expensive header HashMap construction when no route needs it.
|
||||
pub fn any_route_has_headers(&self, port: u16) -> bool {
|
||||
if let Some(indices) = self.port_index.get(&port) {
|
||||
indices.iter().any(|&idx| self.routes[idx].route_match.headers.is_some())
|
||||
} else {
|
||||
false
|
||||
}
|
||||
}
|
||||
|
||||
/// Find the best matching route for the given context.
|
||||
pub fn find_route<'a>(&'a self, ctx: &MatchContext<'_>) -> Option<RouteMatchResult<'a>> {
|
||||
// Get routes for this port
|
||||
|
||||
Reference in New Issue
Block a user