use std::collections::HashMap;
use serde::{Deserialize, Serialize};
use serde_json::Value;
use crate::types::output::OutputValue;
#[derive(Debug, Clone, Deserialize, Serialize)]
pub struct StateRepresentation {
pub format_version: String,
pub terraform_version: String,
pub values: StateValues,
}
#[derive(Debug, Clone, Deserialize, Serialize)]
pub struct StateValues {
#[serde(default)]
pub outputs: HashMap<String, OutputValue>,
pub root_module: Module,
}
#[derive(Debug, Clone, Deserialize, Serialize)]
pub struct Module {
#[serde(default)]
pub resources: Vec<Resource>,
#[serde(default)]
pub child_modules: Vec<ChildModule>,
}
#[derive(Debug, Clone, Deserialize, Serialize)]
pub struct ChildModule {
pub address: String,
#[serde(default)]
pub resources: Vec<Resource>,
#[serde(default)]
pub child_modules: Vec<ChildModule>,
}
#[derive(Debug, Clone, Deserialize, Serialize)]
pub struct Resource {
pub address: String,
pub mode: String,
#[serde(rename = "type")]
pub resource_type: String,
pub name: String,
pub provider_name: String,
pub schema_version: u32,
#[serde(default)]
pub values: Value,
#[serde(default)]
pub sensitive_values: Value,
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn deserialize_state() {
let json = r#"{
"format_version": "1.0",
"terraform_version": "1.14.6",
"values": {
"outputs": {
"id": {
"sensitive": false,
"value": "123456",
"type": "string"
}
},
"root_module": {
"resources": [
{
"address": "null_resource.example",
"mode": "managed",
"type": "null_resource",
"name": "example",
"provider_name": "registry.terraform.io/hashicorp/null",
"schema_version": 0,
"values": {"id": "123456", "triggers": {"value": "hello"}},
"sensitive_values": {"triggers": {}}
}
]
}
}
}"#;
let state: StateRepresentation = serde_json::from_str(json).unwrap();
assert_eq!(state.format_version, "1.0");
assert_eq!(state.values.outputs.len(), 1);
assert_eq!(state.values.root_module.resources.len(), 1);
assert_eq!(
state.values.root_module.resources[0].address,
"null_resource.example"
);
assert_eq!(state.values.root_module.resources[0].mode, "managed");
}
#[test]
fn deserialize_state_no_outputs() {
let json = r#"{
"format_version": "1.0",
"terraform_version": "1.14.6",
"values": {
"root_module": {
"resources": []
}
}
}"#;
let state: StateRepresentation = serde_json::from_str(json).unwrap();
assert!(state.values.outputs.is_empty());
assert!(state.values.root_module.resources.is_empty());
}
}