i18n(국제화) 관련 작업을 위해 비슷한 이름의 여러 라이브러리를 설치해 본 경험이 있다면 각각이 어떤 역할을 하는지 궁금해 질 수 있습니다. 이번 기회에 각각의 라이브러리가 무엇을 하는지 정리해 보았습니다.
i18n은 internationalization(i와 n 사이의 18글자)을 줄인 것으로 한글로 번역하면 ‘국제화’입니다. W3C의 정의에 따르면 국제화는 다음을 의미합니다.
국제화(Internationalization)는 문화, 지역, 언어가 다양한 대상 고객을 위해 쉽게 현지화할 수 있는 제품, 애플리케이션 또는 문서 콘텐츠를 설계하고 개발하는 것입니다. - W3C
i18n은 웹이나 JS에 종속된 개념이 아닌 컴퓨터 소프트웨어(혹은 그 이상 분야) 전반에서 범용적으로 사용되는 단어입니다. i18n을 쉽게 적용하기 위해 만들어진 JS 라이브러리의 이름은 i18next입니다!
국제화를 위해서는 다음 사항에 대한 지원을 필요로합니다.
i18n(국제화) 적용을 위한 JS 라이브러리는 다음과 같이 여러 종류가 있지만 일반적으로 i18next가 많이 사용됩니다.
i18next - documentation
i18next는 i18n 적용을 위한 JS 라이브러리로 보통 다음을 위해 사용됩니다.
이 외에도 다음과 같이 많은 기능을 포함합니다.
사용 방법은 다음과 같습니다.
i18next.init({
resources: {
en: {
translation: {
"key": "Welcome to React and react-i18next"
}
},
ko: {
translation: {
"key": "React 와 react-i18next"
}
}
}
}).then(function(t) {
document.getElementById('output').innerHTML = i18next.t('key');
});
미리 국가별로 지정한 ‘key’를 사용해 실제 텍스트를 렌더링 하는 부분에서 i18next.t로 감싸는 방식으로 번역을 지원합니다.
react-i18next는 i18next를 React/React-Native에서 사용하기 적합하게 만들어진 라이브러리입니다.
react-i18next은 다음과 같이 React에 적합한 useTranslation
이라는 커스텀 훅을 제공합니다.
import i18n from "i18next";
import { useTranslation, initReactI18next } from "react-i18next";
i18n
.use(initReactI18next)
.init({
resources: {
en: {
translation: {
"Welcome to React": "Welcome to React and react-i18next"
}
},
ko: {
translation: {
"웰컴 투 리액트": "React 와 react-i18next"
}
}
},
fallbackLng: "en",
});
function App() {
const { t } = useTranslation();
return <h2>{t('Welcome to React')}</h2>;
}
커스텀 훅을 이용하니 리액트스러운 i18n 적용이 가능해졌습니다.
해당 글은 Next.JS 13의 App Router가 아닌 Pages Router를 기준으로 작성되었습니다.
App Router의 i18n 적용은 아래와 다를 수 있습니다.
next-i18next는 위에서 살펴본 react-i18next를 Next.js 환경에서 사용하기 편리하게 만든 라이브러리입니다. Next.js에선 지금까지와는 다르게 SSR, 즉 서버 측면에서의 고려가 추가로 필요합니다. 국가 정보(locale)을 얻기 위한 방법은 다음과 같이 클라이언트와 서버 측면으로 나누어 볼 수 있습니다.
window.navigator
조회를 통해 가져옵니다.Next.js 에선 이렇게 확인된 유저의 국가(locale) 정보를 자동으로 인식하여 getServerSideProps 컨텍스트를 통해 클라이언트로 넘깁니다.
next-i18next 사용을 위해서는 아래코드와 같이 Home에 해당하는 컴포넌트를 appWithTranslation HOC로 감싸줍니다.
import { GetServerSideProps } from "next";
import { appWithTranslation } from "next-i18next";
import { serverSideTranslations } from "next-i18next/serverSideTranslations";
export const getServerSideProps: GetServerSideProps = async ({ locale }) => {
return {
props: {
...(await serverSideTranslations(locale ?? "ko", ["common"], null, [
"en",
"ja",
"ko",
])),
},
};
};
const Home = (props: any) => {
console.log(props);
return (
<LayoutWrapper>
<HeadMeta />
<Header />
<Section />
<Footer />
</LayoutWrapper>
);
};
export default appWithTranslation(Home);
메인 페이지 getServerSideProps
함수에서 locale을 받아 serverSideTranslations
함수에 넘겨준 후 클라이언트에서 받은 props를 console로 확인하면 다음과 같이 public/locales에 두었던 스트링 파일과 locale 관련 정보가 내려오는 것을 확인할 수 있습니다.
참고로 Next.JS는 다음과 같이 두 가지 방식의 Locale Strategies를 지원합니다.
Sub-path Routing
module.exports = {
i18n: {
locales: ['en-US', 'kr'],
defaultLocale: 'en-US',
},
}
Domain Routing
module.exports = {
i18n: {
locales: ['en-US', 'kr'],
defaultLocale: 'en-US',
domains: [
{
domain: 'example.com',
defaultLocale: 'en-US',
},
{
domain: 'example.kr',
defaultLocale: 'kr',
},
],
},
}
국제화 (internationalization, I18N) - MDN
Internationalization and localization - Wikipedia
i18next - documentation
react-i18next - documentation
next-i18next - github
Next.js로 다국어(i18n) 제공하기 - jeonbyeongmin님의 블로그