Skip to main content

elasticctl_api/compose/
exception_coverage.rs

1use crate::{
2    Rule, exceptions,
3    model::{ListKey, exception_refs},
4};
5use elasticctl_core::{Error, Result, Transport};
6#[derive(Debug)]
7pub struct ListFacts {
8    pub name: Option<String>,
9    pub list_type: Option<String>,
10    pub item_count: u64,
11}
12#[derive(Debug)]
13pub struct ListCoverage {
14    pub key: ListKey,
15    pub ref_type: String,
16    pub facts: std::result::Result<ListFacts, Error>,
17}
18#[derive(Debug)]
19pub struct ExceptionCoverage {
20    pub referenced: usize,
21    pub truncated: bool,
22    pub lists: Vec<ListCoverage>,
23}
24pub async fn exception_coverage(t: &Transport, rule: &Rule) -> Result<ExceptionCoverage> {
25    let refs = exception_refs(rule);
26    let referenced = refs.len();
27    let mut lists = Vec::new();
28    for r in refs.into_iter().take(super::MAX_EXCEPTION_LISTS) {
29        let key = ListKey {
30            list_id: r.list_id,
31            namespace_type: r.namespace_type,
32        };
33        let facts: Result<ListFacts> = async {
34            let list = exceptions::get_list(t, &key).await?;
35            let item_count = exceptions::count_items(t, &key).await?;
36            let field = |k| -> Result<Option<String>> {
37                list.as_map()
38                    .get(k)
39                    .map(|v| {
40                        v.as_str().map(str::to_owned).ok_or_else(|| {
41                            Error::new(
42                                elasticctl_core::ErrorKind::Http,
43                                "invalid exception list field",
44                            )
45                        })
46                    })
47                    .transpose()
48            };
49            Ok(ListFacts {
50                name: field("name")?,
51                list_type: field("type")?,
52                item_count,
53            })
54        }
55        .await;
56        if let Err(e) = &facts
57            && super::is_fatal(e.kind)
58        {
59            return Err(facts.unwrap_err());
60        }
61        lists.push(ListCoverage {
62            key,
63            ref_type: r.ref_type,
64            facts,
65        });
66    }
67    Ok(ExceptionCoverage {
68        referenced,
69        truncated: referenced > super::MAX_EXCEPTION_LISTS,
70        lists,
71    })
72}