piper-phoneme-streaming 0.1.1

A high-performance Rust library for streaming Text-to-Phoneme (G2P) conversion.
Documentation
use std::collections::VecDeque;

use crate::text_expand::{ExpandResult, ExpandTask, ExpandUnit};

pub struct AcronymExpandTask;

impl ExpandTask for AcronymExpandTask {
    fn expand(&self, queue: &VecDeque<ExpandUnit>) -> Option<ExpandResult> {
        if let Some(ExpandUnit::Word(word)) = queue.front()
            && word.chars().count() > 1
            && word.chars().all(|c| c.is_uppercase())
        {
            let mut units = Vec::new();
            for (i, c) in word.chars().enumerate() {
                if i > 0 {
                    units.push(ExpandUnit::Mark(' '));
                }
                units.push(ExpandUnit::Word(c.to_string()));
            }
            return Some(ExpandResult::Replace(1, units));
        }
        None
    }
}

#[cfg(test)]
mod tests {
    use super::*;

    #[test]
    fn test_acronym_expansion() {
        let task = AcronymExpandTask;

        // Happy case: ABC
        let mut queue = VecDeque::new();
        queue.push_back(ExpandUnit::Word("ABC".to_string()));
        let res = task.expand(&queue);
        assert_eq!(
            res,
            Some(ExpandResult::Replace(
                1,
                vec![
                    ExpandUnit::Word("A".to_string()),
                    ExpandUnit::Mark(' '),
                    ExpandUnit::Word("B".to_string()),
                    ExpandUnit::Mark(' '),
                    ExpandUnit::Word("C".to_string()),
                ]
            ))
        );

        // Edge case: A (single letter)
        let mut queue = VecDeque::new();
        queue.push_back(ExpandUnit::Word("A".to_string()));
        assert_eq!(task.expand(&queue), None);

        // Edge case: Abc (mixed case)
        let mut queue = VecDeque::new();
        queue.push_back(ExpandUnit::Word("Abc".to_string()));
        assert_eq!(task.expand(&queue), None);

        // Edge case: Number
        let mut queue = VecDeque::new();
        queue.push_back(ExpandUnit::Number("123".to_string()));
        assert_eq!(task.expand(&queue), None);

        // Edge case: Punctuation
        let mut queue = VecDeque::new();
        queue.push_back(ExpandUnit::Mark('!'));
        assert_eq!(task.expand(&queue), None);
    }
}