1pub(crate) mod auth;
4pub(crate) mod dashboard;
5pub(crate) mod downtime;
6pub(crate) mod events;
7pub(crate) mod format;
8pub(crate) mod helpers;
9pub(crate) mod hosts;
10pub(crate) mod logs;
11pub(crate) mod metrics;
12pub(crate) mod monitor;
13pub(crate) mod slo;
14
15use anyhow::Result;
16use clap::{Parser, Subcommand};
17
18#[derive(Parser)]
20pub struct DatadogCommand {
21 #[command(subcommand)]
23 pub command: DatadogSubcommands,
24}
25
26#[derive(Subcommand)]
28pub enum DatadogSubcommands {
29 Auth(auth::AuthCommand),
31 Dashboard(dashboard::DashboardCommand),
33 Downtime(downtime::DowntimeCommand),
35 Events(events::EventsCommand),
37 Hosts(hosts::HostsCommand),
39 Logs(logs::LogsCommand),
41 Metrics(metrics::MetricsCommand),
43 Monitor(monitor::MonitorCommand),
45 Slo(slo::SloCommand),
47}
48
49impl DatadogCommand {
50 pub async fn execute(self) -> Result<()> {
52 match self.command {
53 DatadogSubcommands::Auth(cmd) => cmd.execute().await,
54 DatadogSubcommands::Dashboard(cmd) => cmd.execute().await,
55 DatadogSubcommands::Downtime(cmd) => cmd.execute().await,
56 DatadogSubcommands::Events(cmd) => cmd.execute().await,
57 DatadogSubcommands::Hosts(cmd) => cmd.execute().await,
58 DatadogSubcommands::Logs(cmd) => cmd.execute().await,
59 DatadogSubcommands::Metrics(cmd) => cmd.execute().await,
60 DatadogSubcommands::Monitor(cmd) => cmd.execute().await,
61 DatadogSubcommands::Slo(cmd) => cmd.execute().await,
62 }
63 }
64}
65
66#[cfg(test)]
67#[allow(clippy::unwrap_used)]
68mod tests {
69 use super::*;
70 use crate::cli::datadog::format::OutputFormat;
71 use crate::datadog::test_support::{with_empty_home, EnvGuard};
72
73 #[test]
74 fn datadog_subcommands_auth_variant() {
75 let cmd = DatadogCommand {
76 command: DatadogSubcommands::Auth(auth::AuthCommand {
77 command: auth::AuthSubcommands::Status(auth::StatusCommand),
78 }),
79 };
80 assert!(matches!(cmd.command, DatadogSubcommands::Auth(_)));
81 }
82
83 #[test]
84 fn datadog_subcommands_metrics_variant() {
85 let cmd = DatadogCommand {
86 command: DatadogSubcommands::Metrics(metrics::MetricsCommand {
87 command: metrics::MetricsSubcommands::Query(metrics::query::QueryCommand {
88 query: "m".into(),
89 from: "1h".into(),
90 to: None,
91 output: OutputFormat::Table,
92 }),
93 }),
94 };
95 assert!(matches!(cmd.command, DatadogSubcommands::Metrics(_)));
96 }
97
98 #[tokio::test]
99 async fn datadog_command_dispatches_auth_logout() {
100 let guard = EnvGuard::take();
101 let _dir = with_empty_home(&guard);
102 let cmd = DatadogCommand {
103 command: DatadogSubcommands::Auth(auth::AuthCommand {
104 command: auth::AuthSubcommands::Logout(auth::LogoutCommand),
105 }),
106 };
107 cmd.execute().await.unwrap();
108 }
109
110 #[tokio::test]
111 async fn datadog_command_dispatches_metrics_query() {
112 let guard = EnvGuard::take();
113 let _dir = with_empty_home(&guard);
114 let cmd = DatadogCommand {
115 command: DatadogSubcommands::Metrics(metrics::MetricsCommand {
116 command: metrics::MetricsSubcommands::Query(metrics::query::QueryCommand {
117 query: "m".into(),
118 from: "1h".into(),
119 to: None,
120 output: OutputFormat::Table,
121 }),
122 }),
123 };
124 let err = cmd.execute().await.unwrap_err();
127 assert!(err.to_string().contains("not configured"));
128 }
129
130 #[tokio::test]
131 async fn datadog_command_dispatches_monitor_get() {
132 let guard = EnvGuard::take();
133 let _dir = with_empty_home(&guard);
134 let cmd = DatadogCommand {
135 command: DatadogSubcommands::Monitor(monitor::MonitorCommand {
136 command: monitor::MonitorSubcommands::Get(monitor::get::GetCommand {
137 id: 1,
138 output: OutputFormat::Table,
139 }),
140 }),
141 };
142 let err = cmd.execute().await.unwrap_err();
145 assert!(err.to_string().contains("not configured"));
146 }
147
148 #[tokio::test]
149 async fn datadog_command_dispatches_monitor_list() {
150 let guard = EnvGuard::take();
151 let _dir = with_empty_home(&guard);
152 let cmd = DatadogCommand {
153 command: DatadogSubcommands::Monitor(monitor::MonitorCommand {
154 command: monitor::MonitorSubcommands::List(monitor::list::ListCommand {
155 name: None,
156 tags: None,
157 monitor_tags: None,
158 limit: 5,
159 output: OutputFormat::Table,
160 }),
161 }),
162 };
163 let err = cmd.execute().await.unwrap_err();
164 assert!(err.to_string().contains("not configured"));
165 }
166
167 #[tokio::test]
168 async fn datadog_command_dispatches_monitor_search() {
169 let guard = EnvGuard::take();
170 let _dir = with_empty_home(&guard);
171 let cmd = DatadogCommand {
172 command: DatadogSubcommands::Monitor(monitor::MonitorCommand {
173 command: monitor::MonitorSubcommands::Search(monitor::search::SearchCommand {
174 query: "q".into(),
175 limit: 5,
176 output: OutputFormat::Table,
177 }),
178 }),
179 };
180 let err = cmd.execute().await.unwrap_err();
181 assert!(err.to_string().contains("not configured"));
182 }
183
184 #[test]
185 fn datadog_subcommands_dashboard_variant() {
186 let cmd = DatadogCommand {
187 command: DatadogSubcommands::Dashboard(dashboard::DashboardCommand {
188 command: dashboard::DashboardSubcommands::List(dashboard::list::ListCommand {
189 filter_shared: false,
190 output: OutputFormat::Table,
191 }),
192 }),
193 };
194 assert!(matches!(cmd.command, DatadogSubcommands::Dashboard(_)));
195 }
196
197 #[tokio::test]
198 async fn datadog_command_dispatches_dashboard_list() {
199 let guard = EnvGuard::take();
200 let _dir = with_empty_home(&guard);
201 let cmd = DatadogCommand {
202 command: DatadogSubcommands::Dashboard(dashboard::DashboardCommand {
203 command: dashboard::DashboardSubcommands::List(dashboard::list::ListCommand {
204 filter_shared: true,
205 output: OutputFormat::Table,
206 }),
207 }),
208 };
209 let err = cmd.execute().await.unwrap_err();
210 assert!(err.to_string().contains("not configured"));
211 }
212
213 #[tokio::test]
214 async fn datadog_command_dispatches_dashboard_get() {
215 let guard = EnvGuard::take();
216 let _dir = with_empty_home(&guard);
217 let cmd = DatadogCommand {
218 command: DatadogSubcommands::Dashboard(dashboard::DashboardCommand {
219 command: dashboard::DashboardSubcommands::Get(dashboard::get::GetCommand {
220 id: "abc".into(),
221 output: OutputFormat::Table,
222 }),
223 }),
224 };
225 let err = cmd.execute().await.unwrap_err();
226 assert!(err.to_string().contains("not configured"));
227 }
228
229 #[test]
230 fn datadog_subcommands_logs_variant() {
231 let cmd = DatadogCommand {
232 command: DatadogSubcommands::Logs(logs::LogsCommand {
233 command: logs::LogsSubcommands::Search(logs::search::SearchCommand {
234 filter: "*".into(),
235 from: "15m".into(),
236 to: "now".into(),
237 limit: 10,
238 sort: logs::search::SortArg::TimestampDesc,
239 output: OutputFormat::Table,
240 }),
241 }),
242 };
243 assert!(matches!(cmd.command, DatadogSubcommands::Logs(_)));
244 }
245
246 #[tokio::test]
247 async fn datadog_command_dispatches_logs_search() {
248 let guard = EnvGuard::take();
249 let _dir = with_empty_home(&guard);
250 let cmd = DatadogCommand {
251 command: DatadogSubcommands::Logs(logs::LogsCommand {
252 command: logs::LogsSubcommands::Search(logs::search::SearchCommand {
253 filter: "*".into(),
254 from: "15m".into(),
255 to: "now".into(),
256 limit: 10,
257 sort: logs::search::SortArg::TimestampDesc,
258 output: OutputFormat::Table,
259 }),
260 }),
261 };
262 let err = cmd.execute().await.unwrap_err();
263 assert!(err.to_string().contains("not configured"));
264 }
265
266 #[test]
267 fn datadog_subcommands_events_variant() {
268 let cmd = DatadogCommand {
269 command: DatadogSubcommands::Events(events::EventsCommand {
270 command: events::EventsSubcommands::List(events::list::ListCommand {
271 filter: None,
272 from: "1h".into(),
273 to: "now".into(),
274 limit: 10,
275 sources: None,
276 tags: None,
277 output: OutputFormat::Table,
278 }),
279 }),
280 };
281 assert!(matches!(cmd.command, DatadogSubcommands::Events(_)));
282 }
283
284 #[tokio::test]
285 async fn datadog_command_dispatches_events_list() {
286 let guard = EnvGuard::take();
287 let _dir = with_empty_home(&guard);
288 let cmd = DatadogCommand {
289 command: DatadogSubcommands::Events(events::EventsCommand {
290 command: events::EventsSubcommands::List(events::list::ListCommand {
291 filter: None,
292 from: "1h".into(),
293 to: "now".into(),
294 limit: 10,
295 sources: None,
296 tags: None,
297 output: OutputFormat::Table,
298 }),
299 }),
300 };
301 let err = cmd.execute().await.unwrap_err();
302 assert!(err.to_string().contains("not configured"));
303 }
304
305 #[test]
306 fn datadog_subcommands_slo_variant() {
307 let cmd = DatadogCommand {
308 command: DatadogSubcommands::Slo(slo::SloCommand {
309 command: slo::SloSubcommands::List(slo::list::ListCommand {
310 tags: None,
311 query: None,
312 ids: None,
313 metrics_query: None,
314 limit: 5,
315 output: OutputFormat::Table,
316 }),
317 }),
318 };
319 assert!(matches!(cmd.command, DatadogSubcommands::Slo(_)));
320 }
321
322 #[tokio::test]
323 async fn datadog_command_dispatches_slo_list() {
324 let guard = EnvGuard::take();
325 let _dir = with_empty_home(&guard);
326 let cmd = DatadogCommand {
327 command: DatadogSubcommands::Slo(slo::SloCommand {
328 command: slo::SloSubcommands::List(slo::list::ListCommand {
329 tags: None,
330 query: None,
331 ids: None,
332 metrics_query: None,
333 limit: 5,
334 output: OutputFormat::Table,
335 }),
336 }),
337 };
338 let err = cmd.execute().await.unwrap_err();
339 assert!(err.to_string().contains("not configured"));
340 }
341
342 #[tokio::test]
343 async fn datadog_command_dispatches_slo_get() {
344 let guard = EnvGuard::take();
345 let _dir = with_empty_home(&guard);
346 let cmd = DatadogCommand {
347 command: DatadogSubcommands::Slo(slo::SloCommand {
348 command: slo::SloSubcommands::Get(slo::get::GetCommand {
349 id: "abc".into(),
350 output: OutputFormat::Table,
351 }),
352 }),
353 };
354 let err = cmd.execute().await.unwrap_err();
355 assert!(err.to_string().contains("not configured"));
356 }
357
358 #[test]
359 fn datadog_subcommands_hosts_variant() {
360 let cmd = DatadogCommand {
361 command: DatadogSubcommands::Hosts(hosts::HostsCommand {
362 command: hosts::HostsSubcommands::List(hosts::list::ListCommand {
363 filter: None,
364 from: None,
365 limit: 5,
366 output: OutputFormat::Table,
367 }),
368 }),
369 };
370 assert!(matches!(cmd.command, DatadogSubcommands::Hosts(_)));
371 }
372
373 #[tokio::test]
374 async fn datadog_command_dispatches_hosts_list() {
375 let guard = EnvGuard::take();
376 let _dir = with_empty_home(&guard);
377 let cmd = DatadogCommand {
378 command: DatadogSubcommands::Hosts(hosts::HostsCommand {
379 command: hosts::HostsSubcommands::List(hosts::list::ListCommand {
380 filter: None,
381 from: None,
382 limit: 5,
383 output: OutputFormat::Table,
384 }),
385 }),
386 };
387 let err = cmd.execute().await.unwrap_err();
388 assert!(err.to_string().contains("not configured"));
389 }
390
391 #[test]
392 fn datadog_subcommands_downtime_variant() {
393 let cmd = DatadogCommand {
394 command: DatadogSubcommands::Downtime(downtime::DowntimeCommand {
395 command: downtime::DowntimeSubcommands::List(downtime::list::ListCommand {
396 active_only: false,
397 output: OutputFormat::Table,
398 }),
399 }),
400 };
401 assert!(matches!(cmd.command, DatadogSubcommands::Downtime(_)));
402 }
403
404 #[tokio::test]
405 async fn datadog_command_dispatches_downtime_list() {
406 let guard = EnvGuard::take();
407 let _dir = with_empty_home(&guard);
408 let cmd = DatadogCommand {
409 command: DatadogSubcommands::Downtime(downtime::DowntimeCommand {
410 command: downtime::DowntimeSubcommands::List(downtime::list::ListCommand {
411 active_only: true,
412 output: OutputFormat::Table,
413 }),
414 }),
415 };
416 let err = cmd.execute().await.unwrap_err();
417 assert!(err.to_string().contains("not configured"));
418 }
419
420 #[tokio::test]
421 async fn datadog_command_dispatches_metrics_catalog_list() {
422 let guard = EnvGuard::take();
423 let _dir = with_empty_home(&guard);
424 let cmd = DatadogCommand {
425 command: DatadogSubcommands::Metrics(metrics::MetricsCommand {
426 command: metrics::MetricsSubcommands::Catalog(metrics::catalog::CatalogCommand {
427 command: metrics::catalog::CatalogSubcommands::List(
428 metrics::catalog::list::ListCommand {
429 host: None,
430 from: None,
431 output: OutputFormat::Table,
432 },
433 ),
434 }),
435 }),
436 };
437 let err = cmd.execute().await.unwrap_err();
438 assert!(err.to_string().contains("not configured"));
439 }
440}