cargo_image_runner/image/
template.rs1use crate::core::error::Result;
2use std::collections::HashMap;
3
4pub struct TemplateProcessor;
6
7impl TemplateProcessor {
8 pub fn process(content: &str, vars: &HashMap<String, String>) -> Result<String> {
12 let mut result = content.to_string();
13
14 for (key, value) in vars {
16 let placeholder = format!("{{{{{}}}}}", key);
17 result = result.replace(&placeholder, value);
18 }
19
20 for (key, value) in vars {
23 let placeholder = format!("${}", key);
24 result = result.replace(&placeholder, value);
25 }
26
27 Ok(result)
28 }
29}
30
31#[cfg(test)]
32mod tests {
33 use super::*;
34
35 #[test]
36 fn test_template_double_brace() {
37 let mut vars = HashMap::new();
38 vars.insert("NAME".to_string(), "test".to_string());
39 vars.insert("VALUE".to_string(), "123".to_string());
40
41 let content = "Hello {{NAME}}, value is {{VALUE}}";
42 let result = TemplateProcessor::process(content, &vars).unwrap();
43 assert_eq!(result, "Hello test, value is 123");
44 }
45
46 #[test]
47 fn test_template_dollar() {
48 let mut vars = HashMap::new();
49 vars.insert("VAR".to_string(), "substituted".to_string());
50
51 let content = "This is $VAR";
52 let result = TemplateProcessor::process(content, &vars).unwrap();
53 assert_eq!(result, "This is substituted");
54 }
55
56 #[test]
57 fn test_template_mixed() {
58 let mut vars = HashMap::new();
59 vars.insert("A".to_string(), "alpha".to_string());
60 vars.insert("B".to_string(), "beta".to_string());
61
62 let content = "{{A}} and $B";
63 let result = TemplateProcessor::process(content, &vars).unwrap();
64 assert_eq!(result, "alpha and beta");
65 }
66
67 #[test]
68 fn test_template_no_vars() {
69 let vars = HashMap::new();
70 let content = "Hello, world!";
71 let result = TemplateProcessor::process(content, &vars).unwrap();
72 assert_eq!(result, "Hello, world!");
73 }
74
75 #[test]
76 fn test_template_empty_content() {
77 let vars = HashMap::new();
78 let result = TemplateProcessor::process("", &vars).unwrap();
79 assert_eq!(result, "");
80 }
81
82 #[test]
83 fn test_template_unknown_var_preserved() {
84 let mut vars = HashMap::new();
85 vars.insert("KNOWN".to_string(), "value".to_string());
86
87 let content = "{{KNOWN}} and {{UNKNOWN}}";
88 let result = TemplateProcessor::process(content, &vars).unwrap();
89 assert_eq!(result, "value and {{UNKNOWN}}");
90 }
91
92 #[test]
93 fn test_template_repeated_var() {
94 let mut vars = HashMap::new();
95 vars.insert("X".to_string(), "42".to_string());
96
97 let content = "{{X}} + {{X}} = 2*{{X}}";
98 let result = TemplateProcessor::process(content, &vars).unwrap();
99 assert_eq!(result, "42 + 42 = 2*42");
100 }
101
102 #[test]
103 fn test_template_multiline() {
104 let mut vars = HashMap::new();
105 vars.insert("TIMEOUT".to_string(), "5".to_string());
106 vars.insert("EXECUTABLE_NAME".to_string(), "kernel.elf".to_string());
107 vars.insert("CMDLINE".to_string(), "quiet".to_string());
108
109 let content = "timeout: {{TIMEOUT}}\n\n/My Kernel\n protocol: limine\n kernel_path: boot():/boot/{{EXECUTABLE_NAME}}\n cmdline: {{CMDLINE}}";
110 let result = TemplateProcessor::process(content, &vars).unwrap();
111 assert_eq!(
112 result,
113 "timeout: 5\n\n/My Kernel\n protocol: limine\n kernel_path: boot():/boot/kernel.elf\n cmdline: quiet"
114 );
115 }
116}