STRAPI의 i18n

28214 단어
wikipedia에 따라

Internationalisation and Localisation, often abbreviated i18n and L10n, is the process of designing a software application so that it can be adapted to various languages and regions without engineering changes.



사용 사례를 예로 들어 보겠습니다. 그래서 우리 둘 다 같은 페이지에 있습니다.
  • 다음 필드가 있는 home-page라는 컬렉션이 하나 있습니다. (내 사용 사례는 4-5개 언어에 대한 지원을 제공하는 것이었으며 향후 더 필요할 수 있습니다.)



  • 여기서 배너(단일 구성 요소) 및 브랜드(반복 가능한 구성 요소)는 구성 요소입니다.
    필드 설명:

  • 제목
    - home-page 3개의 필드 title , title_ar , title_ru , 제목 값 English(en) , Arabic(ar)Russian(ru) 언어가 각각 있습니다.

  • 배너 및 브랜드
    - 배너의 title 및 브랜드의 name는 언어에 따라 다르며 나머지 필드는 모든 언어에 대해 동일합니다.
    - 그리고 선택된 languageCode가 ar 일 때 내 프론트엔드는 배너에 대한 응답으로 title = titile_ar, 브랜드에 대한 응답으로 name = name_ar가 필요합니다.

  • 내 접근 방식(플러그인을 사용하지 않음):



  • 언어 종속 필드를 지정하는 파일을 만들었습니다.

    This is generated automatically (based on the collection) when server starts.
    projec_dir/constants/i18n.config.json



    {
      "home-page": [
        "title"
      ],
      "component.banner-component": [
        "title"
      ],
      "component.brand-component": [
        "name"
      ]
    }
    


  • find, findOne 또는 기타 맞춤형 서비스를 사용하여 모델에서 데이터를 가져옵니다.
  • 모델의 스키마 가져오기(project-dir/constants/i18n.config.json에서 가져온 JSON에서 언어 종속 필드를 가져오기 위한 속성 이름에 필요)
  • ${field}${field}${languageCode}로 바꿉니다.
  • 삭제 ${field}${languageCode} .

  • 암호:



  • project_dir/constants/i18n.constants.js

    const i18nFields = require('./i18n.config.json');
    const DEFAULT_LANGUAGE = 'en';
    const LANGUAGE_LIST = ['en', 'ar', 'ka', 'ru', 'uzb'];
    const I_18_FIELDS = i18nFields;
    const I18N_LIST = ['home-page'];
    
    module.exports = {
      DEFAULT_LANGUAGE,
      LANGUAGE_LIST,
      I_18_FIELDS,
      I18N_LIST,
    };
    
    


  • project_dir/utils/i18n.utils.js

     const _ = require('lodash');
    const {
      LANGUAGE_LIST,
      DEFAULT_LANGUAGE,
    } = require('../constants/i18n.constants');
    
    function internationalizeFields(components, langCode, fields) {
      if (!components) {
        return undefined;
      }
      const i18Component = { ...components };
      if (fields) {
        fields.forEach((field) => {
          const currentLanguageFieldValue = _.get(
            i18Component,
            `${field}_${langCode}`
          );
          if (langCode !== DEFAULT_LANGUAGE) {
            _.set(i18Component, field, currentLanguageFieldValue);
          }
          LANGUAGE_LIST.forEach((lang) =>
            _.unset(i18Component, `${field}_${lang}`)
          );
        });
      }
      return i18Component;
    }
    module.exports = {
      internationalizeFields,
    };
    
  • project_dir/utils/strapi.util.js

  • /* global strapi */
    
    function getAttributes({ modelName }) {
      try {
        return strapi.api[modelName].models[modelName].__schema__.attributes;
      } catch (err) {
        //throw error
      }
    }
    function addComponentSchema({ parentSchema }) {
      const result = Object.keys(parentSchema).reduce((acc, curr) => {
        acc[curr] = parentSchema[curr];
        if (parentSchema[curr].type !== 'component') {
          return acc;
        }
        const component = strapi.components[acc[curr].component];
        if (!component) {
          throw error
        }
        acc[curr].schema = component.attributes;
        acc[curr].schema = addComponentSchema({ parentSchema: acc[curr].schema });
        return acc;
      }, {});
      if (!result || Object.keys(result).length === 0) {
        //through error
      }
      return result;
    }
    
    module.exports = {
      getAttributes,
      addComponentSchema,
    };
    
    

  • project_dir/utils/controller.util.js

  • 
    const { DEFAULT_LANGUAGE } = require('../common/constants/i18n.constants');
    const { I_18_FIELDS } = require('../common/constants/i18n.constants');
    const { internationalizeFields } = require('../common/utils/i18n.utils');
    const { getAttributes, addComponentSchema } = require('./strapi.utils');
    
    /**
     * @param {*} modelName modelName for keys in I_18_FIELDS
     * @param {*} data data to be internationlised
     * @param {*} schema schema corresponding to modelName
     * @param {*} lang
     * @returns internationalised data
     */
    async function internationalizeData({
      modelName,
      data,
      schema,
      lang = DEFAULT_LANGUAGE,
    }) {
      if (!data) {
        return data;
      }
      if (!schema) {
        const modelSchema = getAttributes({ modelName });
        schema = addComponentSchema({ parentSchema: modelSchema });
      }
      const schemaKeys = Object.keys(schema);
      if (!schemaKeys.length) {
        return data;
      }
      if (Array.isArray(data)) {
        data.forEach(async (entry, index) => {
          data[index] = await internationalizeData({
            modelName,
            data: entry,
            schema,
            lang,
          });
        });
        return data;
      } else {
        data = internationalizeFields(data, lang, I_18_FIELDS[modelName], null);
      }
      schemaKeys.forEach(async (curr) => {
        if (
          schema[curr] &&
          (schema[curr].type === 'component' || schema[curr].collection)
        ) {
          if ((schema[curr].repeatable || schema[curr].collection) && data[curr]) {
            data[curr].forEach(async (entry, index) => {
              data[curr][index] = await internationalizeData({
                modelName: schema[curr].component || schema[curr].collection,
                data: entry,
                schema: schema[curr].schema,
                lang,
              });
            });
          } else if (modelName.indexOf('.') === -1) {
            data[curr] = await internationalizeData({
              modelName: schema[curr].component,
              data: data[curr],
              schema: schema[curr].schema,
              lang,
            });
          }
        }
      });
      return data;
    }
    module.exports = {
      internationalizeData,
    };
    

  • project_dir/api/homepage/controller.js

  • /* global strapi */
    
    const { sanitizeEntity } = require('strapi-utils');
    const { internationalizeData } = require('../../../utils/controller.util');
    
    async function findOne(ctx) {
      const { id } = ctx.params;
      const { lang } = ctx.request.header;
      const entity = await strapi.services['home-page'].find({ id });
      const sanitizedEntity = sanitizeEntity(entity, {
        model: strapi.models['home-page'],
      });
      const data = internationalizeData({
        modelName: 'home-page',
        data: sanitizedEntity,
        schema: null,
        lang,
      });
      return data;
    }
    module.exports = {
      findOne,
    };
    
    

    마찬가지로 다른 API에 대해서도 할 수 있습니다.


    토론 상자에서 귀하의 접근 방식에 대해 논의하거나 [email protected] 으로 연락하십시오.

    읽어 주셔서 감사합니다.

    좋은 웹페이지 즐겨찾기