postfix_log_parser/formatters/json/
mod.rs

1use super::LogFormatter;
2use crate::events::ComponentEvent;
3use crate::parsing::ParseResult;
4use serde_json;
5use std::error::Error;
6
7pub mod cleanup;
8pub mod common;
9pub mod discard;
10pub mod error;
11pub mod postfix_script;
12pub mod postsuper;
13pub mod qmgr;
14pub mod relay;
15pub mod smtp;
16pub mod smtpd;
17
18pub use cleanup::format_cleanup_event;
19pub use common::*;
20pub use discard::DiscardJsonFormatter;
21pub use error::ErrorJsonFormatter;
22pub use postfix_script::format_postfix_script_event;
23pub use postsuper::format_postsuper_event;
24pub use qmgr::format_qmgr_event;
25pub use relay::RelayJsonFormatter;
26pub use smtp::format_smtp_event;
27pub use smtpd::format_smtpd_event;
28
29/// JSON格式化器
30pub struct JsonFormatter;
31
32impl JsonFormatter {
33    pub fn new() -> Self {
34        Self
35    }
36}
37
38impl LogFormatter for JsonFormatter {
39    fn format_single(
40        &self,
41        line_number: usize,
42        line: &str,
43        result: &ParseResult,
44    ) -> Result<String, Box<dyn Error>> {
45        let mut parsed_data = serde_json::Map::new();
46
47        // 基础字段
48        parsed_data.insert(
49            "line_number".to_string(),
50            serde_json::Value::Number(serde_json::Number::from(line_number)),
51        );
52        parsed_data.insert(
53            "original_line".to_string(),
54            serde_json::Value::String(line.to_string()),
55        );
56        parsed_data.insert(
57            "confidence".to_string(),
58            serde_json::Value::Number(
59                serde_json::Number::from_f64(result.confidence as f64).unwrap(),
60            ),
61        );
62
63        if let Some(event) = &result.event {
64            // 事件相关字段
65            parsed_data.insert(
66                "timestamp".to_string(),
67                serde_json::Value::String(event.timestamp.to_rfc3339()),
68            );
69            parsed_data.insert(
70                "hostname".to_string(),
71                serde_json::Value::String(event.hostname.clone()),
72            );
73            parsed_data.insert(
74                "component".to_string(),
75                serde_json::Value::String(event.component.clone()),
76            );
77            parsed_data.insert(
78                "process_id".to_string(),
79                serde_json::Value::Number(serde_json::Number::from(event.process_id)),
80            );
81            parsed_data.insert(
82                "log_level".to_string(),
83                serde_json::Value::String(format!("{:?}", event.log_level)),
84            );
85
86            if let Some(queue_id) = &event.queue_id {
87                parsed_data.insert(
88                    "queue_id".to_string(),
89                    serde_json::Value::String(queue_id.clone()),
90                );
91            }
92
93            // 处理具体事件类型
94            match &event.event {
95                ComponentEvent::Smtpd(smtpd_event) => {
96                    let event_data = format_smtpd_event(smtpd_event);
97                    for (key, value) in event_data {
98                        parsed_data.insert(key, value);
99                    }
100                }
101                ComponentEvent::Smtp(smtp_event) => {
102                    let event_data = format_smtp_event(smtp_event);
103                    for (key, value) in event_data {
104                        parsed_data.insert(key, value);
105                    }
106                }
107                ComponentEvent::Qmgr(qmgr_event) => {
108                    let event_data = format_qmgr_event(qmgr_event);
109                    for (key, value) in event_data {
110                        parsed_data.insert(key, value);
111                    }
112                }
113                ComponentEvent::Cleanup(cleanup_event) => {
114                    let event_data = format_cleanup_event(cleanup_event);
115                    if let serde_json::Value::Object(map) = event_data {
116                        for (key, value) in map {
117                            parsed_data.insert(key, value);
118                        }
119                    }
120                }
121                ComponentEvent::Error(error_event) => {
122                    let event_data = ErrorJsonFormatter::format_error_event(error_event);
123                    if let serde_json::Value::Object(map) = event_data {
124                        for (key, value) in map {
125                            parsed_data.insert(key, value);
126                        }
127                    }
128                }
129                ComponentEvent::Relay(relay_event) => {
130                    let event_data = RelayJsonFormatter::new().format_event(relay_event);
131                    if let serde_json::Value::Object(map) = event_data {
132                        for (key, value) in map {
133                            parsed_data.insert(key, value);
134                        }
135                    }
136                }
137                ComponentEvent::Discard(discard_event) => {
138                    let event_data = DiscardJsonFormatter::new().format_event(discard_event);
139                    if let serde_json::Value::Object(map) = event_data {
140                        for (key, value) in map {
141                            parsed_data.insert(key, value);
142                        }
143                    }
144                }
145                ComponentEvent::PostfixScript(postfix_script_event) => {
146                    let event_data = format_postfix_script_event(postfix_script_event);
147                    if let serde_json::Value::Object(map) = event_data {
148                        for (key, value) in map {
149                            parsed_data.insert(key, value);
150                        }
151                    }
152                }
153                ComponentEvent::Postsuper(postsuper_event) => {
154                    let event_data = format_postsuper_event(postsuper_event);
155                    if let serde_json::Value::Object(map) = event_data {
156                        for (key, value) in map {
157                            parsed_data.insert(key, value);
158                        }
159                    }
160                }
161                ComponentEvent::Unknown(unknown_event) => {
162                    parsed_data.insert(
163                        "event_type".to_string(),
164                        serde_json::Value::String("unknown".to_string()),
165                    );
166                    parsed_data.insert(
167                        "message".to_string(),
168                        serde_json::Value::String(unknown_event.message.clone()),
169                    );
170                }
171                _ => {
172                    parsed_data.insert(
173                        "event_type".to_string(),
174                        serde_json::Value::String("other".to_string()),
175                    );
176                    parsed_data.insert(
177                        "message".to_string(),
178                        serde_json::Value::String(format!("{:?}", event.event)),
179                    );
180                }
181            }
182        } else {
183            // 解析失败的情况
184            parsed_data.insert(
185                "error".to_string(),
186                serde_json::Value::String("parse_failed".to_string()),
187            );
188            if !result.parsing_errors.is_empty() {
189                parsed_data.insert(
190                    "error_details".to_string(),
191                    serde_json::Value::String(format!("{:?}", result.parsing_errors[0])),
192                );
193            }
194        }
195
196        Ok(serde_json::to_string(&serde_json::Value::Object(
197            parsed_data,
198        ))?)
199    }
200
201    fn format_multiple(
202        &self,
203        results: Vec<(usize, String, ParseResult)>,
204    ) -> Result<String, Box<dyn Error>> {
205        let mut json_objects = Vec::new();
206
207        for (line_number, line, result) in results {
208            let json_str = self.format_single(line_number, &line, &result)?;
209            let json_value: serde_json::Value = serde_json::from_str(&json_str)?;
210            json_objects.push(json_value);
211        }
212
213        let json_array = serde_json::Value::Array(json_objects);
214        Ok(serde_json::to_string_pretty(&json_array)?)
215    }
216}
217
218impl Default for JsonFormatter {
219    fn default() -> Self {
220        Self::new()
221    }
222}