{"version":3,"names":["componentLangToMessageBundleCache","async","getMessageBundle","lang","component","key","fetch","getAssetPath","then","resp","ok","throwMessageFetchError","json","catch","Error","mergeMessages","messages","defaultMessages","messageOverrides","noop","setUpMessages","fetchMessages","effectiveLocale","isBrowser","el","tag","tagName","toLowerCase","componentName","replace","getSupportedLocale","updateMessages","connectMessages","onMessagesChange","defaultOnMessagesChange","disconnectMessages","this"],"sources":["src/utils/t9n.ts"],"sourcesContent":["import { getAssetPath } from \"@stencil/core\";\nimport { getSupportedLocale, LocalizedComponent } from \"./locale\";\nimport { isBrowser } from \"./browser\";\n\nexport type MessageBundle = Record;\n\nexport const componentLangToMessageBundleCache: Record> = {};\n\nasync function getMessageBundle(lang: string, component: string): Promise {\n const key = `${component}_${lang}`;\n\n if (componentLangToMessageBundleCache[key]) {\n return componentLangToMessageBundleCache[key];\n }\n\n componentLangToMessageBundleCache[key] = fetch(getAssetPath(`./assets/${component}/t9n/messages_${lang}.json`))\n .then((resp) => {\n if (!resp.ok) {\n throwMessageFetchError();\n }\n return resp.json();\n })\n .catch(() => throwMessageFetchError());\n\n return componentLangToMessageBundleCache[key];\n}\n\nfunction throwMessageFetchError(): never {\n throw new Error(\"could not fetch component message bundle\");\n}\n\nfunction mergeMessages(component: T9nComponent): void {\n component.messages = {\n ...component.defaultMessages,\n ...component.messageOverrides,\n };\n}\n\nfunction noop(): void {\n // intentionally empty\n}\n\n/**\n * This utility sets up the messages used by the component. It should be awaited in the `componentWillLoad` lifecycle hook.\n *\n * @param component\n */\nexport async function setUpMessages(component: T9nComponent): Promise {\n component.defaultMessages = await fetchMessages(component, component.effectiveLocale);\n mergeMessages(component);\n}\n\nasync function fetchMessages(component: T9nComponent, lang: string): Promise {\n if (!isBrowser()) {\n return {};\n }\n\n const { el } = component;\n const tag = el.tagName.toLowerCase();\n const componentName = tag.replace(\"calcite-\", \"\");\n\n return getMessageBundle(getSupportedLocale(lang, \"t9n\"), componentName);\n}\n\n/**\n * This utility must be set up for the component to update its default message bundle if the locale changes.\n *\n * It can be set up in **either** of the following ways:\n *\n * 1. called from `LocalizedComponent`'s `onLocaleChange` method or\n * 2. called from a watcher configured to watch `LocalizedComponent`'s `effectiveLocale` prop\n *\n * @param component\n * @param lang\n */\nexport async function updateMessages(component: T9nComponent, lang: string): Promise {\n component.defaultMessages = await fetchMessages(component, lang);\n mergeMessages(component);\n}\n\n/**\n * This utility sets up internals for messages support.\n *\n * It needs to be called in `connectedCallback`\n *\n * **Note**: this must be called after `LocalizedComponent`'s `connectLocalized` method.\n *\n * @param component\n */\nexport function connectMessages(component: T9nComponent): void {\n component.onMessagesChange = defaultOnMessagesChange;\n}\n\n/**\n * This utility tears down internals for messages support.\n *\n * It needs to be called in `disconnectedCallback`\n *\n * @param component\n */\nexport function disconnectMessages(component: T9nComponent): void {\n // we set this to noop to for watchers triggered when components are disconnected\n component.onMessagesChange = noop;\n}\n\n/**\n * This interface enables components to support built-in translation strings.\n *\n * **Notes**:\n *\n * This requires `LocalizedComponent` to be implemented.\n * To avoid unnecessary lookups, composite components should set `lang` on internal t9n components.\n */\nexport interface T9nComponent extends LocalizedComponent {\n el: HTMLElement;\n\n /**\n * This property holds all messages used by the component's rendering.\n *\n * This prop should use the `@Prop` decorator. It uses `@Prop` decorator for testing purpose only.\n */\n messages: MessageBundle;\n\n /**\n * This property holds the component's default messages.\n */\n defaultMessages: MessageBundle;\n\n /**\n * This property holds all user message overrides.\n *\n * This prop should use the `@Prop` decorator.\n */\n messageOverrides: Partial;\n\n /**\n * This private method ensures messages are kept in sync.\n *\n * This method should be empty and configured to watch for changes on `messageOverrides` property.\n *\n * @Watch(\"messageOverrides\")\n * onMessagesChange(): void {\n * \\/* wired up by t9n util *\\/\n * }\n */\n onMessagesChange: () => void;\n}\n\nfunction defaultOnMessagesChange(this: T9nComponent): void {\n mergeMessages(this);\n}\n"],"mappings":";;;;;4GAMO,MAAMA,EAA4E,GAEzFC,eAAeC,EAAiBC,EAAcC,GAC5C,MAAMC,EAAM,GAAGD,KAAaD,IAE5B,GAAIH,EAAkCK,GAAM,CAC1C,OAAOL,EAAkCK,E,CAG3CL,EAAkCK,GAAOC,MAAMC,EAAa,YAAYH,kBAA0BD,WAC/FK,MAAMC,IACL,IAAKA,EAAKC,GAAI,CACZC,G,CAEF,OAAOF,EAAKG,MAAM,IAEnBC,OAAM,IAAMF,MAEf,OAAOX,EAAkCK,EAC3C,CAEA,SAASM,IACP,MAAM,IAAIG,MAAM,2CAClB,CAEA,SAASC,EAAcX,GACrBA,EAAUY,SAAW,IAChBZ,EAAUa,mBACVb,EAAUc,iBAEjB,CAEA,SAASC,IAET,CAOOlB,eAAemB,EAAchB,GAClCA,EAAUa,sBAAwBI,EAAcjB,EAAWA,EAAUkB,iBACrEP,EAAcX,EAChB,CAEAH,eAAeoB,EAAcjB,EAAyBD,GACpD,IAAKoB,IAAa,CAChB,MAAO,E,CAGT,MAAMC,GAAEA,GAAOpB,EACf,MAAMqB,EAAMD,EAAGE,QAAQC,cACvB,MAAMC,EAAgBH,EAAII,QAAQ,WAAY,IAE9C,OAAO3B,EAAiB4B,EAAmB3B,EAAM,OAAQyB,EAC3D,CAaO3B,eAAe8B,EAAe3B,EAAyBD,GAC5DC,EAAUa,sBAAwBI,EAAcjB,EAAWD,GAC3DY,EAAcX,EAChB,C,SAWgB4B,EAAgB5B,GAC9BA,EAAU6B,iBAAmBC,CAC/B,C,SASgBC,EAAmB/B,GAEjCA,EAAU6B,iBAAmBd,CAC/B,CA6CA,SAASe,IACPnB,EAAcqB,KAChB,Q","ignoreList":[]}