|
16 | 16 | //! [W3C Baggage]: https://w3c.github.io/baggage
|
17 | 17 | use crate::{Context, Key, KeyValue, Value};
|
18 | 18 | use once_cell::sync::Lazy;
|
| 19 | +use std::borrow::Cow; |
19 | 20 | use std::collections::{hash_map, HashMap};
|
20 | 21 | use std::fmt;
|
21 | 22 | use std::iter::FromIterator;
|
22 |
| -use urlencoding::encode; |
23 | 23 |
|
24 | 24 | static DEFAULT_BAGGAGE: Lazy<Baggage> = Lazy::new(Baggage::default);
|
25 | 25 |
|
@@ -282,10 +282,29 @@ impl FromIterator<KeyValueMetadata> for Baggage {
|
282 | 282 | }
|
283 | 283 | }
|
284 | 284 |
|
| 285 | +fn encode(s: Cow<'_, str>) -> String { |
| 286 | + let special_characters = ['.', '-', '_', '~']; |
| 287 | + let mut encoded_string = String::new(); |
| 288 | + |
| 289 | + for char in s.as_ref().chars() { |
| 290 | + if char.is_ascii_alphanumeric() || special_characters.contains(&char) { |
| 291 | + encoded_string.push(char); |
| 292 | + } else if char == ' ' { |
| 293 | + encoded_string.push_str("%20"); |
| 294 | + } else { |
| 295 | + // Convert to a two-digit hexadecimal representation |
| 296 | + for byte in char.to_string().as_bytes() { |
| 297 | + encoded_string.push_str(&format!("%{:02X}", byte)); |
| 298 | + } |
| 299 | + } |
| 300 | + } |
| 301 | + encoded_string |
| 302 | +} |
| 303 | + |
285 | 304 | impl fmt::Display for Baggage {
|
286 | 305 | fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
|
287 | 306 | for (i, (k, v)) in self.into_iter().enumerate() {
|
288 |
| - write!(f, "{}={}", k, encode(&v.0.as_str()))?; |
| 307 | + write!(f, "{}={}", k, encode(v.0.as_str()))?; |
289 | 308 | if !v.1.as_str().is_empty() {
|
290 | 309 | write!(f, ";{}", v.1)?;
|
291 | 310 | }
|
@@ -473,6 +492,26 @@ mod tests {
|
473 | 492 | assert_eq!(baggage.len(), 0, "did not insert invalid key");
|
474 | 493 | }
|
475 | 494 |
|
| 495 | + #[test] |
| 496 | + fn test_ascii_values() { |
| 497 | + let string1 = Cow::Borrowed("test_ 123"); |
| 498 | + let string2 = Cow::Borrowed("Hello123"); |
| 499 | + let string3 = Cow::Borrowed("This & That = More"); |
| 500 | + let string4 = Cow::Borrowed("Unicode: 😊"); |
| 501 | + let string5 = Cow::Borrowed("Non-ASCII: áéíóú"); |
| 502 | + let string6 = Cow::Borrowed("Unsafe: ~!@#$%^&*()_+{}[];:'\\\"<>?,./"); |
| 503 | + |
| 504 | + assert_eq!(encode(string1), "test_%20123"); |
| 505 | + assert_eq!(encode(string2), "Hello123"); |
| 506 | + assert_eq!(encode(string3), "This%20%26%20That%20%3D%20More"); |
| 507 | + assert_eq!(encode(string4), "Unicode%3A%20%F0%9F%98%8A"); |
| 508 | + assert_eq!( |
| 509 | + encode(string5), |
| 510 | + "Non-ASCII%3A%20%C3%A1%C3%A9%C3%AD%C3%B3%C3%BA" |
| 511 | + ); |
| 512 | + assert_eq!(encode(string6), "Unsafe%3A%20~%21%40%23%24%25%5E%26%2A%28%29_%2B%7B%7D%5B%5D%3B%3A%27%5C%22%3C%3E%3F%2C.%2F"); |
| 513 | + } |
| 514 | + |
476 | 515 | #[test]
|
477 | 516 | fn insert_too_much_baggage() {
|
478 | 517 | // too many key pairs
|
|
0 commit comments