automaton

An automaton library & basic programs written in Rust
git clone git://git.ethandl.dev/automaton
Log | Files | Refs | README

web_automaton.rs (3719B)


      1 use std::{error::Error, fmt::Display};
      2 
      3 use wasm_bindgen::prelude::*;
      4 
      5 use crate::{
      6     dfa::Transition as DFATransition,
      7     graph_enfa::{GraphENFA, Transition as GraphENFATransition},
      8     nfa::{Transition as NFATransition, NFA},
      9     regex::Regex,
     10     Automaton, AutomatonError, Dot, Encodable,
     11 };
     12 
     13 #[wasm_bindgen]
     14 extern "C" {
     15     #[wasm_bindgen(js_namespace = console)]
     16     fn log(s: &str);
     17 
     18     #[wasm_bindgen(js_namespace = console)]
     19     fn error(s: &str);
     20 }
     21 
     22 #[wasm_bindgen]
     23 #[derive(Debug)]
     24 pub struct WebAutomatonError {
     25     automaton_error: AutomatonError,
     26 }
     27 
     28 impl Display for WebAutomatonError {
     29     fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
     30         write!(f, "{}", self.automaton_error.to_string())
     31     }
     32 }
     33 
     34 impl Error for WebAutomatonError {}
     35 
     36 impl From<AutomatonError> for WebAutomatonError {
     37     fn from(e: AutomatonError) -> Self {
     38         WebAutomatonError { automaton_error: e }
     39     }
     40 }
     41 
     42 #[wasm_bindgen]
     43 impl WebAutomatonError {
     44     #[wasm_bindgen]
     45     pub fn to_string(&self) -> String {
     46         ToString::to_string(self)
     47     }
     48 }
     49 
     50 #[wasm_bindgen]
     51 pub struct WebRegex {
     52     regex_string: String,
     53     regex: Regex,
     54     enfa: GraphENFA,
     55     nfa: NFA,
     56 }
     57 
     58 impl Display for WebRegex {
     59     fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
     60         writeln!(f, "Regex string: {}", self.regex_string)?;
     61         writeln!(f, "Parsed regex: {:?}", self.regex.parsed)?;
     62         writeln!(f, "ENFA: {}", self.enfa)?;
     63         writeln!(f, "NFA: {}", self.nfa)?;
     64         writeln!(f, "DFA: {}", self.regex.automaton)
     65     }
     66 }
     67 
     68 impl Automaton for WebRegex {
     69     fn accepts(&self, input: &str) -> bool {
     70         self.regex.automaton.accepts(input)
     71     }
     72 }
     73 
     74 #[wasm_bindgen]
     75 impl WebRegex {
     76     #[wasm_bindgen(constructor)]
     77     pub fn new(regex: &str) -> Result<WebRegex, WebAutomatonError> {
     78         let (mut graph_enfa, current_state) = GraphENFA::new();
     79         let re = Regex::parse(regex)?;
     80         let parse_tree = re.parsed.clone();
     81         let final_state = graph_enfa.add_non_terminal(parse_tree, current_state)?;
     82         graph_enfa.set_state_acceptance(final_state, true)?;
     83 
     84         Ok(WebRegex {
     85             regex_string: regex.to_owned(),
     86             regex: re,
     87             enfa: graph_enfa.clone(),
     88             nfa: graph_enfa.as_enfa()?.as_nfa(),
     89         })
     90     }
     91 
     92     #[wasm_bindgen]
     93     pub fn accepts(&self, input: &str) -> bool {
     94         Automaton::accepts(self, input)
     95     }
     96 
     97     #[wasm_bindgen]
     98     pub fn regex_string(&self) -> String {
     99         self.regex_string.clone()
    100     }
    101 
    102     #[wasm_bindgen]
    103     pub fn regex_to_string(&self) -> String {
    104         self.regex.to_string()
    105     }
    106 
    107     #[wasm_bindgen]
    108     pub fn enfa_to_string(&self) -> String {
    109         self.enfa.to_string()
    110     }
    111 
    112     #[wasm_bindgen]
    113     pub fn nfa_to_string(&self) -> String {
    114         self.nfa.to_string()
    115     }
    116 
    117     #[wasm_bindgen]
    118     pub fn dfa_to_string(&self) -> String {
    119         self.regex.automaton.to_string()
    120     }
    121 
    122     #[wasm_bindgen]
    123     pub fn enfa_dot(&self) -> Result<String, WebAutomatonError> {
    124         (&self.enfa)
    125             .try_into()
    126             .map(|d: Dot<GraphENFATransition>| d.to_string())
    127             .map_err(|e| e.into())
    128             .into()
    129     }
    130 
    131     #[wasm_bindgen]
    132     pub fn nfa_dot(&self) -> Result<String, WebAutomatonError> {
    133         (&self.nfa)
    134             .try_into()
    135             .map(|d: Dot<NFATransition>| d.to_string())
    136             .map_err(|e| e.into())
    137             .into()
    138     }
    139 
    140     #[wasm_bindgen]
    141     pub fn dfa_dot(&self) -> Result<String, WebAutomatonError> {
    142         (&self.regex.automaton)
    143             .try_into()
    144             .map(|d: Dot<DFATransition>| d.to_string())
    145             .map_err(|e| e.into())
    146             .into()
    147     }
    148 }