(fileContent, prefix=tokenPrefix, map=[])
| 17 | } |
| 18 | |
| 19 | function parseTokens(fileContent, prefix=tokenPrefix, map=[]) { |
| 20 | let baseKey, baseValue, keyValue, keys, modify, ns; |
| 21 | |
| 22 | Object.entries(fileContent).forEach(([key, value]) => { |
| 23 | key = key.replace(/\?/g, ''); |
| 24 | key = key.replace(/&/g, '-'); // some token names contain & chars |
| 25 | ns = prefix === tokenPrefix ? (tokenPrefix + key) : key === 'value' ? prefix : `${prefix}-${key}`; |
| 26 | |
| 27 | if (typeof value === 'object') { |
| 28 | keys = Object.keys(value); |
| 29 | modify = value[keys[0]]?.$extensions?.['studio.tokens']?.modify || // the first key could contain the value, |
| 30 | value[keys[1]]?.$extensions?.['studio.tokens']?.modify; // so we are checking the 2nd too |
| 31 | |
| 32 | if (modify) { |
| 33 | // assuming that each object contains its base value |
| 34 | keys.forEach(objKey => { |
| 35 | if (!value[objKey].$extensions) { |
| 36 | baseKey = objKey; |
| 37 | baseValue = value[baseKey].value; |
| 38 | } |
| 39 | }); |
| 40 | |
| 41 | keys.forEach(objKey => { |
| 42 | if (objKey !== baseKey) { |
| 43 | modify = value[objKey].$extensions?.['studio.tokens']?.modify; |
| 44 | keyValue = `#{${modify.type}(${baseValue}, ${modify.value * 100}%)}`; |
| 45 | |
| 46 | map.push([`${ns}-${objKey}`, keyValue]); |
| 47 | } else { |
| 48 | parseTokens(value[baseKey], `${ns}-${baseKey}`, map); |
| 49 | } |
| 50 | }) |
| 51 | } else { |
| 52 | parseTokens(value, ns, map); |
| 53 | } |
| 54 | } else if (key !== 'description' && key !== 'type') { |
| 55 | if (typeof value === 'string') { |
| 56 | if (!value.includes('{')) { |
| 57 | if (value.includes(' ')) { |
| 58 | value = `'${value}'`; |
| 59 | } |
| 60 | } else { |
| 61 | value = value.replace(/\?/g, ''); |
| 62 | matches = value.matchAll(tokenRegex); |
| 63 | |
| 64 | // replace . with - only inside each token |
| 65 | for (match of matches) { |
| 66 | value = value.replace(match[0], match[0].replace(/\./g, '-')); |
| 67 | } |
| 68 | |
| 69 | /* |
| 70 | * some design tokens contain operations without empty spaces |
| 71 | * e.g. {token}*0.9 |
| 72 | * calc() relies on having spaces around operators |
| 73 | */ |
| 74 | value = value.replace(/(\S)(\*)(\S)/g, '$1 $2 $3'); |
| 75 | value = value.replace(/(\S)(\/)(\S)/g, '$1 $2 $3'); |
| 76 |
no test coverage detected