1use serde::{Deserialize, Serialize};
4use serde_json::Value as JsonValue;
5
6use crate::pack::PackMetadata;
7use crate::release::ReleaseInfo;
8use crate::values::Values;
9
10#[derive(Debug, Clone, Serialize, Deserialize)]
12pub struct TemplateContext {
13 pub values: JsonValue,
15
16 pub release: ReleaseInfo,
18
19 pub pack: PackInfo,
21
22 pub capabilities: Capabilities,
24
25 pub template: TemplateInfo,
27}
28
29#[derive(Debug, Clone, Serialize, Deserialize)]
31#[serde(rename_all = "camelCase")]
32pub struct PackInfo {
33 pub name: String,
35
36 pub version: String,
38
39 pub app_version: Option<String>,
41}
42
43impl From<&PackMetadata> for PackInfo {
44 fn from(meta: &PackMetadata) -> Self {
45 Self {
46 name: meta.name.clone(),
47 version: meta.version.to_string(),
48 app_version: meta.app_version.clone(),
49 }
50 }
51}
52
53#[derive(Debug, Clone, Default, Serialize, Deserialize)]
55#[serde(rename_all = "camelCase")]
56pub struct Capabilities {
57 pub kube_version: KubeVersion,
59
60 pub api_versions: Vec<String>,
62}
63
64#[derive(Debug, Clone, Serialize, Deserialize)]
66#[serde(rename_all = "camelCase")]
67pub struct KubeVersion {
68 pub version: String,
69 pub major: String,
70 pub minor: String,
71}
72
73impl Default for KubeVersion {
74 fn default() -> Self {
75 Self {
77 version: "v1.28.0".to_string(),
78 major: "1".to_string(),
79 minor: "28".to_string(),
80 }
81 }
82}
83
84impl KubeVersion {
85 pub fn new(version: &str) -> Self {
86 let version = version.trim_start_matches('v');
87 let parts: Vec<&str> = version.split('.').collect();
88
89 Self {
90 version: format!("v{}", version),
91 major: parts.first().unwrap_or(&"1").to_string(),
92 minor: parts.get(1).unwrap_or(&"28").to_string(),
93 }
94 }
95}
96
97#[derive(Debug, Clone, Default, Serialize, Deserialize)]
99#[serde(rename_all = "camelCase")]
100pub struct TemplateInfo {
101 pub name: String,
103
104 pub base_path: String,
106}
107
108impl TemplateContext {
109 pub fn new(values: Values, release: ReleaseInfo, pack: &PackMetadata) -> Self {
111 Self {
112 values: values.into_inner(),
113 release,
114 pack: PackInfo::from(pack),
115 capabilities: Capabilities::default(),
116 template: TemplateInfo::default(),
117 }
118 }
119
120 pub fn with_template(mut self, name: &str, base_path: &str) -> Self {
122 self.template = TemplateInfo {
123 name: name.to_string(),
124 base_path: base_path.to_string(),
125 };
126 self
127 }
128
129 pub fn with_capabilities(mut self, capabilities: Capabilities) -> Self {
131 self.capabilities = capabilities;
132 self
133 }
134
135 pub fn to_json(&self) -> JsonValue {
137 serde_json::to_value(self).unwrap_or(JsonValue::Null)
138 }
139}
140
141#[cfg(test)]
142mod tests {
143 use super::*;
144 use semver::Version;
145
146 #[test]
147 fn test_template_context() {
148 let values = Values::from_yaml("replicas: 3").unwrap();
149 let release = ReleaseInfo::for_install("myapp", "default");
150 let pack = PackMetadata {
151 name: "mypack".to_string(),
152 version: Version::new(1, 0, 0),
153 description: None,
154 app_version: Some("2.0.0".to_string()),
155 kube_version: None,
156 home: None,
157 icon: None,
158 sources: vec![],
159 keywords: vec![],
160 maintainers: vec![],
161 annotations: Default::default(),
162 };
163
164 let ctx = TemplateContext::new(values, release, &pack);
165
166 assert_eq!(ctx.pack.name, "mypack");
167 assert_eq!(ctx.release.name, "myapp");
168 assert!(ctx.release.is_install);
169 }
170}