Skip to main content

xml_disassembler/
types.rs

1//! Type definitions for XML element representation.
2//!
3//! Uses serde_json::Value for flexible representation matching the TypeScript structure:
4//! - Object with keys: element names, @attr for attributes, #text for text content, ?xml for declaration
5//! - Values: string, nested object, or array of objects/strings
6
7use serde_json::Value as JsonValue;
8
9/// XmlElement is a flexible representation of XML - equivalent to TypeScript's XmlElement type.
10/// Uses serde_json::Value for compatibility with quickxml_to_serde output.
11pub type XmlElement = JsonValue;
12
13/// Parameters for parsing an element during disassembly.
14#[derive(Debug, Clone)]
15pub struct XmlElementParams<'a> {
16    pub element: XmlElement,
17    pub disassembled_path: &'a str,
18    pub unique_id_elements: Option<&'a str>,
19    pub root_element_name: &'a str,
20    pub root_attributes: XmlElement,
21    pub key: &'a str,
22    pub leaf_content: XmlElement,
23    pub leaf_count: usize,
24    pub has_nested_elements: bool,
25    pub format: &'a str,
26    pub xml_declaration: Option<XmlElement>,
27    pub strategy: &'a str,
28}
29
30/// Options for building a single disassembled file.
31#[derive(Debug, Clone)]
32pub struct BuildDisassembledFileOptions<'a> {
33    pub content: XmlElement,
34    pub disassembled_path: &'a str,
35    pub output_file_name: Option<&'a str>,
36    pub subdirectory: Option<&'a str>,
37    pub wrap_key: Option<&'a str>,
38    pub is_grouped_array: bool,
39    pub root_element_name: &'a str,
40    pub root_attributes: XmlElement,
41    pub format: &'a str,
42    pub xml_declaration: Option<XmlElement>,
43    pub unique_id_elements: Option<&'a str>,
44}
45
46/// Result from unified element parsing.
47#[derive(Debug, Clone, Default)]
48pub struct UnifiedParseResult {
49    pub leaf_content: XmlElement,
50    pub leaf_count: usize,
51    pub has_nested_elements: bool,
52    pub nested_groups: Option<XmlElementArrayMap>,
53}
54
55/// Map of tag name to array of elements.
56pub type XmlElementArrayMap = std::collections::HashMap<String, Vec<XmlElement>>;
57
58/// Rule for decomposing a nested tag when using grouped-by-tag strategy.
59/// E.g. write each &lt;objectPermissions&gt; to its own file, or group &lt;fieldPermissions&gt; by object.
60#[derive(Debug, Clone)]
61pub struct DecomposeRule {
62    /// Element tag to decompose (e.g. "objectPermissions", "fieldPermissions").
63    pub tag: String,
64    /// Subdirectory under disassembled path (defaults to tag if empty).
65    pub path_segment: String,
66    /// "split" = one file per array item (filename from field); "group" = group by field, one file per group.
67    pub mode: String,
68    /// Field name: for split, used for filename; for group, used to group items.
69    pub field: String,
70}
71
72/// Options for building disassembled files from a source file.
73#[derive(Debug, Clone)]
74pub struct BuildDisassembledFilesOptions<'a> {
75    pub file_path: &'a str,
76    pub disassembled_path: &'a str,
77    pub base_name: &'a str,
78    pub post_purge: bool,
79    pub format: &'a str,
80    pub unique_id_elements: Option<&'a str>,
81    pub strategy: &'a str,
82    /// When strategy is grouped-by-tag, optionally decompose specific tags (split or group by field).
83    pub decompose_rules: Option<&'a [DecomposeRule]>,
84}
85
86/// Parameters for writing leaf content.
87#[derive(Debug, Clone)]
88pub struct LeafWriteParams<'a> {
89    pub leaf_count: usize,
90    pub leaf_content: XmlElement,
91    pub strategy: &'a str,
92    pub key_order: Vec<String>,
93    pub options: LeafWriteOptions<'a>,
94}
95
96#[derive(Debug, Clone)]
97pub struct LeafWriteOptions<'a> {
98    pub disassembled_path: &'a str,
99    pub output_file_name: &'a str,
100    pub root_element_name: &'a str,
101    pub root_attributes: XmlElement,
102    pub xml_declaration: Option<XmlElement>,
103    pub format: &'a str,
104}
105
106/// Rule for multi-level disassembly: which files to further disassemble and how.
107#[derive(Debug, Clone, serde::Serialize, serde::Deserialize)]
108pub struct MultiLevelRule {
109    /// File name pattern (e.g. "programProcesses-meta"); any XML file whose name contains this is processed.
110    pub file_pattern: String,
111    /// Root element to strip (e.g. "LoyaltyProgramSetup"); its inner content becomes the new document.
112    pub root_to_strip: String,
113    /// Comma-separated unique-id elements for the second-level disassembly (e.g. "parameterName,ruleName").
114    pub unique_id_elements: String,
115    /// Path segment under the disassembly root for reassembly (e.g. "programProcesses").
116    #[serde(default)]
117    pub path_segment: String,
118    /// Root element name to wrap reassembled files with (defaults to root_to_strip).
119    #[serde(default)]
120    pub wrap_root_element: String,
121    /// xmlns value for the wrap root (optional; captured from original when stripping).
122    #[serde(default)]
123    pub wrap_xmlns: String,
124}
125
126/// Persisted config for multi-level reassembly (stored as .multi_level.json in the disassembly root).
127#[derive(Debug, Clone, Default, serde::Serialize, serde::Deserialize)]
128pub struct MultiLevelConfig {
129    pub rules: Vec<MultiLevelRule>,
130}