rustywallet_address/encoding/
bech32.rs1use crate::error::AddressError;
4use bech32::Hrp;
5
6pub struct Bech32Encoder;
8
9impl Bech32Encoder {
10 pub fn encode_bech32(hrp: &str, _witness_version: u8, data: &[u8]) -> Result<String, AddressError> {
12 let hrp = Hrp::parse(hrp).map_err(|e| AddressError::InvalidBech32(e.to_string()))?;
13
14 bech32::segwit::encode(hrp, bech32::segwit::VERSION_0, data)
15 .map_err(|e| AddressError::InvalidBech32(e.to_string()))
16 }
17
18 pub fn encode_bech32m(hrp: &str, data: &[u8]) -> Result<String, AddressError> {
20 let hrp = Hrp::parse(hrp).map_err(|e| AddressError::InvalidBech32(e.to_string()))?;
21
22 bech32::segwit::encode(hrp, bech32::segwit::VERSION_1, data)
23 .map_err(|e| AddressError::InvalidBech32(e.to_string()))
24 }
25
26 pub fn encode_bech32m_with_version(hrp: &str, version: u8, data: &[u8]) -> Result<String, AddressError> {
29 let hrp = Hrp::parse(hrp).map_err(|e| AddressError::InvalidBech32(e.to_string()))?;
30
31 if version == 0 {
34 bech32::segwit::encode(hrp, bech32::segwit::VERSION_1, data)
37 .map_err(|e| AddressError::InvalidBech32(e.to_string()))
38 } else {
39 Err(AddressError::InvalidBech32(format!("Unsupported version: {}", version)))
40 }
41 }
42
43 pub fn decode(s: &str) -> Result<(String, u8, Vec<u8>), AddressError> {
46 let (hrp, version, program) = bech32::segwit::decode(s)
47 .map_err(|e| AddressError::InvalidBech32(e.to_string()))?;
48
49 Ok((hrp.to_string(), version.to_u8(), program))
50 }
51}
52
53#[cfg(test)]
54mod tests {
55 use super::*;
56
57 #[test]
58 fn test_bech32_segwit_roundtrip() {
59 let data = [0u8; 20]; let encoded = Bech32Encoder::encode_bech32("bc", 0, &data).unwrap();
61 assert!(encoded.starts_with("bc1q"));
62
63 let (hrp, version, decoded) = Bech32Encoder::decode(&encoded).unwrap();
64 assert_eq!(hrp, "bc");
65 assert_eq!(version, 0);
66 assert_eq!(decoded, data);
67 }
68
69 #[test]
70 fn test_bech32m_taproot_roundtrip() {
71 let data = [0u8; 32]; let encoded = Bech32Encoder::encode_bech32m("bc", &data).unwrap();
73 assert!(encoded.starts_with("bc1p"));
74
75 let (hrp, version, decoded) = Bech32Encoder::decode(&encoded).unwrap();
76 assert_eq!(hrp, "bc");
77 assert_eq!(version, 1);
78 assert_eq!(decoded, data);
79 }
80}