Skip to main content

stylex_transform/shared/utils/
object.rs

1use std::rc::Rc;
2
3use indexmap::IndexMap;
4
5use stylex_macros::stylex_panic;
6use swc_core::ecma::ast::{Expr, KeyValueProp};
7
8use crate::shared::enums::data_structures::flat_compiled_styles_value::FlatCompiledStylesValue;
9use crate::shared::enums::data_structures::obj_map_type::ObjMapType;
10use crate::shared::structures::pre_rule::PreRuleValue;
11use crate::shared::structures::state_manager::StateManager;
12use crate::shared::structures::types::FlatCompiledStyles;
13use crate::shared::utils::common::get_key_values_from_object;
14use crate::shared::utils::core::flat_map_expanded_shorthands::flat_map_expanded_shorthands;
15use stylex_structures::order_pair::OrderPair;
16use stylex_structures::pair::Pair;
17
18use super::ast::convertors::convert_key_value_to_str;
19
20pub(crate) fn obj_map<F>(
21  prop_values: ObjMapType,
22  state: &mut StateManager,
23  mapper: F,
24) -> FlatCompiledStyles
25where
26  F: Fn(Rc<FlatCompiledStylesValue>, &mut StateManager) -> Rc<FlatCompiledStylesValue>,
27{
28  let mut variables_map = IndexMap::new();
29
30  match prop_values {
31    ObjMapType::Object(obj) => {
32      let key_values = get_key_values_from_object(&obj);
33
34      for key_value in key_values.iter() {
35        let key = convert_key_value_to_str(key_value);
36
37        let value = Rc::new(FlatCompiledStylesValue::Tuple(
38          key.clone(),
39          key_value.value.clone(),
40          None,
41        ));
42
43        let result = mapper(value, state);
44
45        variables_map.insert(key, result);
46      }
47    },
48
49    ObjMapType::Map(map) => {
50      for (key, value) in map {
51        // Created hashed variable names with fileName//themeName//key
52        let result = mapper(value, state);
53
54        variables_map.insert(key, result);
55      }
56    },
57  }
58
59  variables_map
60}
61
62#[derive(Debug, Clone, Copy, PartialEq, Eq, PartialOrd, Ord, Hash)]
63pub(crate) struct Pipe<T> {
64  value: T,
65}
66
67impl<T> Pipe<T> {
68  pub fn new(value: T) -> Self {
69    Self { value }
70  }
71
72  pub fn pipe<U, F>(self, mapper: F) -> Pipe<U>
73  where
74    F: FnOnce(T) -> U,
75  {
76    Pipe::new(mapper(self.value))
77  }
78
79  pub fn done(self) -> T {
80    self.value
81  }
82
83  pub fn create(value: T) -> Self {
84    Self::new(value)
85  }
86}
87
88pub(crate) fn obj_entries(obj: &Expr) -> Vec<KeyValueProp> {
89  let object = match obj.as_object() {
90    Some(o) => o,
91    None => stylex_panic!("Object expected"),
92  };
93
94  get_key_values_from_object(object)
95}
96
97pub(crate) fn obj_from_entries(entries: &[OrderPair]) -> IndexMap<String, String> {
98  let mut map = IndexMap::with_capacity(entries.len());
99
100  for OrderPair(key, value) in entries {
101    map.insert(
102      key.clone(),
103      match value.as_ref() {
104        Some(v) => v.clone(),
105        None => stylex_panic!("Value is not a string"),
106      },
107    );
108  }
109
110  map
111}
112
113pub(crate) fn obj_map_keys_string(
114  entries: &IndexMap<String, String>,
115  mapper: fn(&str) -> String,
116) -> FlatCompiledStyles {
117  let mut map = IndexMap::with_capacity(entries.len());
118
119  for (key, value) in entries {
120    let mapped_key = mapper(key);
121
122    map.insert(
123      mapped_key.clone(),
124      Rc::new(FlatCompiledStylesValue::KeyValue(Pair::new(
125        mapped_key,
126        value.clone(),
127      ))),
128    );
129  }
130
131  map
132}
133
134pub(crate) fn obj_map_keys_key_value(
135  entries: &FlatCompiledStyles,
136  mapper: fn(&str) -> String,
137) -> FlatCompiledStyles {
138  let mut map = IndexMap::with_capacity(entries.len());
139
140  for (key, value) in entries {
141    let obejct_key = mapper(key);
142
143    let key_values = match value.as_key_values() {
144      Some(kv) => kv,
145      None => stylex_panic!("Value must be a key-value pairs"),
146    };
147
148    let object_key_values = key_values
149      .iter()
150      .map(|pair| Pair::new(pair.key.clone(), pair.value.clone()))
151      .collect::<Vec<Pair>>();
152
153    map.insert(
154      obejct_key.clone(),
155      Rc::new(FlatCompiledStylesValue::KeyValues(object_key_values)),
156    );
157  }
158
159  map
160}
161
162pub(crate) fn _obj_map_entries(
163  entries: &IndexMap<String, String>,
164  mapper: fn((&str, &str)) -> Pair,
165) -> IndexMap<String, FlatCompiledStylesValue> {
166  let mut map = IndexMap::with_capacity(entries.len());
167
168  for (key, value) in entries {
169    let result = mapper((key, value));
170    map.insert(key.clone(), FlatCompiledStylesValue::KeyValue(result));
171  }
172
173  map
174}
175
176pub(crate) fn preprocess_object_properties(
177  style: &Expr,
178  state: &mut StateManager,
179) -> IndexMap<String, String> {
180  let res: Vec<OrderPair> = obj_entries(&style.clone())
181    .iter()
182    .flat_map(|pair| {
183      let key = convert_key_value_to_str(pair);
184
185      flat_map_expanded_shorthands(
186        (key, PreRuleValue::Expr(*pair.value.clone())),
187        &state.options,
188      )
189      .into_iter()
190      .collect::<Vec<OrderPair>>()
191    })
192    .filter(|item| item.1.is_some())
193    .collect::<Vec<OrderPair>>();
194
195  obj_from_entries(&res)
196}