datagen_rs/schema/
transform.rs

1use crate::schema::reference::Reference;
2use crate::transform::filter::FilterTransform;
3use crate::transform::plugin_transform::PluginTransform;
4use crate::transform::regex_filter::RegexFilter;
5use crate::transform::sort::SortTransform;
6use crate::transform::string_case_transform::ToLowerCase;
7use crate::transform::string_case_transform::ToUpperCase;
8use crate::transform::to_string::ToStringTransform;
9#[cfg(feature = "schema")]
10use schemars::JsonSchema;
11#[cfg(feature = "serialize")]
12use serde::{Deserialize, Serialize};
13
14#[derive(Debug, Clone)]
15#[cfg_attr(feature = "schema", derive(JsonSchema))]
16#[cfg_attr(feature = "serialize", derive(Serialize, Deserialize))]
17#[cfg_attr(
18    feature = "serialize",
19    serde(tag = "type", rename_all = "camelCase", deny_unknown_fields)
20)]
21pub enum Transform {
22    Filter(FilterTransform),
23    RegexFilter(RegexFilter),
24    /// Remove all null values from the array or object.
25    /// This can only be used on arrays and objects.
26    FilterNonNull,
27    ToString(ToStringTransform),
28    ToUpperCase(ToUpperCase),
29    ToLowerCase(ToLowerCase),
30    Sort(SortTransform),
31    Plugin(PluginTransform),
32}
33
34#[derive(Debug, Clone)]
35#[cfg_attr(feature = "schema", derive(JsonSchema))]
36#[cfg_attr(feature = "serialize", derive(Serialize, Deserialize))]
37#[cfg_attr(feature = "serialize", serde(untagged, deny_unknown_fields))]
38pub enum ReferenceOrString {
39    Reference(Box<Reference>),
40    String(String),
41}
42
43#[cfg(feature = "map-schema")]
44pub mod generate {
45    use crate::generate::current_schema::CurrentSchemaRef;
46    use crate::generate::generated_schema::generate::IntoGeneratedArc;
47    use crate::generate::generated_schema::GeneratedSchema;
48    use crate::schema::transform::{ReferenceOrString, Transform};
49    use crate::util::traits::generate::{ResolveRef, TransformTrait};
50    use crate::util::types::Result;
51    use indexmap::IndexMap;
52    use std::sync::Arc;
53
54    impl ResolveRef for ReferenceOrString {
55        fn resolve_ref(self, schema: &CurrentSchemaRef) -> Result<Arc<GeneratedSchema>> {
56            match self {
57                ReferenceOrString::Reference(reference) => {
58                    reference.into_generated_arc(schema.clone())
59                }
60                ReferenceOrString::String(string) => string.resolve_ref(schema),
61            }
62        }
63    }
64
65    impl TransformTrait for Transform {
66        fn transform(
67            self,
68            schema: CurrentSchemaRef,
69            value: Arc<GeneratedSchema>,
70        ) -> Result<Arc<GeneratedSchema>> {
71            match self {
72                Transform::Filter(filter) => filter.transform(schema, value),
73                Transform::FilterNonNull => match value.as_ref() {
74                    GeneratedSchema::Array(array) => {
75                        let array = array
76                            .iter()
77                            .filter(|item| item.as_ref() != &GeneratedSchema::None)
78                            .cloned()
79                            .collect::<Vec<_>>();
80                        Ok(GeneratedSchema::Array(array).into())
81                    }
82                    GeneratedSchema::Object(map) => {
83                        let map = map
84                            .iter()
85                            .filter(|(_, item)| item.as_ref() != &GeneratedSchema::None)
86                            .map(|(key, value)| (key.clone(), value.clone()))
87                            .collect::<IndexMap<_, _>>();
88                        Ok(GeneratedSchema::Object(map).into())
89                    }
90                    _ => Err("FilterNonNull can only be used on arrays and objects".into()),
91                },
92                Transform::ToString(to_string) => to_string.transform(schema, value),
93                Transform::ToLowerCase(to_lower_case) => to_lower_case.transform(schema, value),
94                Transform::ToUpperCase(to_upper_case) => to_upper_case.transform(schema, value),
95                Transform::RegexFilter(regex_filter) => regex_filter.transform(schema, value),
96                Transform::Sort(sort) => sort.transform(schema, value),
97                Transform::Plugin(plugin) => plugin.transform(schema, value),
98            }
99        }
100    }
101}