UNPKG

sb-mig

Version:

CLI to rule the world. (and handle stuff related to Storyblok CMS)

179 lines (178 loc) 7.11 kB
import { discoverResolvers, LOOKUP_TYPE, SCOPE, } from "../../cli/utils/discover.js"; import config from "../../config/config.js"; import { getFileContentWithRequire } from "../../utils/main.js"; export const transformWithResolverFiles = async (componentsContent) => { componentsContent = structuredClone(componentsContent); const resolversFilenames = await discoverResolvers({ scope: SCOPE.local, type: LOOKUP_TYPE.fileName, }); /* * if resolversFilenames exist, then do stuff if not, than follow with the old approach * */ if (resolversFilenames.length !== 0) { const resolverFilesContent = await Promise.all( // TODO: change to allSettled resolversFilenames.map((filename) => { return getFileContentWithRequire({ file: filename }); })); componentsContent = resolverTransformations(componentsContent, resolverFilesContent[0]); } return componentsContent; }; const isContentAvailableAsBloks = (component) => "content" in component.schema && component.schema.content.component_whitelist && component.schema.content.type === "bloks"; const isItemsAvailableAsBloks = (component) => "items" in component.schema && component.schema.items.component_whitelist && component.schema.items.type === "bloks"; const updateComponentWhitelist = ({ component, update, }) => { if (isContentAvailableAsBloks(component)) { component.schema.content.component_whitelist = [ ...new Set(update(component.schema.content.component_whitelist)), // make sure it will have unique items ]; } else if (isItemsAvailableAsBloks(component)) { component.schema.items.component_whitelist = [ ...new Set(update(component.schema.items.component_whitelist)), // make sure it will have unique items ]; } }; export const transformWithMainConfigFile = (componentsContent) => { componentsContent = structuredClone(componentsContent); if (config.resolvers && config.resolvers.length > 0) { config.resolvers.map((resolver) => { componentsContent = componentsContent.map((component) => { // If the component that we try to sync is in resolved component names list to resolve / transform if (resolver.match.includes(component.name)) { if (resolver.fields.component_whitelist) { updateComponentWhitelist({ component, update: resolver.fields.component_whitelist, }); } if (resolver.fields.translatable) { component.schema.icon.translatable = resolver.fields.translatable(component.schema.icon.translatable); } } return component; }); }); } if (config.advancedResolvers) { componentsContent = resolverTransformations(componentsContent, config.advancedResolvers); } return componentsContent; }; /** * side effect: true */ export const resolveGlobalTransformations = async (componentsContent) => { componentsContent = await transformWithResolverFiles(componentsContent); componentsContent = await transformWithMainConfigFile(componentsContent); return componentsContent; }; const extendField = (obj, targetField, newValue) => { if (typeof obj !== "object" || obj === null) { return false; } if (obj.hasOwnProperty(targetField)) { if (Array.isArray(obj[targetField])) { for (const element of newValue) { if (!obj[targetField].includes(element)) { obj[targetField] = [...obj[targetField], element]; } } } else if (typeof obj[targetField] === "object") { // this is something i have to fix, comparing to object is stupid obj[targetField] = { ...obj[targetField], ...newValue }; } return true; } for (const key in obj) { if (extendField(obj[key], targetField, newValue)) { return true; } } return false; }; const resolveAll = (resolver, componentsContent) => { if (!resolver.all) return componentsContent; return componentsContent; }; export const extendFields = (componentNamesResolver, component) => { const targetField = Object.keys(componentNamesResolver.methods.extend)[0]; console.log("This is target field ?"); console.log(targetField); extendField(component, targetField, componentNamesResolver.methods.extend[targetField]); }; function deepTransform(obj, transformers) { if (typeof obj !== "object" || obj === null) { return obj; } const result = Array.isArray(obj) ? [...obj] : { ...obj }; for (const key in transformers) { if (typeof transformers[key] === "function") { result[key] = transformers[key](obj[key]); } else if (typeof transformers[key] === "object" && transformers[key] !== null) { result[key] = deepTransform(obj[key] || {}, transformers[key]); } else { result[key] = transformers[key]; } } // Preserve untransformed properties for (const key in obj) { if (!(key in transformers)) { result[key] = obj[key]; } } return result; } export const resolverTransformations = (componentsContent, resolverFilesContent) => { let resolvedComponents = []; resolvedComponents = resolveComponentNames(resolverFilesContent, componentsContent); /** * * TODO: implement this * * */ // resolvedComponents = resolveComponentGroupNames( // resolver, // resolvedComponents, // ); // resolvedComponents = resolvePluginNames(resolver, resolvedComponents); return resolvedComponents; }; const resolveComponentNames = (resolver, componentsContent) => { if (!resolver.byComponentNames) return componentsContent; componentsContent = structuredClone(componentsContent); resolver.byComponentNames.map((componentNameResolver) => { componentsContent = componentsContent.map((component) => { // If the component that we try to sync is in resolved component names list to resolve / transform if (componentNameResolver && componentNameResolver.match.includes(component.name)) { const changedObj = deepTransform(component, componentNameResolver.componentData); component = changedObj; } return component; }); }); return componentsContent; }; const resolvePluginNames = (resolver, componentsContent) => { if (!resolver.componentPluginNames) return componentsContent; return componentsContent; }; const resolveComponentGroupNames = (resolver, componentsContent) => { if (!resolver.componentGroupNames) return componentsContent; return componentsContent; };