use zbus::zvariant::Signature;
#[must_use]
pub fn signatures_are_eq(lhs: &Signature, rhs: &Signature) -> bool {
fn strip_parens(bytes: &[u8]) -> &[u8] {
let [b'(', inner @ .., b')'] = bytes else {
return bytes;
};
if inner.iter().fold(0, |count, byte| match byte {
b'(' => count + 1,
b')' if count != 0 => count - 1,
_ => count,
}) == 0
{
inner
} else {
bytes
}
}
let lhs_bytes = lhs.as_bytes();
let rhs_bytes = rhs.as_bytes();
let lhs_stripped = strip_parens(lhs_bytes);
let rhs_stripped = strip_parens(rhs_bytes);
lhs_stripped == rhs_stripped
}
#[cfg(test)]
mod test {
use zbus::zvariant::Signature;
use super::signatures_are_eq;
#[test]
fn test_signatures_are_eq() {
let sig1 = Signature::from_str_unchecked("(ii)(ii)");
let sig2 = Signature::from_str_unchecked("((ii)(ii))");
assert!(signatures_are_eq(&sig1, &sig2));
let sig1 = Signature::from_str_unchecked("a{sv}");
let sig2 = Signature::from_str_unchecked("a{sv}");
assert!(signatures_are_eq(&sig1, &sig2));
let sig1 = Signature::from_str_unchecked("a{sv}");
let sig2 = Signature::from_str_unchecked("(a{sv})");
assert!(signatures_are_eq(&sig1, &sig2));
let sig1 = Signature::from_str_unchecked("a{sv}");
let sig2 = Signature::from_str_unchecked("((a{sv}))");
assert!(!signatures_are_eq(&sig1, &sig2));
let sig1 = Signature::from_str_unchecked("(ii)(ii)");
let sig2 = Signature::from_str_unchecked("((ii)(ii))");
assert!(signatures_are_eq(&sig1, &sig2));
let sig1 = Signature::from_str_unchecked("(ii)(ii)");
let sig2 = Signature::from_str_unchecked("ii)(ii");
assert!(!signatures_are_eq(&sig1, &sig2));
}
}