syslog_rs/formatters/mod.rs
1/*-
2 * syslog-rs - a syslog client translated from libc to rust
3 *
4 * Copyright 2025 Aleksandr Morozov
5 *
6 * The syslog-rs crate can be redistributed and/or modified
7 * under the terms of either of the following licenses:
8 *
9 * 1. the Mozilla Public License Version 2.0 (the “MPL”) OR
10 *
11 * 2. The MIT License (MIT)
12 *
13 * 3. EUROPEAN UNION PUBLIC LICENCE v. 1.2 EUPL © the European Union 2007, 2016
14 */
15
16/// A list of build-in formatters.
17///
18/// Excluding Windows specific.
19#[derive(Debug, Clone, Copy, PartialEq, Eq)]
20pub enum SyslogFormatters
21{
22 FormatRfc3146,
23 FormatRfc5424,
24 FormatFile,
25}
26
27impl FromStr for SyslogFormatters
28{
29 type Err = SyslogError;
30
31 fn from_str(s: &str) -> Result<Self, Self::Err>
32 {
33 let s_up = s.to_ascii_uppercase();
34
35 match s_up.as_str()
36 {
37 Self::FORMAT_RFC3146_NAME =>
38 return Ok(Self::FormatRfc3146),
39 Self::FORMAT_RFC5424_NAME =>
40 return Ok(Self::FormatRfc5424),
41 Self::FORMAT_FILE_NAME =>
42 return Ok(Self::FormatFile),
43 n =>
44 throw_error!("unknown syslog formatter: {}", n)
45 }
46 }
47}
48
49impl SyslogFormatters
50{
51 pub const FORMAT_RFC3146_NAME: &'static str = FormatRfc3146::FORMATTER_NAME;
52 pub const FORMAT_RFC5424_NAME: &'static str = FormatRfc5424::FORMATTER_NAME;
53 pub const FORMAT_FILE_NAME: &'static str = FormatFile::FORMATTER_NAME;
54}
55
56/// A container which holds the formatted message and a range of slices
57/// which are suitable for the stderror output or syscons output.
58/// Normally, the `stderr_range` is a message without `PRI` and other headers
59///
60/// For example for the message type <34> Mon 12 ... the stderr_tange can be 1..
61/// which will exclude the <34>.
62#[derive(Debug)]
63pub struct SyslogFormatted
64{
65 /// A header
66 msg_header: Option<String>,
67
68 /// A msg which is sent to stderr if needed. Usually this is a message without PRI
69 msg_payload: String,
70
71 /// A cache in case if it will be reqired to obtain a full message which consists
72 /// from header and payload.
73 full_msg: Option<String>,
74}
75
76impl SyslogFormatted
77{
78 /// Constructs new container.
79 pub
80 fn new(msg_header: Option<String>, msg_payload: String) -> Self
81 {
82 return Self{ msg_header: msg_header, msg_payload: msg_payload, full_msg: None };
83 }
84
85 /// Returns the payload without header.
86 pub(crate)
87 fn get_stderr_output(&self) -> &str
88 {
89 return &self.msg_payload;
90 }
91
92 /// Returns the concatinated message (headr+payload) or just a payload
93 /// if header does not present.
94 pub(crate)
95 fn get_full_msg(&mut self) -> &str
96 {
97 if self.full_msg.is_some() == true
98 {
99 return self.full_msg.as_ref().unwrap();
100 }
101 else
102 {
103 let header=
104 if self.msg_header.is_some() == true
105 {
106 let msg = [self.msg_header.as_ref().unwrap().as_str(), self.msg_payload.as_str()].concat();
107
108 self.full_msg.replace(msg);
109
110 self.full_msg.as_ref().unwrap().as_str()
111 }
112 else
113 {
114 self.msg_payload.as_ref()
115 };
116
117 return header;
118 }
119 }
120}
121
122/// A trait for the custom syslog formatter.
123pub trait SyslogFormatter: std::fmt::Debug + Send + Sync + Clone + From<String> + From<&'static str> + 'static
124{
125 /// Formats the message for the syslog server with specific protocol or
126 /// RFC.
127 ///
128 /// # Arguments
129 ///
130 /// * `max_msg_size` - a max msg size in bytes.
131 ///
132 /// * `prifac` - a [SyslogMsgPriFac] a prepared PRI header value.
133 ///
134 /// * `progname` - a ref to program name or identifier which is set during init.
135 ///
136 /// * `pid` - an [Option] value where inner constains a PID number already converted
137 /// into `string` form. If [Option::None] is provided, a [crate::LogStat::LOG_PID] was
138 /// not set during init. The formatter must exclude the `PID` from the report.
139 ///
140 /// # Returns
141 ///
142 /// A [SyslogFormatted] should be returned.
143 fn vsyslog1_format(&self, max_msg_size: usize, prifac: SyslogMsgPriFac, progname: &str, pid: Option<&str>) -> SyslogFormatted;
144}
145
146/// A windows specific formatter (which is not bounded to any standart).
147/// Used for Windows Event Log and not appliciable to the rest logging.
148#[cfg(target_os = "windows")]
149pub mod windows_10;
150
151/// RFC3146 based formatter.
152pub mod syslog_3146;
153
154/// RFC5424 based formatter.
155pub mod syslog_5424;
156
157/// Formatter for local file (which is not bounded to any standart).
158pub mod syslog_file;
159
160use std::str::FromStr;
161
162pub use syslog_3146::FormatRfc3146;
163pub use syslog_5424::FormatRfc5424;
164pub use syslog_file::FormatFile;
165
166#[cfg(target_os = "windows")]
167pub use windows_10::FormatWindows;
168
169use crate::{SyslogMsgPriFac, error::SyslogError, throw_error};
170
171/// A default syslog formatter. For GNU/Linux it is RFC3146
172#[cfg(target_os = "linux")]
173pub type DefaultSyslogFormatter = FormatRfc3146;
174
175/// A default syslog formatter. For GNU/Linux it is RFC3146 (as a runtime type)
176#[cfg(target_os = "linux")]
177pub const DEFAULT_SYSLOG_FORMATTER_TYPE: SyslogFormatters = SyslogFormatters::FormatRfc3146;
178
179/// A default syslog formatter. For xBSD it is RFC5424
180#[cfg(any(
181 target_os = "freebsd",
182 target_os = "dragonfly",
183 target_os = "openbsd",
184 target_os = "netbsd",
185 target_os = "macos"
186))]
187pub type DefaultSyslogFormatter = FormatRfc5424;
188
189/// A default syslog formatter. For xBSD it is RFC5424 (as a runtime type)
190#[cfg(any(
191 target_os = "freebsd",
192 target_os = "dragonfly",
193 target_os = "openbsd",
194 target_os = "netbsd",
195 target_os = "macos"
196))]
197pub const DEFAULT_SYSLOG_FORMATTER_TYPE: SyslogFormatters = SyslogFormatters::FormatRfc5424;
198
199/// If the crate is compiled on the Windows OS, the value is set to
200/// the one which is for the Local Windows Event Log because by default
201/// the default syslog instance is `local`. You must override the value
202/// if working with remote or local syslog.
203#[cfg(target_os = "windows")]
204pub type DefaultSyslogFormatter = FormatWindows;
205
206/// A default syslog message formatter for local files.
207pub type DefaultSyslogFormatterFile = FormatFile;