iword-rs 0.1.11

High-speed keyword search — Rust implementation of iWord
Documentation
use wasm_bindgen::prelude::*;
use crate::{Dictionary as InnerDict, Mode, key};

/// JS-facing match result.
#[wasm_bindgen]
pub struct WasmMatch {
    pub position: usize,
    pub length: usize,
    pub key: u8,
}

#[wasm_bindgen]
impl WasmMatch {
    /// Extract the matched substring from the original text.
    pub fn extract(&self, text: &str) -> String {
        text[self.position..self.position + self.length].to_string()
    }
}

/// JS-facing dictionary handle.
#[wasm_bindgen]
pub struct IwordDict {
    inner: InnerDict,
}

#[wasm_bindgen]
impl IwordDict {
    /// Build a dictionary from a tab-separated word list string.
    #[wasm_bindgen(constructor)]
    pub fn new(data: &str) -> IwordDict {
        IwordDict { inner: InnerDict::from_text(data) }
    }

    /// Look up a single word. Returns the key (0–254) or 255 if not found.
    pub fn seek(&self, word: &str) -> u8 {
        self.inner.seek(word).unwrap_or(255)
    }

    /// Return true if text contains at least one keyword match.
    pub fn contains(&self, text: &str, forbid: bool) -> bool {
        let mode = if forbid { Mode::FORBID } else { Mode::default() };
        self.inner.contains(text, mode)
    }

    /// Replace matched keywords with '*'. Returns the filtered string.
    pub fn filter(&self, text: &str, forbid: bool) -> String {
        let mode = if forbid { Mode::FORBID } else { Mode::default() };
        self.inner.filter(text, mode)
    }

    /// Scan and return all matches as a JS array of WasmMatch.
    pub fn scan(&self, text: &str, forbid: bool, html: bool) -> Vec<WasmMatch> {
        let mut mode = Mode::default();
        if forbid { mode = mode | Mode::FORBID; }
        if html   { mode = mode | Mode::HTML; }
        self.inner.scan(text, mode)
            .into_iter()
            .map(|m| WasmMatch { position: m.position, length: m.length, key: m.key })
            .collect()
    }

    /// Return the highest-severity (lowest key) match, or null.
    pub fn severity(&self, text: &str, forbid: bool) -> Option<WasmMatch> {
        let mode = if forbid { Mode::FORBID } else { Mode::default() };
        self.inner.severity(text, mode)
            .map(|m| WasmMatch { position: m.position, length: m.length, key: m.key })
    }

    /// Bitmask of keys present in the dictionary (covers keys 0–127).
    pub fn mask(&self) -> u32 {
        self.inner.mask() as u32
    }
}

/// Key constants exposed to JS.
#[wasm_bindgen]
pub struct Key;

#[wasm_bindgen]
impl Key {
    #[wasm_bindgen(getter)] pub fn block()    -> u8 { key::BLOCK }
    #[wasm_bindgen(getter)] pub fn alert()    -> u8 { key::ALERT }
    #[wasm_bindgen(getter)] pub fn flag()     -> u8 { key::FLAG }
    #[wasm_bindgen(getter)] pub fn throttle() -> u8 { key::THROTTLE }
    #[wasm_bindgen(getter)] pub fn log()      -> u8 { key::LOG }
    #[wasm_bindgen(getter)] pub fn pass()     -> u8 { key::PASS }
}