resrap_rs/
lib.rs

1mod core;
2use std::collections::HashMap;
3
4use crate::core::{file::Lang, prng::PRNG};
5
6/// Resrap is the main access point for single-threaded uses.
7/// It's a collection of grammars which can be generated using parsing grammar.
8pub struct Resrap {
9    language_graph: HashMap<String, Lang>,
10}
11
12impl Resrap {
13    /// Creates and returns a new Resrap instance.
14    /// The returned instance starts with no loaded grammars.
15    pub fn new() -> Self {
16        Resrap {
17            language_graph: HashMap::new(),
18        }
19    }
20
21    /// Parses a grammar string and stores it under the given name.
22    ///
23    /// # Arguments
24    /// * `name` - A unique identifier for this grammar (e.g., "C"), should be in ABNF format
25    ///            (Check osdc/resrap for more info on that).
26    /// * `grammar` - The grammar string to parse
27    ///
28    /// # Returns
29    /// Returns error generated while parsing
30    pub fn parse_grammar(&mut self, name: String, grammar: String) -> Result<(), String> {
31        let mut lang = Lang::new();
32        let err = lang.parse_string(grammar);
33
34        self.language_graph.insert(name.clone(), lang);
35        err
36    }
37
38    /// Parses a grammar from a file and stores it under the given name.
39    ///
40    /// # Arguments
41    /// * `name` - A unique identifier for this grammar (e.g., "C"), should be in ABNF format
42    ///            (Check osdc/resrap for more info on that).
43    /// * `location` - Path to the grammar file
44    ///
45    /// # Returns
46    /// Returns error generated while parsing
47    pub fn parse_grammar_file(&mut self, name: String, location: String) -> Result<(), String> {
48        let mut lang = Lang::new();
49        let err = lang.parse_file(location);
50
51        self.language_graph.insert(name.clone(), lang);
52        err
53    }
54
55    /// Generates content from the grammar identified by 'name' with a seed.
56    ///
57    /// # Arguments
58    /// * `name` - The grammar name to use
59    /// * `starting_node` - The starting symbol in the grammar for generation
60    /// * `seed` - A numeric seed to make generation deterministic
61    /// * `tokens` - Number of tokens to generate
62    ///
63    /// # Returns
64    /// A string containing the generated content.
65    pub fn generate_with_seed(
66        &self,
67        name: &str,
68        starting_node: String,
69        seed: u64,
70        tokens: usize,
71    ) -> Result<Vec<String>, &str> {
72        let prng = PRNG::new(seed);
73        self.language_graph
74            .get(name)
75            .unwrap()
76            .get_graph()
77            .unwrap()
78            .walk_graph(prng, starting_node, tokens)
79    }
80}
81
82impl Default for Resrap {
83    fn default() -> Self {
84        Self::new()
85    }
86}