Search code examples
urlrustquery-string

How to decode "+" as a space in URL query?


I am trying to use urlencoding (version 2.1.3) to decode the datetime from a URL like this:

fn main() {
    let result = urlencoding::decode("gmt_create=2024-05-05+11%3A14%3A19");
    print!("{}", result.unwrap_or_default().into_owned());
}

How to make the date and time concat with whitespace (i.e replacing the plus)? I'd like this result may look like: gmt_create=2024-05-05 00:05:28.

I also tried using percent-encoding like this, but it still left the "+":

use percent_encoding::percent_decode_str;

fn main() {
    let encoded_str = "gmt_create=2024-05-05+11%3A14%3A19";
    let decoded_str = percent_decode_str(encoded_str).decode_utf8().unwrap();
    println!("Decoded string: {}", decoded_str);
}

Solution

  • I recommend you use the form-urlencoded crate. There are nuances that + are not to be parsed in URLs (except in the querystring) and thus the urlencoding and percent-encoding crates are not appropriate.

    Annoyingly, this crate doesn't have a method to simply decode a string into another string, it only parses it as a key-value pair iterator. But I hope you can make this work:

    use form_urlencoded; // 1.2.1
    
    fn main() {
        let (key, value) = form_urlencoded::parse("gmt_create=2024-05-05+11%3A14%3A19".as_bytes())
            .next()
            .unwrap_or_default();
    
        println!("{key}={value}");
    }
    
    gmt_create=2024-05-05 11:14:19