Something went wrong. Try again.
[READ-ONLY] Mirror of https://github.com/wojtekmaj/react-t. Simple translation module for React applications.
Something went wrong. Try again.
TypeScript
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123import { cloneElement, isValidElement, useContext } from 'react';import invariant from 'tiny-invariant';
import TContext from './TContext';
import type { Args, ArgsOfNodes, ArgsOfStringsOrNumbers, LanguageFile } from './shared/types';
function getRawTranslatedString(string: string, languageFile: LanguageFile | undefined): string { if (languageFile) { const rawTranslatedString = languageFile[string];
if (rawTranslatedString) { return rawTranslatedString; } }
return string;}
function applyArg( string: string, argName: string, replacement: string | number, keyPrefix: string,): string;function applyArg( string: string, argName: string, replacement: React.ReactNode, keyPrefix: string,): React.ReactNode[];function applyArg( string: string, argName: string, replacement: string | number | React.ReactNode, keyPrefix = '',): string | React.ReactNode[] { const placeholder = `{${argName}}`; const regExp = new RegExp(placeholder, 'g');
if (typeof replacement === 'string' || typeof replacement === 'number') { const result = string.replace(regExp, `${replacement}`);
return result; }
const splitString = string.split(placeholder);
const initialValue: React.ReactNode[] = [];
return splitString.reduce((arr, element, index) => { const isLast = index === splitString.length - 1;
if (isLast) { return [...arr, element]; }
return [ ...arr, element, isValidElement(replacement) ? // eslint-disable-next-line react/no-array-index-key cloneElement(replacement, { key: `${keyPrefix}-${index}` }) : replacement, ]; }, initialValue);}
function applyArgs(string: string, args: ArgsOfStringsOrNumbers): string;function applyArgs(string: string, args: ArgsOfNodes): React.ReactNode[];function applyArgs(rawString: string, args: Args): string | React.ReactNode[] { let result: React.ReactNode[] = [rawString];
for (const [argName, replacement] of Object.entries(args || {})) { result = result.flatMap((string, index) => { return typeof string === 'string' ? applyArg(string, argName, replacement, `${index}`) : string; }); }
return result;}
export default function useTranslation(string?: undefined, args?: undefined): undefined;export default function useTranslation(string: undefined, args?: Args): undefined;export default function useTranslation<T extends string | undefined>( string: T, args?: undefined,): T extends string ? string : undefined;export default function useTranslation<T extends string | undefined>( string: T, args: ArgsOfStringsOrNumbers,): T extends string ? string : undefined;export default function useTranslation<T extends string | undefined>( string: T, args: ArgsOfNodes,): T extends string ? React.ReactNode[] : undefined;export default function useTranslation( string?: string, args?: Args,): string | React.ReactNode[] | undefined { const context = useContext(TContext);
invariant(context, 'Unable to find TProvider context. Did you wrap your app in <TProvider />?');
const { languageFile } = context;
if (!string) { return string; }
const rawTranslatedString = getRawTranslatedString(string, languageFile);
if (!args) { return rawTranslatedString; }
const stringWithArgs = applyArgs(rawTranslatedString, args);
return stringWithArgs;}