microapps / gatsby-plugin-react-i18next

Easily translate your Gatsby website into multiple languages
MIT License
122 stars 72 forks source link

[Help wanted] Build failed on localization? #114

Open AhmedBHameed opened 2 years ago

AhmedBHameed commented 2 years ago

Hi there!

For Gatsby, While developing, the application works just fine till we started to build. We are encounter with the error listed down. The following configuration we used looks like this:

gatsby-config.js

const path = require('path');
const { languages, defaultLanguage } = require('./languages');

const gatsbyRequiredRules = path.join(
  process.cwd(),
  'node_modules',
  'gatsby',
  'dist',
  'utils',
  'eslint-rules'
);

module.exports = {
  siteMetadata: {
    siteUrl: 'https://www.yourdomain.tld',
    title: 'developer.xentral.com',
  },
  plugins: [
    'gatsby-plugin-postcss',
    'gatsby-plugin-image',
    'gatsby-plugin-react-helmet',
    {
      resolve: 'gatsby-plugin-manifest',
      options: {
        icon: 'src/images/icon.png',
      },
    },
    'gatsby-plugin-sharp',
    'gatsby-transformer-sharp',
    {
      resolve: 'gatsby-source-filesystem',
      options: {
        name: 'images',
        path: './src/images/',
      },
      __key: 'images',
    },
    {
      resolve: 'gatsby-plugin-eslint',
      options: {
        rulePaths: [gatsbyRequiredRules],
        stages: ['develop'],
        extensions: ['js', 'jsx', 'ts', 'tsx'],
        exclude: ['node_modules', 'bower_components', '.cache', 'public'],
      },
    },
    {
      resolve: 'gatsby-source-filesystem',
      options: {
        path: `${__dirname}/locales`,
        name: 'locale'
      },
      __key: 'locale',
    },
    {
      resolve: 'gatsby-plugin-react-i18next',
      options: {
        localeJsonSourceName: 'locale',
        languages,
        defaultLanguage,
        redirect: true,
        generateDefaultLanguagePage: true,
        // if you are using Helmet, you must include siteUrl, and make sure you add http:https
        siteUrl: 'https://developer.example.com/',
        // you can pass any i18next options
        i18nextOptions: {
          debug: true,
          interpolation: {
            escapeValue: false // not needed for react as it escapes by default
          },
          keySeparator: false,
          nsSeparator: false
        },
        pages: [
          {
            matchPath: '/:lang?',
            getLanguageFromPath: true,
          },
        ]
      }
    },
  ],
};

gatsby-node.js

exports.onCreateWebpackConfig = ({ stage, loaders, actions }) => {
  if (stage === 'build-html' || stage === 'develop-html') {
    actions.setWebpackConfig({
      module: {
        rules: [
          {
            test: /@xentral\/websites-core/,
            use: loaders.null(),
          },
        ],
      },
    });
  }
};

languages.js

module.exports = {
  languages: ['en', 'de'],
  defaultLanguage: 'en'
};

Pages folder structure is like this:

├── pages
│   ├── 404.tsx
│   ├── de
│   │   ├── http-api.tsx
│   │   └── index.tsx
│   ├── http-api.tsx
│   └── index.tsx

package.json

{
  "name": "developer.example.com",
  "version": "1.0.0",
  "private": true,
  "description": "...",
  "author": "ahmedbhameed",
  "keywords": [
    "gatsby"
  ],
  "scripts": {
    "develop": "gatsby develop",
    "start": "gatsby develop",
    "build": "gatsby build",
    "serve": "gatsby serve",
    "clean": "gatsby clean",
    "lint:r": "eslint **/*.{ts,tsx}",
    "lint:r:fix": "npm run lint:r -- --fix",
    "prettify": "prettier --write src",
    "prepare:husky": "husky install && npx husky add .husky/pre-commit \"npm run pre-commit\"",
    "prepare": "husky install",
    "pre-commit": "lint-staged",
    "test": "jest --coverage --silent",
    "test:debug": "jest --coverage=false --watchAll --verbose --detectOpenHandles"
  },
  "dependencies": {
    "@fontsource/inter": "^4.5.1",
    "@loadable/component": "^5.15.2",
    "@xentral/websites-core": "^1.0.14",
    "gatsby": "^4.5.3",
    "gatsby-plugin-image": "^2.5.2",
    "gatsby-plugin-manifest": "^4.5.2",
    "gatsby-plugin-react-helmet": "^5.5.0",
    "gatsby-plugin-react-i18next": "^1.2.2",
    "gatsby-plugin-sharp": "^4.5.2",
    "gatsby-source-filesystem": "^4.5.2",
    "gatsby-transformer-sharp": "^4.5.0",
    "i18next": "^21.6.6",
    "i18next-http-backend": "^1.3.1",
    "react": "^17.0.2",
    "react-dom": "^17.0.2",
    "react-helmet": "^6.1.0",
    "react-i18next": "^11.15.3"
  },
  "devDependencies": {
    "@babel/plugin-proposal-private-methods": "^7.16.7",
    "@tailwindcss/typography": "^0.5.0",
    "@testing-library/jest-dom": "^5.16.1",
    "@testing-library/react": "^12.1.2",
    "@types/jest": "^27.4.0",
    "@types/jest-axe": "^3.5.3",
    "@types/loadable__component": "^5.13.4",
    "@typescript-eslint/eslint-plugin": "^5.9.1",
    "@typescript-eslint/parser": "^5.9.1",
    "autoprefixer": "^10.4.2",
    "babel-eslint": "^10.1.0",
    "babel-jest": "^27.4.6",
    "babel-preset-gatsby": "^2.5.2",
    "eslint": "^8.7.0",
    "eslint-config-airbnb": "^19.0.4",
    "eslint-plugin-import": "^2.25.4",
    "eslint-plugin-jsx-a11y": "^6.5.1",
    "eslint-plugin-react": "^7.28.0",
    "eslint-plugin-react-hooks": "^4.3.0",
    "eslint-plugin-simple-import-sort": "^7.0.0",
    "eslint-webpack-plugin": "^3.1.1",
    "gatsby-plugin-eslint": "^4.0.2",
    "gatsby-plugin-postcss": "^5.5.0",
    "husky": "^7.0.4",
    "identity-obj-proxy": "^3.0.0",
    "jest": "^27.4.7",
    "jest-axe": "^5.0.1",
    "jest-watch-typeahead": "^1.0.0",
    "lint-staged": "^12.1.7",
    "postcss": "^8.4.5",
    "prettier": "^2.5.1",
    "react-test-renderer": "^17.0.2",
    "tailwindcss": "^3.0.15",
    "ts-jest": "^27.1.3",
    "typescript": "^4.5.4"
  },
  "husky": {
    "hooks": {
      "pre-commit": "lint-staged"
    }
  },
  "lint-staged": {
    "src/**/*.{js,ts,tsx}": [
      "eslint --fix"
    ]
  }
}

It fails on build script with the following error:

success Writing page-data.json files to public directory - 0.006s - 8/8 1296.27/s
i18next: languageChanged en
i18next: initialized {
  debug: true,
  initImmediate: true,
  ns: [ 'translation' ],
  defaultNS: 'translation',
  fallbackLng: [ 'en' ],
  fallbackNS: [],
  supportedLngs: false,
  nonExplicitSupportedLngs: false,
  load: 'all',
  preload: false,
  simplifyPluralSuffix: true,
  keySeparator: false,
  nsSeparator: false,
  pluralSeparator: '_',
  contextSeparator: '_',
  partialBundledLanguages: false,
  saveMissing: false,
  updateMissing: false,
  saveMissingTo: 'fallback',
  saveMissingPlurals: true,
  missingKeyHandler: false,
  missingInterpolationHandler: false,
  postProcess: false,
  postProcessPassResolved: false,
  returnNull: true,
  returnEmptyString: true,
  returnObjects: false,
  joinArrays: false,
  returnedObjectHandler: false,
  parseMissingKeyHandler: false,
  appendNamespaceToMissingKey: false,
  appendNamespaceToCIMode: false,
  overloadTranslationOptionHandler: [Function: handle],
  interpolation: {
    escapeValue: false,
    format: [Function: bound format],
    prefix: '{{',
    suffix: '}}',
    formatSeparator: ',',
    unescapePrefix: '-',
    nestingPrefix: '$t(',
    nestingSuffix: ')',
    nestingOptionsSeparator: ',',
    maxReplaces: 1000,
    skipOnVariables: true
  },
  resources: {},
  lng: 'en',
  react: { useSuspense: false },
  userDefinedKeySeparator: false,
  userDefinedNsSeparator: false,
  ignoreJSONStructure: true
}
i18next: languageChanged en
i18next: initialized {
  debug: true,
  initImmediate: true,
  ns: [ 'translation' ],
  defaultNS: 'translation',
  fallbackLng: [ 'en' ],
  fallbackNS: [],
  supportedLngs: false,
  nonExplicitSupportedLngs: false,
  load: 'all',
  preload: false,
  simplifyPluralSuffix: true,
  keySeparator: false,
  nsSeparator: false,
  pluralSeparator: '_',
  contextSeparator: '_',
  partialBundledLanguages: false,
  saveMissing: false,
  updateMissing: false,
  saveMissingTo: 'fallback',
  saveMissingPlurals: true,
  missingKeyHandler: false,
  missingInterpolationHandler: false,
  postProcess: false,
  postProcessPassResolved: false,
  returnNull: true,
  returnEmptyString: true,
  returnObjects: false,
  joinArrays: false,
  returnedObjectHandler: false,
  parseMissingKeyHandler: false,
  appendNamespaceToMissingKey: false,
  appendNamespaceToCIMode: false,
  overloadTranslationOptionHandler: [Function: handle],
  interpolation: {
    escapeValue: false,
    format: [Function: bound format],
    prefix: '{{',
    suffix: '}}',
    formatSeparator: ',',
    unescapePrefix: '-',
    nestingPrefix: '$t(',
    nestingSuffix: ')',
    nestingOptionsSeparator: ',',
    maxReplaces: 1000,
    skipOnVariables: true
  },
  resources: {},
  lng: 'en',
  react: { useSuspense: false },
  userDefinedKeySeparator: false,
  userDefinedNsSeparator: false,
  ignoreJSONStructure: true
}
i18next: languageChanged de
i18next: initialized {
  debug: true,
  initImmediate: true,
  ns: [ 'translation' ],
  defaultNS: 'translation',
  fallbackLng: [ 'en' ],
  fallbackNS: [],
  supportedLngs: false,
  nonExplicitSupportedLngs: false,
  load: 'all',
  preload: false,
  simplifyPluralSuffix: true,
  keySeparator: false,
  nsSeparator: false,
  pluralSeparator: '_',
  contextSeparator: '_',
  partialBundledLanguages: false,
  saveMissing: false,
  updateMissing: false,
  saveMissingTo: 'fallback',
  saveMissingPlurals: true,
  missingKeyHandler: false,
  missingInterpolationHandler: false,
  postProcess: false,
  postProcessPassResolved: false,
  returnNull: true,
  returnEmptyString: true,
  returnObjects: false,
  joinArrays: false,
  returnedObjectHandler: false,
  parseMissingKeyHandler: false,
  appendNamespaceToMissingKey: false,
  appendNamespaceToCIMode: false,
  overloadTranslationOptionHandler: [Function: handle],
  interpolation: {
    escapeValue: false,
    format: [Function: bound format],
    prefix: '{{',
    suffix: '}}',
    formatSeparator: ',',
    unescapePrefix: '-',
    nestingPrefix: '$t(',
    nestingSuffix: ')',
    nestingOptionsSeparator: ',',
    maxReplaces: 1000,
    skipOnVariables: true
  },
  resources: {},
  lng: 'de',
  react: { useSuspense: false },
  userDefinedKeySeparator: false,
  userDefinedNsSeparator: false,
  ignoreJSONStructure: true
}
i18next: languageChanged en
i18next: initialized {
  debug: true,
  initImmediate: true,
  ns: [ 'translation' ],
  defaultNS: 'translation',
  fallbackLng: [ 'en' ],
  fallbackNS: [],
  supportedLngs: false,
  nonExplicitSupportedLngs: false,
  load: 'all',
  preload: false,
  simplifyPluralSuffix: true,
  keySeparator: false,
  nsSeparator: false,
  pluralSeparator: '_',
  contextSeparator: '_',
  partialBundledLanguages: false,
  saveMissing: false,
  updateMissing: false,
  saveMissingTo: 'fallback',
  saveMissingPlurals: true,
  missingKeyHandler: false,
  missingInterpolationHandler: false,
  postProcess: false,
  postProcessPassResolved: false,
  returnNull: true,
  returnEmptyString: true,
  returnObjects: false,
  joinArrays: false,
  returnedObjectHandler: false,
  parseMissingKeyHandler: false,
  appendNamespaceToMissingKey: false,
  appendNamespaceToCIMode: false,
  overloadTranslationOptionHandler: [Function: handle],
  interpolation: {
    escapeValue: false,
    format: [Function: bound format],
    prefix: '{{',
    suffix: '}}',
    formatSeparator: ',',
    unescapePrefix: '-',
    nestingPrefix: '$t(',
    nestingSuffix: ')',
    nestingOptionsSeparator: ',',
    maxReplaces: 1000,
    skipOnVariables: true
  },
  resources: {},
  lng: 'en',
  react: { useSuspense: false },
  userDefinedKeySeparator: false,
  userDefinedNsSeparator: false,
  ignoreJSONStructure: true
}
i18next: languageChanged de
i18next: initialized {
  debug: true,
  initImmediate: true,
  ns: [ 'translation' ],
  defaultNS: 'head',
  fallbackLng: [ 'en' ],
  fallbackNS: [ 'home' ],
  supportedLngs: false,
  nonExplicitSupportedLngs: false,
  load: 'all',
  preload: false,
  simplifyPluralSuffix: true,
  keySeparator: false,
  nsSeparator: false,
  pluralSeparator: '_',
  contextSeparator: '_',
  partialBundledLanguages: false,
  saveMissing: false,
  updateMissing: false,
  saveMissingTo: 'fallback',
  saveMissingPlurals: true,
  missingKeyHandler: false,
  missingInterpolationHandler: false,
  postProcess: false,
  postProcessPassResolved: false,
  returnNull: true,
  returnEmptyString: true,
  returnObjects: false,
  joinArrays: false,
  returnedObjectHandler: false,
  parseMissingKeyHandler: false,
  appendNamespaceToMissingKey: false,
  appendNamespaceToCIMode: false,
  overloadTranslationOptionHandler: [Function: handle],
  interpolation: {
    escapeValue: false,
    format: [Function: bound format],
    prefix: '{{',
    suffix: '}}',
    formatSeparator: ',',
    unescapePrefix: '-',
    nestingPrefix: '$t(',
    nestingSuffix: ')',
    nestingOptionsSeparator: ',',
    maxReplaces: 1000,
    skipOnVariables: true
  },
  resources: { de: { head: [Object], home: [Object] } },
  lng: 'de',
  react: { useSuspense: false },
  userDefinedKeySeparator: false,
  userDefinedNsSeparator: false,
  ignoreJSONStructure: true
}
i18next: languageChanged en
i18next: initialized {
  debug: true,
  initImmediate: true,
  ns: [ 'translation' ],
  defaultNS: 'translation',
  fallbackLng: [ 'en' ],
  fallbackNS: [],
  supportedLngs: false,
  nonExplicitSupportedLngs: false,
  load: 'all',
  preload: false,
  simplifyPluralSuffix: true,
  keySeparator: false,
  nsSeparator: false,
  pluralSeparator: '_',
  contextSeparator: '_',
  partialBundledLanguages: false,
  saveMissing: false,
  updateMissing: false,
  saveMissingTo: 'fallback',
  saveMissingPlurals: true,
  missingKeyHandler: false,
  missingInterpolationHandler: false,
  postProcess: false,
  postProcessPassResolved: false,
  returnNull: true,
  returnEmptyString: true,
  returnObjects: false,
  joinArrays: false,
  returnedObjectHandler: false,
  parseMissingKeyHandler: false,
  appendNamespaceToMissingKey: false,
  appendNamespaceToCIMode: false,
  overloadTranslationOptionHandler: [Function: handle],
  interpolation: {
    escapeValue: false,
    format: [Function: bound format],
    prefix: '{{',
    suffix: '}}',
    formatSeparator: ',',
    unescapePrefix: '-',
    nestingPrefix: '$t(',
    nestingSuffix: ')',
    nestingOptionsSeparator: ',',
    maxReplaces: 1000,
    skipOnVariables: true
  },
  resources: {},
  lng: 'en',
  react: { useSuspense: false },
  userDefinedKeySeparator: false,
  userDefinedNsSeparator: false,
  ignoreJSONStructure: true
}

 ERROR 

Page data from page-data.json for the failed page "/de/": {
  "componentChunkName": "component---src-pages-de-index-tsx",
  "path": "/de/",
  "result": {
    "data": {
      "locales": {
        "edges": [
          {
            "node": {
              "ns": "head",
              "data": "{\"httpApi\":\"HTTP API\",\"graphqlApi\":\"GraphQL API\"}",
              "language": "de"
            }
          },
          {
            "node": {
              "ns": "home",
              "data": "{\"adminApisTitle\":\"Admin API's\",\"adminApiDescription\":\"Eine Reihe neuer APIs, die
wir entwickeln. Sie bieten größere Flexibilität und ermöglichen den Zugriff auf alle Ressourcen innerhalb von
Xentral.\"}",
              "language": "de"
            }
          }
        ]
      }
    },
    "pageContext": {
      "language": "de",
      "i18n": {
        "language": "de",
        "languages": [
          "en",
          "de"
        ],
        "defaultLanguage": "en",
        "generateDefaultLanguagePage": true,
        "routed": true,
        "originalPath": "/",
        "path": "/de/"
      }
    }
  },
  "staticQueryHashes": []
}

failed Building static HTML for pages - 1.791s

 ERROR #95313 

Building static HTML failed for path "/de/"

See our docs page for more info on this error: https://gatsby.dev/debug-html

  36 |       if (desc && (desc.get || desc.set)) {
  37 |         Object.defineProperty(newObj, key, desc);
> 38 |       } else {
     |         ^
  39 |         newObj[key] = obj[key];
  40 |       }
  41 |     }

  WebpackError: Minified React error #130; visit https://reactjs.org/docs/error-decoder.html?invariant=130&args[
  ]=undefined&args[]= for the full message or use the non-minified dev environment for full errors and additiona
  l helpful warnings.

  - interopRequireWildcard.js:38 
    [developer.xentral.com]/[@babel]/runtime/helpers/interopRequireWildcard.js:38:9

  - interopRequireWildcard.js:34 
    [developer.xentral.com]/[@babel]/runtime/helpers/interopRequireWildcard.js:34:1

  - classCallCheck.js:3 
    [developer.xentral.com]/[@babel]/runtime/helpers/classCallCheck.js:3:1

  - static-entry.js:294 
    developer.xentral.com/.cache/static-entry.js:294:22

  - createClass.js:1 
    [developer.xentral.com]/[@babel]/runtime/helpers/createClass.js:1:1

  - objectWithoutPropertiesLoose.js:4 
    [developer.xentral.com]/[@babel]/runtime/helpers/objectWithoutPropertiesLoose.js:4:1

  - extends.js:9 
    [developer.xentral.com]/[@babel]/runtime/helpers/extends.js:9:1

error Command failed with exit code 1.
info Visit https://yarnpkg.com/en/docs/cli/run for documentation about this command.

Any idea of this error? Is there any updated example to follow? Not the ones from Gatsby documentation please.

Migarl commented 2 years ago

Hi @AhmedBHameed! I face the same error now. Do you managed to fix it?

AhmedBHameed commented 2 years ago

Hi @Migarl I ended up using next.js