o192 0.2.2

ORION-192: ordered, resilient, independent, URL-safe 192-bit IDs for distributed systems.
Documentation
//! Codec unit tests.

mod common;

use common::hex_to_bytes;
use o192::{
    decode_sortable64, encode_sortable64, is_valid, parse, OrionIdError, ALPHABET, ID_SIZE_BYTES,
    ID_SIZE_CHARS,
};

#[test]
fn alphabet_has_64_ascii_sorted_chars() {
    let bytes = ALPHABET.as_bytes();
    assert_eq!(bytes.len(), 64);
    for window in bytes.windows(2) {
        assert!(window[0] < window[1], "alphabet must be ASCII-sorted");
    }
}

#[test]
fn encode_decode_roundtrips_arbitrary_bytes() {
    let mut raw = [0u8; ID_SIZE_BYTES];
    for (i, byte) in raw.iter_mut().enumerate() {
        *byte = ((i as u8).wrapping_mul(31)).wrapping_add(7);
    }
    let text = encode_sortable64(&raw).expect("encode succeeds");
    assert_eq!(text.len(), ID_SIZE_CHARS);
    assert_eq!(decode_sortable64(&text).expect("decode succeeds"), raw);
}

#[test]
fn encode_rejects_wrong_length_input() {
    assert_eq!(
        encode_sortable64(&[0u8; 23]),
        Err(OrionIdError::InvalidLength),
    );
}

#[test]
fn decode_rejects_wrong_length_input() {
    assert_eq!(
        decode_sortable64("too-short"),
        Err(OrionIdError::InvalidLength),
    );
    let too_long: String = "0".repeat(33);
    assert!(matches!(
        decode_sortable64(&too_long),
        Err(OrionIdError::InvalidLength)
    ));
}

#[test]
fn decode_rejects_out_of_alphabet_characters() {
    assert_eq!(
        decode_sortable64("0000000000000000000000000000000+"),
        Err(OrionIdError::InvalidCharacter),
    );
}

#[test]
fn is_valid_returns_expected_results() {
    assert!(is_valid("0007MxpLW00lEG0H8ZD4LMPsY9bfjxoT"));
    assert!(!is_valid(""));
    assert!(!is_valid("plus_sign_at_end_breaks_alphabet+"));
}

#[test]
fn parse_exposes_structured_fields() {
    let bytes = hex_to_bytes("0000075bcd158000303900112233445566778899aabbccdd");
    let id = encode_sortable64(&bytes).unwrap();
    let view = parse(&id, 0).unwrap();
    assert_eq!(view.relative_ms, 123_456_789);
    assert_eq!(view.fraction4096, 2048);
    assert_eq!(view.counter, 12_345);
    assert_eq!(view.random_hex, "00112233445566778899aabbccdd");
}