use ihe_atna::balp::{Described, Detail, Entity, OTHER};
use super::detail;
use crate::transformation::{Elements, Transformation};
pub const TRANSFORMATION_ENTITY: &str = "ehds-transformation";
pub const TRANSFORMATION_DESCRIPTION: &str = "Semantic transformation: the mapping this access \
applied between openEHR and the exchange format, with the elements it transcoded, left \
untranscoded and dropped, counted by path and never by value (eHealth Network General \
Guidelines Release 3.1 Art 6(3)).";
pub(super) fn entity(transformation: &Transformation) -> Entity {
let mapping = &transformation.mapping;
let mut details = vec![Detail::new(
detail::TRANSFORMATION_DIRECTION,
transformation.direction.code(),
)];
details.extend(
transformation
.category
.iter()
.map(|category| Detail::new(detail::TRANSFORMATION_CATEGORY, category.token())),
);
details.extend(
mapping
.context
.iter()
.map(|context| Detail::new(detail::MAPPING_CONTEXT, context.clone())),
);
details.push(Detail::new(
detail::MAPPING_TEMPLATE,
mapping.template.clone(),
));
details.extend(
mapping
.profile
.iter()
.map(|profile| Detail::new(detail::MAPPING_PROFILE, profile.clone())),
);
details.extend(
mapping
.files
.iter()
.map(|file| Detail::new(detail::MAPPING_FILE, file.clone())),
);
details.extend(
mapping
.package
.iter()
.map(|package| Detail::new(detail::MAPPING_PACKAGE, package.clone())),
);
details.extend(
transformation
.terminology
.iter()
.map(|version| Detail::new(detail::TERMINOLOGY_VERSION, version.clone())),
);
for (count, path, elements) in [
(
detail::TRANSCODED,
detail::TRANSCODED_PATH,
&transformation.transcoded,
),
(
detail::UNTRANSCODED,
detail::UNTRANSCODED_PATH,
&transformation.untranscoded,
),
(
detail::DROPPED,
detail::DROPPED_PATH,
&transformation.dropped,
),
] {
details.extend(counted((count, path), elements));
}
Entity::Described(Described {
what: None,
kind: OTHER,
role: None,
name: Some(TRANSFORMATION_ENTITY.to_owned()),
description: Some(TRANSFORMATION_DESCRIPTION.to_owned()),
details,
security_labels: Vec::new(),
})
}
fn counted((count, path): (&str, &str), elements: &Elements) -> Vec<Detail> {
let mut details = vec![Detail::new(count, elements.count().to_string())];
details.extend(
elements
.paths()
.iter()
.map(|(at, held)| Detail::new(path, format!("{at}={held}"))),
);
details
}