Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

文字セット

文字列をパーセントエンコードする

percent-encoding-badge cat-encoding-badge

入力文字列を、percent-encoding クレートの utf8_percent_encode 関数を使って percent-encoding します。次に、percent_decode 関数を使ってデコードします。

use percent_encoding::{utf8_percent_encode, percent_decode, AsciiSet, CONTROLS};
use std::str::Utf8Error;

/// https://url.spec.whatwg.org/#fragment-percent-encode-set
const FRAGMENT: &AsciiSet = &CONTROLS.add(b' ').add(b'"').add(b'<').add(b'>').add(b'`');

fn main() -> Result<(), Utf8Error> {
    let input = "confident, productive systems programming";

    let iter = utf8_percent_encode(input, FRAGMENT);
    let encoded: String = iter.collect();
    assert_eq!(encoded, "confident,%20productive%20systems%20programming");

    let iter = percent_decode(encoded.as_bytes());
    let decoded = iter.decode_utf8()?;
    assert_eq!(decoded, "confident, productive systems programming");

    Ok(())
}

エンコードセットは、どのバイトを(非 ASCII 文字と制御文字に加えて)パーセントエンコードする必要があるかを定義します。このセットの選択はコンテキストに依存します。たとえば、url は URL パス内では ? をエンコードしますが、クエリ文字列内ではエンコードしません。

エンコードの戻り値は &str スライスのイテレータで、String に collect できます。

文字列を application/x-www-form-urlencoded としてエンコードする

url-badge cat-encoding-badge

文字列を form_urlencoded::byte_serialize を使って application/x-www-form-urlencoded 構文にエンコードし、その後 form_urlencoded::parse でデコードします。どちらの関数も String に collect できるイテレータを返します。

use url::form_urlencoded::{byte_serialize, parse};

fn main() {
    let urlencoded: String = byte_serialize("What is ❤?".as_bytes()).collect();
    assert_eq!(urlencoded, "What+is+%E2%9D%A4%3F");
    println!("urlencoded:'{}'", urlencoded);

    let decoded: String = parse(urlencoded.as_bytes())
        .map(|(key, val)| [key, val].concat())
        .collect();
    assert_eq!(decoded, "What is ❤?");
    println!("decoded:'{}'", decoded);
}

16進数のエンコードとデコード

data-encoding-badge cat-encoding-badge

data_encoding クレートは HEXUPPER::encode メソッドを提供しており、 これは &[u8] を受け取り、データの16進数表現を含む String を返します。

同様に、HEXUPPER::decode メソッドも提供されており、これは &[u8] を受け取り、 入力データのデコードに成功した場合は Vec<u8> を返します。

以下の例では、&[u8] データを対応する16進数表現に変換します。次に、この 値を期待される値と比較します。

use data_encoding::{HEXUPPER, DecodeError};

fn main() -> Result<(), DecodeError> {
    let original = b"The quick brown fox jumps over the lazy dog.";
    let expected = "54686520717569636B2062726F776E20666F78206A756D7073206F76\
        657220746865206C617A7920646F672E";

    let encoded = HEXUPPER.encode(original);
    assert_eq!(encoded, expected);

    let decoded = HEXUPPER.decode(&encoded.into_bytes())?;
    assert_eq!(&decoded[..], &original[..]);

    Ok(())
}

base64 をエンコードおよびデコードする

base64-badge cat-encoding-badge

encode を使用してバイトスライスを base64 の String にエンコードし、 decode でそれをデコードします。

use anyhow::Result;
use std::str;
use base64::prelude::{Engine as _, BASE64_STANDARD};

fn main() -> Result<()> {
    let hello = b"hello rustaceans";
    let encoded = BASE64_STANDARD.encode(hello);
    let decoded = BASE64_STANDARD.decode(&encoded)?;

    println!("origin: {}", str::from_utf8(hello)?);
    println!("base64 encoded: {}", encoded);
    println!("back to origin: {}", str::from_utf8(&decoded)?);

    Ok(())
}