1use core::processors::{PluginBridge, ProcessorRegistry};
2use std::fmt::Debug;
3
4use parser::parse_entry_content;
5
6pub mod core;
7pub mod types;
8pub mod errors;
9mod parser;
10mod tests;
11
12pub use types::WorldInfoType;
13pub use errors::{ParserError, WorldInfoError};
14
15
16
17pub struct WorldInfo<P: PluginBridge + 'static> {
18 name: String,
19 entries: Vec<WorldInfoEntry>,
20 permitted_processors: Vec<String>,
22 processor_registry: Box<ProcessorRegistry<P>>,
23 error_stack: Vec<WorldInfoError>,
24}
25
26impl<P: PluginBridge> WorldInfo<P>{
27 pub fn evaluate(&mut self) -> Result<String, &Vec<WorldInfoError>> {
28 let mut result = String::new();
29 let mut failed = false;
30 for entry in &mut self.entries {
31 match entry.parse(&self.processor_registry) {
32 Ok(_) => (),
33 Err(e) => {
34 self.error_stack.push(e);
35 failed = true;
36 }
37 }
38
39 if failed {
40 break;
41 }
42
43 match entry.evalute() {
44 Ok(content) => result.push_str(&content),
45 Err(e) => {
46 failed = true;
47 self.error_stack.push(e)
48 },
49 }
50 }
51
52 if failed {
53 Err(&self.error_stack)
54 } else {
55 Ok(result)
56 }
57 }
58}
59
60pub trait WorldInfoFactory<P: PluginBridge> {
61 fn new(registry: Box<ProcessorRegistry<P>>) -> Self;
63 fn set_name(&mut self, name: &str) -> &mut Self;
65 fn insert_entry(&mut self, entry: WorldInfoEntry) -> &mut Self;
67 fn set_permitted_processors(&mut self, processors: Vec<String>) -> &mut Self;
69 fn build(&self) -> &Self;
71
72 fn insert_entries(&mut self, entries: Vec<WorldInfoEntry>) -> &mut Self {
74 for entry in entries {
75 self.insert_entry(entry);
76 }
77 self
78 }
79}
80
81impl<P: PluginBridge> WorldInfoFactory<P> for WorldInfo<P> {
82 fn new(registry: Box<ProcessorRegistry<P>>) -> Self {
83 WorldInfo {
84 name: String::new(),
85 entries: Vec::new(),
86 permitted_processors: Vec::new(),
87 processor_registry: registry,
88 error_stack: Vec::new()
89 }
90 }
91 fn set_name(&mut self, name: &str) -> &mut Self {
92 self.name = name.to_string();
93 self
94 }
95 fn insert_entry(&mut self, entry: WorldInfoEntry) -> &mut Self {
96 self.entries.push(entry);
97 self
98 }
99 fn set_permitted_processors(&mut self, processors: Vec<String>) -> &mut Self {
100 self.permitted_processors = processors;
101 self
102 }
103 fn build(&self) -> &WorldInfo::<P> {
104 self
105 }
106}
107
108pub struct WorldInfoEntry {
109 name: String,
110 id: u32,
111 order: u32,
112 nodes: Vec<Box<dyn WorldInfoNode>>,
113 text: String
114}
115
116
117impl WorldInfoEntry {
118 pub fn new(name: String, id: u32, order: u32) -> Self {
119 Self { name, id, order, nodes: Vec::new(), text: String::new() }
120 }
121
122 pub fn evalute(&self) -> Result<String, crate::WorldInfoError> {
123 let mut result = String::new();
124 for node in &self.nodes {
125 match node.content() {
126 Ok(content) => result.push_str(&content),
127 Err(err) => return Err(err)
128 }
129 }
130 Ok(result.into())
131 }
132
133 pub fn name(&self) -> String {
134 self.name.clone()
135 }
136
137 pub fn id(&self) -> u32 {
138 self.id
139 }
140
141 pub fn order(&self) -> u32 {
142 self.order
143 }
144}
145
146pub trait EntryFactory {
147 fn create(name: &str, id: u32, order: u32) -> WorldInfoEntry;
148 fn set_text(&mut self, text: &str) -> &mut WorldInfoEntry;
149 fn parse<P: PluginBridge>(&mut self, registry: &ProcessorRegistry<P>) -> Result<&mut WorldInfoEntry, WorldInfoError>;
150}
151
152impl EntryFactory for WorldInfoEntry {
153 fn create(name: &str, id: u32, order: u32) -> WorldInfoEntry {
154 WorldInfoEntry::new(name.to_string(), id, order)
155 }
156 fn parse<P: PluginBridge>(&mut self, registry: &ProcessorRegistry<P>) -> Result<&mut WorldInfoEntry, WorldInfoError> {
157 println!("Parsing node: {:?}", self.text);
158 match parse_entry_content(&self.text, registry) {
159 Ok(nodes) => self.nodes = nodes,
160 Err(e) => return Err(WorldInfoError::ParserError(e)),
161 }
162 Ok(self)
163 }
164
165 fn set_text(&mut self, text: &str) -> &mut WorldInfoEntry {
166 self.text = text.to_string();
167 self
168 }
169}
170
171pub trait WorldInfoNode: Debug {
172 fn content(&self) -> Result<String, crate::WorldInfoError>;
173 fn name(&self) -> String;
174 fn cloned(&self) -> Box<dyn WorldInfoNode + '_>;
175}
176
177pub trait WorldInfoProcessor: WorldInfoNode {
178 fn process(&self) -> Result<String, crate::WorldInfoError>;
179}
180
181#[derive(Debug, Clone)]
182struct TextNode {
183 content: String,
184}
185
186impl WorldInfoNode for TextNode {
187 fn content(&self) -> Result<String, crate::WorldInfoError> {
188 Ok(self.content.clone())
189 }
190
191 fn name(&self) -> String {
192 "text".to_string()
193 }
194
195 fn cloned(&self) -> Box<dyn WorldInfoNode> {
196 Box::new(self.to_owned())
197 }
198}
199