#[macro_use]
extern crate error_chain;
#[macro_use]
extern crate nom;
mod errors;
pub use errors::{Result, Error};
mod parser;
use parser::Exp;
use std::collections::HashMap;
pub struct Tpl<'a> {
template: Vec<Exp<'a>>,
len: usize,
}
impl<'a> Tpl<'a> {
pub fn new(tpl_str: &'a str) -> Result<Tpl<'a>> {
Ok(Tpl {
len: tpl_str.len(),
template: parser::parse(tpl_str)?,
})
}
pub fn render(&self, context: &HashMap<&'static str, String>) -> String {
self.template.iter().fold(
String::with_capacity(self.len),
|mut buff, exp| {
match *exp {
Exp::Literal(text) => buff.push_str(text),
Exp::Func { name } => {
match context.get(name) {
Some(value) => buff.push_str(value),
None => buff.push_str(name),
}
}
}
buff
},
)
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn render_template() {
let tpl = Tpl::new("Hello %{name}!").unwrap();
let mut context = HashMap::new();
context.insert("name".into(), "world".into());
assert_eq!(tpl.render(&context), "Hello world!");
}
}