Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

react-i18next - No overload matches this call when `string` type specified

I'm using react-i18next with React and TypeScript. If I try loading a property using a string literal and type inference, it works correctly. However if I specify the type of string, the error is thrown.

i18n.ts

import ns1 from './locales/en/translation.json';
import { initReactI18next } from 'react-i18next';
import i18n from 'i18next';

export const defaultNS = 'ns1';

export const resources = {
  en: {
    ns1
  }
} as const;
i18n.use(initReactI18next).init({
  lng: 'en',
  ns: ['ns1', 'ns2'],
  defaultNS,
  resources
});

react-i18next.d.ts

import { resources, defaultNS } from './i18n';

// react-i18next versions higher than 11.11.0
declare module 'react-i18next' {
  interface CustomTypeOptions {
    defaultNS: typeof defaultNS;
    resources: typeof resources['en'];
  }
}

translation.json

{
  "title": "Welcome to react using react-i18next",
  "description": {
    "part1": "To get started, edit <1>src/App.js</1> and save to reload.",
    "part2": "Switch language between english and german using buttons above."
  }
}

Working code

import { useTranslation } from 'react-i18next';

const t = useTranslation().t;
const title = 'title';

// "Welcome to react using react-i18next"
console.log(t(title));

No overload matches this call exception

import { useTranslation } from 'react-i18next';

const t = useTranslation().t;
const title: string = 'title';

// No overload matches this call exception
console.log(t(title));

How can I translate a string variable where the type is specified?

like image 735
Michael Avatar asked Oct 20 '25 02:10

Michael


1 Answers

I guess the problem is that you are using type string, and that means it can be anything in there. I18next is using string literal types to check typing.

If you want types working in project, but sometimes use dynamic translation, at the moment you can cheat your way using Tagged Template Literal, as it does not work with type check right now:

t`key1.key2`;

Based on i18 documentation

Another option is to just override typing on t function to any:

t<any>(`namespace:${dynamicString}`)

Also when using defaultValue, the check is ignored:

t('dynamicString', { defaultValue: 'Test' })
like image 148
DirectionUnkown Avatar answered Oct 21 '25 15:10

DirectionUnkown