1use std::{hash, ops::Deref};
3
4use regex::Regex;
5
6#[derive(Debug, serde::Serialize, serde::Deserialize, Clone)]
8pub struct EncodableRegex(#[serde(with = "serde_regex")] Regex);
9
10impl PartialEq for EncodableRegex {
11 fn eq(&self, other: &Self) -> bool {
12 self.0.as_str() == other.0.as_str()
13 }
14}
15
16impl hash::Hash for EncodableRegex {
17 fn hash<H: hash::Hasher>(&self, state: &mut H) {
18 self.0.as_str().hash(state);
19 }
20}
21
22impl EncodableRegex {
23 pub fn new<S: AsRef<str>>(pattern: S) -> Result<Self, regex::Error> {
25 Regex::new(pattern.as_ref()).map(EncodableRegex)
26 }
27}
28
29impl From<Regex> for EncodableRegex {
30 fn from(regex: Regex) -> Self {
31 EncodableRegex(regex)
32 }
33}
34impl AsRef<Regex> for EncodableRegex {
35 fn as_ref(&self) -> &Regex {
36 &self.0
37 }
38}
39
40impl Deref for EncodableRegex {
41 type Target = Regex;
42
43 fn deref(&self) -> &Self::Target {
44 &self.0
45 }
46}
47
48#[cfg(feature = "bincode")]
49mod bincode_impls {
50 use super::{EncodableRegex, Regex};
51
52 impl bincode::Encode for EncodableRegex {
53 fn encode<E: bincode::enc::Encoder>(
54 &self,
55 encoder: &mut E,
56 ) -> Result<(), bincode::error::EncodeError> {
57 self.0.as_str().encode(encoder)
58 }
59 }
60
61 impl<Context> bincode::Decode<Context> for EncodableRegex {
62 fn decode<D: bincode::de::Decoder>(
63 decoder: &mut D,
64 ) -> Result<Self, bincode::error::DecodeError> {
65 let regex_str: String = bincode::Decode::decode(decoder)?;
66 Regex::new(®ex_str)
67 .map(EncodableRegex)
68 .map_err(|_| bincode::error::DecodeError::Other("Invalid regex"))
69 }
70 }
71 bincode::impl_borrow_decode!(EncodableRegex);
72}