From fb3794ee89d92076b4ed3e4c7aa92069aa4d957d Mon Sep 17 00:00:00 2001 From: Aymeric PINEAU Date: Thu, 20 Jun 2024 19:56:23 -0600 Subject: [PATCH] fix(intlayer-core): fix array intlayer --- apps/website/src/Routes.ts | 13 ++ apps/website/src/app/[locale]/doc/metadata.ts | 50 +++++ apps/website/src/app/[locale]/doc/page.tsx | 16 ++ .../src/components/DocPage/DocPageLayout.tsx | 89 +++++++++ .../components/DocPage/doc-page.content.ts | 123 ++++++++++++ apps/website/src/components/DocPage/index.tsx | 5 + .../src/components/Navbar/navbar.content.ts | 38 ++-- packages/@intlayer/chokidar/package.json | 1 + .../chokidar/src/chokidar/watcher.ts | 16 +- .../dictionary_to_type/createType.ts | 178 ++++++------------ .../core/src/types/declarationContent.ts | 6 +- .../src/components/Container/index.tsx | 5 +- .../src/components/Navbar/DesktopNavbar.tsx | 2 +- packages/react-intlayer/src/index.ts | 1 - .../react-intlayer/src/useIntlayerBase.ts | 55 ++---- pnpm-lock.yaml | 140 ++++++++++++-- 16 files changed, 541 insertions(+), 197 deletions(-) create mode 100644 apps/website/src/app/[locale]/doc/metadata.ts create mode 100644 apps/website/src/app/[locale]/doc/page.tsx create mode 100644 apps/website/src/components/DocPage/DocPageLayout.tsx create mode 100644 apps/website/src/components/DocPage/doc-page.content.ts create mode 100644 apps/website/src/components/DocPage/index.tsx diff --git a/apps/website/src/Routes.ts b/apps/website/src/Routes.ts index 58d7d16fa..82b8e29d4 100644 --- a/apps/website/src/Routes.ts +++ b/apps/website/src/Routes.ts @@ -1,6 +1,19 @@ export enum PagesRoutes { Home = '/', Demo = '/demo', + Doc = '/doc', + Doc_GetStarted = '/doc/get_started', + Doc_Configuration = '/doc/configuration', + Doc_Interest = '/doc/interest-of-intlayer', + Doc_IntlayerEditor = '/doc/intlayer-editor', + Doc_ContentDeclaration = '/doc/content-declaration', + Doc_ContentDeclaration_Translation = '/doc/content-declaration/translation', + Doc_ContentDeclaration_Enumeration = '/doc/content-declaration/enumeration', + Doc_ContentDeclaration_FunctionFetching = '/doc/content-declaration/function-fetching', + Doc_ContentDeclaration_NestedId = '/doc/content-declaration/nested-id', + Doc_Environment_NextJS = '/doc/environment/intlayer-with-nextjs', + Doc_Environment_CRA = '/doc/environment/intlayer-with-create-react-app', + Doc_Environment_ViteAndReact = '/doc/environment/intlayer-with-vite-and-react', LogIn = '/auth/sign-in', SignUp = '/auth/sign-up', diff --git a/apps/website/src/app/[locale]/doc/metadata.ts b/apps/website/src/app/[locale]/doc/metadata.ts new file mode 100644 index 000000000..332ca6116 --- /dev/null +++ b/apps/website/src/app/[locale]/doc/metadata.ts @@ -0,0 +1,50 @@ +import { type IConfigLocales, getTranslationContent } from 'intlayer'; +import type { Metadata } from 'next'; +import type { LocalParams } from 'next-intlayer'; + +export const generateMetadata = ({ + params: { locale }, +}: LocalParams): Metadata => { + const t = (content: IConfigLocales) => + getTranslationContent(content, locale); + + return { + title: t({ + en: 'Intlayer | Documentation', + fr: 'Intlayer | Documentation', + es: 'Intlayer | Documentación', + }), + description: t({ + en: 'Transform your website into a multilingual application in 2 minutes. Discover the full range of Intlayer features through this online documentation.', + fr: "Transformez votre site web en application multilingue en 2 minutes. Découvrez l'ensemble des fonctionnalités de Intlayer à travers cette documentation en ligne.", + es: 'Transforme su sitio web en una aplicación multilingüe en 2 minutos. Descubra todas las funcionalidades de Intlayer a través de esta documentación en línea.', + }), + generator: undefined, + keywords: t({ + en: [ + 'Documentation', + 'Internationalization', + 'Intlayer', + 'Next.js', + 'JavaScript', + 'React', + ], + fr: [ + 'Documentation', + 'Internationalisation', + 'Intlayer', + 'Next.js', + 'JavaScript', + 'React', + ], + es: [ + 'Documentation', + 'Internacionalización', + 'Intlayer', + 'Next.js', + 'JavaScript', + 'React', + ], + }), + }; +}; diff --git a/apps/website/src/app/[locale]/doc/page.tsx b/apps/website/src/app/[locale]/doc/page.tsx new file mode 100644 index 000000000..fb596b402 --- /dev/null +++ b/apps/website/src/app/[locale]/doc/page.tsx @@ -0,0 +1,16 @@ +import { DocPage } from '@components/DocPage'; +import { DocPageLayout } from '@components/DocPage/DocPageLayout'; +import { PageLayout } from '@layouts/PageLayout'; +import type { NextPageIntlayer } from 'next-intlayer'; +import { generateMetadata } from './metadata'; + +export { generateMetadata }; + +const Page: NextPageIntlayer = ({ params: { locale } }) => ( + + + + + +); +export default Page; diff --git a/apps/website/src/components/DocPage/DocPageLayout.tsx b/apps/website/src/components/DocPage/DocPageLayout.tsx new file mode 100644 index 000000000..5f48005cc --- /dev/null +++ b/apps/website/src/components/DocPage/DocPageLayout.tsx @@ -0,0 +1,89 @@ +'use client'; + +import { Container } from '@intlayer/design-system'; +import { cn } from '@utils/cn'; +import { usePathname, useRouter } from 'next/navigation'; +import { useIntlayer } from 'next-intlayer'; +import type { FC, ReactNode } from 'react'; + +type DocPageLayoutProps = { + children?: ReactNode; +}; + +export const DocPageLayout: FC = ({ children }) => { + const { navbar } = useIntlayer('doc-page'); + const pathname = usePathname(); + const router = useRouter(); + + return ( +
+ + + +
{children}
+
+ ); +}; diff --git a/apps/website/src/components/DocPage/doc-page.content.ts b/apps/website/src/components/DocPage/doc-page.content.ts new file mode 100644 index 000000000..bed59d125 --- /dev/null +++ b/apps/website/src/components/DocPage/doc-page.content.ts @@ -0,0 +1,123 @@ +import { type DeclarationContent, t } from 'intlayer'; +import { PagesRoutes } from '@/Routes'; + +type NavLink = { + title: string; + subSections?: NavLink[]; + url?: string; +}; + +type NavbarContent = { + navbar: NavLink[]; +}; + +export const navbarContent: DeclarationContent = { + id: 'doc-page', + navbar: [ + { + title: t({ fr: 'Commencez', en: 'Get started', es: 'Comenzar' }), + url: PagesRoutes.Doc_GetStarted, + subSections: [], + }, + { + title: t({ fr: 'Concept', en: 'Concept', es: 'Concepto' }), + subSections: [ + { + title: t({ + fr: 'Configuration', + en: 'Configuration', + es: 'Configuración', + }), + url: PagesRoutes.Doc_Configuration, + }, + { + title: t({ + fr: 'Intérêt de intlayer', + en: 'Interest of intlayer', + es: 'Interés de intlayer', + }), + url: PagesRoutes.Doc_Interest, + }, + { + title: t({ + fr: 'Éditeur Intlayer', + en: 'Intlayer editor', + es: 'Editor de Intlayer', + }), + url: PagesRoutes.Doc_IntlayerEditor, + }, + { + title: t({ + fr: 'Déclaration de contenu', + en: 'Content declaration', + es: 'Declaración de contenido', + }), + url: PagesRoutes.Doc_ContentDeclaration, + subSections: [ + { + title: t({ + fr: 'Traduction', + en: 'Translation', + es: 'Traducción', + }), + url: PagesRoutes.Doc_ContentDeclaration_Translation, + }, + { + title: t({ + fr: 'Énumération', + en: 'Enumeration', + es: 'Enumeración', + }), + url: PagesRoutes.Doc_ContentDeclaration_Enumeration, + }, + { + title: t({ + fr: 'Récupération de fonction', + en: 'Function fetching', + es: 'Obtención de función', + }), + url: PagesRoutes.Doc_ContentDeclaration_FunctionFetching, + }, + { + title: t({ + fr: 'ID imbriqué', + en: 'Nested ID', + es: 'ID anidado', + }), + url: PagesRoutes.Doc_ContentDeclaration_NestedId, + }, + ], + }, + ], + }, + { + title: t({ fr: 'Environnements', en: 'Environments', es: 'Entornos' }), + subSections: [ + { + title: t({ + fr: 'Intlayer avec NextJS', + en: 'Intlayer with NextJS', + es: 'Intlayer con NextJS', + }), + url: PagesRoutes.Doc_Environment_NextJS, + }, + { + title: t({ + fr: 'Intlayer avec React (CRA)', + en: 'Intlayer with React (CRA)', + es: 'Intlayer con React (CRA)', + }), + url: PagesRoutes.Doc_Environment_CRA, + }, + { + title: t({ + fr: 'Intlayer avec ViteJS+React', + en: 'Intlayer with ViteJS+React', + es: 'Intlayer con ViteJS+React', + }), + url: PagesRoutes.Doc_Environment_ViteAndReact, + }, + ], + }, + ], +}; diff --git a/apps/website/src/components/DocPage/index.tsx b/apps/website/src/components/DocPage/index.tsx new file mode 100644 index 000000000..c189053cb --- /dev/null +++ b/apps/website/src/components/DocPage/index.tsx @@ -0,0 +1,5 @@ +import type { FC } from 'react'; + +export const DocPage: FC = () => { + return <>; +}; diff --git a/apps/website/src/components/Navbar/navbar.content.ts b/apps/website/src/components/Navbar/navbar.content.ts index 21df187dc..3d4470434 100644 --- a/apps/website/src/components/Navbar/navbar.content.ts +++ b/apps/website/src/components/Navbar/navbar.content.ts @@ -1,24 +1,16 @@ +import type { NavSection } from '@intlayer/design-system'; import { type DeclarationContent, t } from 'intlayer'; import { PagesRoutes } from '@/Routes'; -// type SectionsContent = { -// sections: NavSection[]; -// bottomSections: NavSection[]; -// logo: { -// label: string; -// onClick: () => void; -// }; -// profile: { -// label: string; -// }; -// login: { -// text: string; -// label: string; -// onClick: () => void; -// }; -// }; +type SectionsContent = { + sections: Omit[]; + // bottomSections: Omit[]; + logo: { + label: string; + }; +}; -export const navbarContent: DeclarationContent = { +export const navbarContent: DeclarationContent = { id: 'navbar', logo: { label: t({ @@ -51,11 +43,21 @@ export const navbarContent: DeclarationContent = { }), url: PagesRoutes.Demo, label: t({ - en: 'Go to demo page', + en: 'Go to the demo page', fr: 'Aller à la page de démo', es: 'Ir a la página de demostración', }), }, + { + id: 'doc', + title: 'Doc', + url: PagesRoutes.Doc, + label: t({ + en: 'Go to the documentation page', + fr: 'Aller à la page de documentation', + es: 'Ir a la página de documentation', + }), + }, ], // bottomSections: { // logout: { diff --git a/packages/@intlayer/chokidar/package.json b/packages/@intlayer/chokidar/package.json index 8a6732bf9..6dc5fbdbf 100644 --- a/packages/@intlayer/chokidar/package.json +++ b/packages/@intlayer/chokidar/package.json @@ -61,6 +61,7 @@ "glob": "^10.3.12", "intlayer": "workspace:^", "node-loader": "^2.0.0", + "quicktype-core": "^23.0.170", "rimraf": "5.0.5" }, "devDependencies": { diff --git a/packages/@intlayer/chokidar/src/chokidar/watcher.ts b/packages/@intlayer/chokidar/src/chokidar/watcher.ts index a95be0116..6a5bdfac1 100644 --- a/packages/@intlayer/chokidar/src/chokidar/watcher.ts +++ b/packages/@intlayer/chokidar/src/chokidar/watcher.ts @@ -28,14 +28,17 @@ export const watch = (options?: WatchOptions) => { .on('ready', async () => { const dictionariesPaths = await buildDictionary(files); - console.info('Building Intlayer types...'); - createTypes(dictionariesPaths); + console.info('Building TypeScript types...'); + await createTypes(dictionariesPaths); + console.info('TypeScript types built'); console.info('Building Intlayer module augmentation...'); createModuleAugmentation(); + console.info('Intlayer module augmentation built'); console.info('Building Intlayer dictionary list...'); createDictionaryList(); + console.info('Intlayer dictionary list built'); const relativeDictionariesPath = dictionariesPaths.map((dictionary) => relative(baseDir, dictionary) @@ -53,10 +56,12 @@ export const watch = (options?: WatchOptions) => { const dictionaries = await buildDictionary(filePath); console.info('Building TypeScript types...'); - createTypes(dictionaries); + await createTypes(dictionaries); + console.info('TypeScript types built'); - console.info('Building type index...'); + console.info('Building Intlayer module augmentation...'); createModuleAugmentation(); + console.info('Intlayer module augmentation built'); console.info('Building main...'); createDictionaryList(); @@ -67,7 +72,8 @@ export const watch = (options?: WatchOptions) => { const dictionaries = await buildDictionary(filePath); console.info('Building TypeScript types...'); - createTypes(dictionaries); + await createTypes(dictionaries); + console.info('TypeScript types built'); }) .on('error', (error) => { console.error('Watcher error:', error); diff --git a/packages/@intlayer/chokidar/src/transpiler/dictionary_to_type/createType.ts b/packages/@intlayer/chokidar/src/transpiler/dictionary_to_type/createType.ts index 660778764..8b874ae63 100644 --- a/packages/@intlayer/chokidar/src/transpiler/dictionary_to_type/createType.ts +++ b/packages/@intlayer/chokidar/src/transpiler/dictionary_to_type/createType.ts @@ -2,13 +2,12 @@ import { existsSync, mkdirSync, writeFileSync } from 'fs'; import { createRequire } from 'module'; import { resolve } from 'path'; import { getConfiguration } from '@intlayer/config'; +import type { Dictionary } from '@intlayer/core'; import { - NodeType, - type Dictionary, - type DictionaryValue, - type TypedNode, -} from '@intlayer/core'; -import { getTypeName } from './createModuleAugmentation'; + quicktype, + InputData, + jsonInputForTargetLanguage, +} from 'quicktype-core'; const { content } = getConfiguration(); const { typesDir } = content; @@ -16,123 +15,60 @@ const { typesDir } = content; const isESModule = typeof import.meta.url === 'string'; const requireFunction = isESModule ? createRequire(import.meta.url) : require; -const getFirstValue = (obj: Record): DictionaryValue => - Object.values(obj)[0]; - -/** - * - * This function generates a TypeScript type definition from a JSON object - * - * Example: - * - * const input = { - * id: '1', - * name: 'John Doe', - * address: { - * id: '2', - * street: '123 Main St', - * city: 'Springfield', - * } - * }; - * - * const result = generateTypeScriptType(input, 'RootObject'); - * console.log(result); - * - * Output: - * - * type RootObject = { - * id: '1', - * name: string, - * address: { - * id: '2', - * street: string, - * city: string, - * }, - * }; - * - */ -export const generateTypeScriptType = (obj: Dictionary): string => { - let typeDefinition = ``; - - const typeName = getTypeName(obj.id); - - typeDefinition += `export type ${typeName} = `; - typeDefinition += generateTypeScriptTypeContent(obj as DictionaryValue); - typeDefinition += ';\n\n'; - - return typeDefinition; +const kebabCaseToCammelCase = (name: string): string => + name + .split(/[\s\-_]+/) // Regular expression to match space, hyphen, or underscore + .map((word, index) => { + if (index === 0) { + return word; // Return the first word as is + } + return word.charAt(0).toUpperCase() + word.slice(1); // Capitalize the first letter of subsequent words + }) + .join(''); // Join all the segments into one string + +export const generateTypeScriptType = async ( + typeName: string, + jsonString: string +) => { + const { lines } = await quicktypeJSON(typeName, jsonString); + + const linesString: string = lines.join('\n'); + + return linesString; }; -const isReactNode = (node: Record): boolean => - typeof node?.key !== 'undefined' && typeof node?.props !== 'undefined'; - -// eslint-disable-next-line sonarjs/cognitive-complexity -export const generateTypeScriptTypeContent = (obj: DictionaryValue): string => { - if (typeof obj !== 'object' || obj === null) { - return `${typeof obj}`; - } - - const isReactNodeValue = isReactNode(obj as Record); - - if (isReactNodeValue) { - // ReactNode handling - return `JSX.Element`; - } - - if ( - // Check if the value is a typed node - (obj as TypedNode).nodeType === NodeType.Translation - ) { - const { nodeType, ...content } = obj as TypedNode; - - const languageValue: DictionaryValue = getFirstValue( - content as Record - ); - - const tsType = generateTypeScriptTypeContent(languageValue); - return `${tsType}`; - } else if ( - // Check if the value is a typed node - (obj as TypedNode).nodeType === NodeType.Enumeration - ) { - const { nodeType, ...content } = obj as TypedNode; - - const quantifiedValue: DictionaryValue = getFirstValue( - content as Record - ); - - const tsType = generateTypeScriptTypeContent(quantifiedValue); - - return `(quantity: number) => ${tsType}`; - } else if (Array.isArray(obj)) { - // Array handling (simplified, assumes non-empty arrays with uniform type) - const arrayType = generateTypeScriptTypeContent(obj[0] as DictionaryValue); - - return `${arrayType}[]`; - } - - let typeDefinition = '{'; - // Nested object, recurse - for (const [key, value] of Object.entries(obj)) { - const isLast = - Object.keys(obj).indexOf(key) === Object.keys(obj).length - 1; - - const nestedType = generateTypeScriptTypeContent(value as DictionaryValue); - - typeDefinition += `'${key}': ${nestedType}`; - - if (!isLast) { - typeDefinition += ','; - } - } - typeDefinition += '}'; - return typeDefinition; +const quicktypeJSON = async (typeName: string, jsonString: string) => { + const jsonInput = jsonInputForTargetLanguage('typescript'); + + // We could add multiple samples for the same desired + // type, or many sources for other types. Here we're + // just making one type from one piece of sample JSON. + await jsonInput.addSource({ + name: typeName, + samples: [jsonString], + }); + + const inputData = new InputData(); + inputData.addInput(jsonInput); + + return await quicktype({ + inputData, + lang: 'typescript', + alphabetizeProperties: true, + rendererOptions: { + 'just-types': 'true', + 'explicit-unions': 'true', + 'acronym-style': 'camel', + }, + }); }; /** * This function generates a TypeScript type definition from a JSON object */ -export const createTypes = (dictionariesPaths: string[]): string[] => { +export const createTypes = async ( + dictionariesPaths: string[] +): Promise => { const resultTypesPaths: string[] = []; // Create type folders if they don't exist @@ -143,7 +79,15 @@ export const createTypes = (dictionariesPaths: string[]): string[] => { for (const dictionaryPath of dictionariesPaths) { const dictionary: Dictionary = requireFunction(dictionaryPath); const dictionaryName: string = dictionary.id; - const typeDefinition: string = generateTypeScriptType(dictionary); + const dictionaryNameCamelCase: string = + kebabCaseToCammelCase(dictionaryName) + 'Content'; + + const dictionaryContentString: string = JSON.stringify(dictionary); + + const typeDefinition: string = await generateTypeScriptType( + dictionaryNameCamelCase, + dictionaryContentString + ); const outputPath: string = resolve(typesDir, `${dictionaryName}.d.ts`); diff --git a/packages/@intlayer/core/src/types/declarationContent.ts b/packages/@intlayer/core/src/types/declarationContent.ts index 2785d6773..322bef181 100644 --- a/packages/@intlayer/core/src/types/declarationContent.ts +++ b/packages/@intlayer/core/src/types/declarationContent.ts @@ -45,9 +45,13 @@ type ReplaceContentValue = { ? ContentValue : T[P] extends object ? ReplaceContentValue - : T[P]; + : ReplaceContentValueArray; }; +type ReplaceContentValueArray = T extends (infer U)[] + ? ReplaceContentValue[] + : ReplaceContentValue; + export type DeclarationContent = (T extends undefined // Applying the generic to replace ContentValue with Replacement ? Content : ReplaceContentValue) & { diff --git a/packages/@intlayer/design-system/src/components/Container/index.tsx b/packages/@intlayer/design-system/src/components/Container/index.tsx index cef109ebb..e93bd967f 100644 --- a/packages/@intlayer/design-system/src/components/Container/index.tsx +++ b/packages/@intlayer/design-system/src/components/Container/index.tsx @@ -1,4 +1,4 @@ -import { type PropsWithChildren, forwardRef } from 'react'; +import { type PropsWithChildren, forwardRef, type HTMLAttributes } from 'react'; import { css, styled } from 'styled-components'; import tw, { type TwStyle } from 'twin.macro'; @@ -82,7 +82,8 @@ type ContainerProps = PropsWithChildren<{ transparency?: Transparency; padding?: Padding; separator?: Separator; -}>; +}> & + HTMLAttributes; // Container component export const Container = forwardRef( diff --git a/packages/@intlayer/design-system/src/components/Navbar/DesktopNavbar.tsx b/packages/@intlayer/design-system/src/components/Navbar/DesktopNavbar.tsx index 1bd23cbcc..b7bb7a80f 100644 --- a/packages/@intlayer/design-system/src/components/Navbar/DesktopNavbar.tsx +++ b/packages/@intlayer/design-system/src/components/Navbar/DesktopNavbar.tsx @@ -24,7 +24,7 @@ const StyledNav = styled.nav(() => [ var(--tw-backdrop-saturate) var(--tw-backdrop-sepia); `, ]); -const StyledList = tw.div`ml-[10vw] flex flex-row gap-6 tracking-wide text-neutral-800`; +const StyledList = tw.div`ml-[10vw] flex flex-row gap-6 tracking-wide text-neutral dark:text-neutral-dark`; const StyledRightItemContainer = tw.div`mr-4 flex w-full justify-end items-center gap-2`; diff --git a/packages/react-intlayer/src/index.ts b/packages/react-intlayer/src/index.ts index dc0e4f8f6..f1cb32139 100644 --- a/packages/react-intlayer/src/index.ts +++ b/packages/react-intlayer/src/index.ts @@ -12,4 +12,3 @@ export { getBrowserLocale, useLocaleBase, } from './client/index'; -export { recursiveStringifyContent } from './useIntlayerBase'; diff --git a/packages/react-intlayer/src/useIntlayerBase.ts b/packages/react-intlayer/src/useIntlayerBase.ts index 588c5f773..ca6181ca8 100644 --- a/packages/react-intlayer/src/useIntlayerBase.ts +++ b/packages/react-intlayer/src/useIntlayerBase.ts @@ -34,15 +34,21 @@ export type DictionaryKeys = StringFallback< keyof IntlayerDictionaryTypesConnector >; -export type IntlayerNode = ReactNode & { - value: string; +export type IntlayerNode = ReactNode & { + value: T; }; -type DeepTransformContent = T extends object - ? { - [K in keyof T]: DeepTransformContent; - } - : IntlayerNode; +type DeepTransformContent = T extends object // Check if the property is an object + ? T extends (infer U)[] // If it's an array, infer the type of array elements + ? DeepTransformContent[] // Apply DeepTransformContent recursively to each element of the array + : T extends { nodeType: string } + ? IntlayerNode // Apply DeepTransformContent recursively to properties of the object + : { + [K in keyof T]: DeepTransformContent; + } + : T extends undefined + ? never + : IntlayerNode; /** * Excludes the 'id' and 'filePath' keys from the dictionary content, @@ -84,39 +90,6 @@ export const recursiveTransformContent = (value: any): object => { return value.value; }; -type DeepStrinfifyContent = - T extends React.ComponentType - ? string - : T extends object - ? { - [K in keyof T]: DeepStrinfifyContent; - } - : T; - -export const recursiveStringifyContent = ( - obj: T -): DeepStrinfifyContent => - Object.entries(obj).reduce((acc, [key, value]) => { - if (typeof value === 'object' && typeof value.value !== 'undefined') { - return { - ...acc, - [key]: value.value, - }; - } else if (typeof value === 'object' && Array.isArray(value)) { - return { - ...acc, - [key]: value.map(recursiveStringifyContent), - }; - } else if (typeof value === 'object') { - return { - ...acc, - [key]: recursiveStringifyContent(value), - }; - } - - return acc; - }, {}) as DeepStrinfifyContent; - /** * Type definition for the useIntlayer hook, which takes a dictionary ID and an optional locale, * and returns the deeply transformed dictionary content. @@ -135,7 +108,7 @@ export const useIntlayerBase: UseIntlayer = ( id: T, locale?: Locales ) => { - const dictionary: Dictionary = dictionaries[id]; + const dictionary: Dictionary = dictionaries[id as keyof typeof dictionaries]; const result = processDictionary( dictionary, diff --git a/pnpm-lock.yaml b/pnpm-lock.yaml index a598635ec..c8a06e84e 100644 --- a/pnpm-lock.yaml +++ b/pnpm-lock.yaml @@ -372,6 +372,9 @@ importers: node-loader: specifier: ^2.0.0 version: 2.0.0(webpack@5.91.0) + quicktype-core: + specifier: ^23.0.170 + version: 23.0.170 rimraf: specifier: 5.0.5 version: 5.0.5 @@ -4473,6 +4476,13 @@ packages: tslib: 2.6.2 dev: false + /@glideapps/ts-necessities@2.2.3: + resolution: + { + integrity: sha512-gXi0awOZLHk3TbW55GZLCPP6O+y/b5X1pBXKBVckFONSwF1z1E5ND2BGJsghQFah+pW7pkkyFb2VhUQI2qhL5w==, + } + dev: false + /@humanwhocodes/config-array@0.11.14: resolution: { @@ -8602,7 +8612,6 @@ packages: engines: { node: '>=6.5' } dependencies: event-target-shim: 5.0.1 - dev: true /accepts@1.3.8: resolution: @@ -9413,7 +9422,6 @@ packages: { integrity: sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==, } - dev: true /batch@0.6.1: resolution: @@ -9606,6 +9614,13 @@ packages: } dev: true + /browser-or-node@3.0.0: + resolution: + { + integrity: sha512-iczIdVJzGEYhP5DqQxYM9Hh7Ztpqqi+CXZpSmX8ALFs9ecXkQIeqRyM6TfxEfMVpwhl3dSuDvxdzzo9sUOIVBQ==, + } + dev: false + /browser-process-hrtime@1.0.0: resolution: { @@ -9748,7 +9763,6 @@ packages: dependencies: base64-js: 1.5.1 ieee754: 1.2.1 - dev: true /builtin-modules@3.3.0: resolution: @@ -10362,6 +10376,13 @@ packages: } dev: false + /collection-utils@1.0.1: + resolution: + { + integrity: sha512-LA2YTIlR7biSpXkKYwwuzGjwL5rjWEZVOSnvdUc7gObvWe4WkjxOpfrdhoP7Hs09YWDVfg0Mal9BpAqLfVEzQg==, + } + dev: false + /color-convert@1.9.3: resolution: { @@ -10958,6 +10979,17 @@ packages: - encoding dev: true + /cross-fetch@4.0.0: + resolution: + { + integrity: sha512-e4a5N8lVvuLgAWgnCrLr2PP0YyDOTHa9H/Rj54dirp61qXnNq46m82bRhNqIA5VccJtWBvPTFRV3TtvHUKPB1g==, + } + dependencies: + node-fetch: 2.7.0 + transitivePeerDependencies: + - encoding + dev: false + /cross-spawn@5.1.0: resolution: { @@ -13897,7 +13929,6 @@ packages: integrity: sha512-i/2XbnSz/uxRCU6+NdVJgKWDTM427+MqYbkQzD321DuCQJUqOuJKIA0IM2+W2xtYHdKOmZ4dR6fExsd4SXL+WQ==, } engines: { node: '>=6' } - dev: true /eventemitter3@4.0.7: resolution: @@ -16422,6 +16453,13 @@ packages: engines: { node: '>=10' } dev: true + /is-url@1.2.4: + resolution: + { + integrity: sha512-ITvGim8FhRiYe4IQ5uHSkj7pVaPDrCTkNd3yq3cV7iZAcJdHTUMPMEHcqSOy9xZ9qFenQCvi+2wjH9a1nXqHww==, + } + dev: false + /is-weakmap@2.0.2: resolution: { @@ -17294,6 +17332,13 @@ packages: } engines: { node: '>=10' } + /js-base64@3.7.7: + resolution: + { + integrity: sha512-7rCnleh0z2CkXhH67J8K1Ytz0b2Y+yxTPL+/KOJoa20hfnVQ/3/T6W/KflYI4bRHRagNeXeU2bkNGI3v1oS/lw==, + } + dev: false + /js-beautify@1.15.1: resolution: { @@ -19581,7 +19626,6 @@ packages: optional: true dependencies: whatwg-url: 5.0.0 - dev: true /node-forge@1.3.1: resolution: @@ -20234,12 +20278,18 @@ packages: } engines: { node: '>=6' } + /pako@0.2.9: + resolution: + { + integrity: sha512-NUcwaKxUxWrZLpDG+z/xZaCgQITkA/Dv4V/T6bw7VON6l1Xz/VnrBqrYjZQ12TamKHzITTfOEIYUj48y2KXImA==, + } + dev: false + /pako@1.0.11: resolution: { integrity: sha512-4hLB8Py4zZce5s4yd9XzopqwVv/yGNhV1Bl8NTmCq1763HeK2+EwVTv+leGeL13Dnh2wfbqowVPXCIO0z4taYw==, } - dev: true /param-case@3.0.4: resolution: @@ -20635,6 +20685,14 @@ packages: find-up: 3.0.0 dev: false + /pluralize@8.0.0: + resolution: + { + integrity: sha512-Nc3IT5yHzflTfbjgqWcCPpo7DaKy4FnpB0l/zCAW0Tc7jxAiuqSxHasntB3D7887LSrA93kDJ9IXovxJYxyLCA==, + } + engines: { node: '>=4' } + dev: false + /possible-typed-array-names@1.0.0: resolution: { @@ -21954,7 +22012,6 @@ packages: integrity: sha512-cdGef/drWFoydD1JsMzuFf8100nZl+GT+yacc2bEced5f9Rjk4z+WtFUTBu9PhOi9j/jfmBPu0mMEY4wIdAF8A==, } engines: { node: '>= 0.6.0' } - dev: true /progress@2.0.3: resolution: @@ -22201,6 +22258,30 @@ packages: engines: { node: '>=10' } dev: false + /quicktype-core@23.0.170: + resolution: + { + integrity: sha512-ZsjveG0yJUIijUx4yQshzyQ5EAXKbFSBTQJHnJ+KoSZVxcS+m3GcmDpzrdUIRYMhgLaF11ZGvLSYi5U0xcwemw==, + } + dependencies: + '@glideapps/ts-necessities': 2.2.3 + browser-or-node: 3.0.0 + collection-utils: 1.0.1 + cross-fetch: 4.0.0 + is-url: 1.2.4 + js-base64: 3.7.7 + lodash: 4.17.21 + pako: 1.0.11 + pluralize: 8.0.0 + readable-stream: 4.5.2 + unicode-properties: 1.4.1 + urijs: 1.19.11 + wordwrap: 1.0.0 + yaml: 2.4.2 + transitivePeerDependencies: + - encoding + dev: false + /raf@3.4.1: resolution: { @@ -22633,7 +22714,6 @@ packages: events: 3.3.0 process: 0.11.10 string_decoder: 1.3.0 - dev: true /readable-web-to-node-stream@3.0.2: resolution: @@ -25077,6 +25157,13 @@ packages: setimmediate: 1.0.5 dev: true + /tiny-inflate@1.0.3: + resolution: + { + integrity: sha512-pkY1fj1cKHb2seWDy0B16HeWyczlJA9/WW3u3c4z/NiWDsO3DOU5D7nhTLE9CF0yXv/QZFY7sEJmj24dK+Rrqw==, + } + dev: false + /tinybench@2.8.0: resolution: { @@ -25177,7 +25264,6 @@ packages: { integrity: sha512-N3WMsuqV66lT30CrXNbEjx4GEwlow3v6rr4mCcv6prnfwhS01rkgyFdjPNBYd9br7LpXV1+Emh01fHnq2Gdgrw==, } - dev: true /tr46@1.0.1: resolution: @@ -25859,6 +25945,16 @@ packages: } engines: { node: '>=4' } + /unicode-properties@1.4.1: + resolution: + { + integrity: sha512-CLjCCLQ6UuMxWnbIylkisbRj31qxHPAurvena/0iwSVbQ2G1VY5/HjV0IRabOEbDHlzZlRdCrD4NhB0JtU40Pg==, + } + dependencies: + base64-js: 1.5.1 + unicode-trie: 2.0.0 + dev: false + /unicode-property-aliases-ecmascript@2.1.0: resolution: { @@ -25866,6 +25962,16 @@ packages: } engines: { node: '>=4' } + /unicode-trie@2.0.0: + resolution: + { + integrity: sha512-x7bc76x0bm4prf1VLg79uhAzKw8DVboClSN5VxJuQ+LKDOVEW9CdH+VY7SP+vX7xCYQqzzgQpFqz15zeLvAtZQ==, + } + dependencies: + pako: 0.2.9 + tiny-inflate: 1.0.3 + dev: false + /unicorn-magic@0.1.0: resolution: { @@ -26096,6 +26202,13 @@ packages: dependencies: punycode: 2.3.1 + /urijs@1.19.11: + resolution: + { + integrity: sha512-HXgFDgDommxn5/bIv0cnQZsPhHDA90NPHD6+c/v21U5+Sx5hoP8+dP9IZXBU1gIfvdRfhG8cel9QNPeionfcCQ==, + } + dev: false + /url-parse@1.5.10: resolution: { @@ -26606,7 +26719,6 @@ packages: { integrity: sha512-2JAn3z8AR6rjK8Sm8orRC0h/bcl/DqL7tRPdGZ4I1CjdF+EaMLmYxBHyXuKL849eucPFhvBoxMsflfOb8kxaeQ==, } - dev: true /webidl-conversions@4.0.2: resolution: @@ -27151,7 +27263,6 @@ packages: dependencies: tr46: 0.0.3 webidl-conversions: 3.0.1 - dev: true /whatwg-url@7.1.0: resolution: @@ -27295,6 +27406,13 @@ packages: } engines: { node: '>=0.10.0' } + /wordwrap@1.0.0: + resolution: + { + integrity: sha512-gvVzJFlPycKc5dZN4yPkP8w7Dc37BtP1yczEneOb4uq34pXZcvrtRTmWV8W+Ume+XCxKgbjM+nevkyFPMybd4Q==, + } + dev: false + /workbox-background-sync@6.6.0: resolution: {