How to internationalize a Yup validation schema in a React, Formik and react-i18next app

How to internationalize a Yup validation schema in a React, Formik and react-i18next appAbou KoneBlockedUnblockFollowFollowingJun 12Internationalization of Yup validation schema with Formik and react-18nextAnybody that had to deal with internationalization (shortened as i18n) knows that it can be a real pain if not handled properly, but in the modern Javascript stack, there exists libraries that remove a lot of that pain and actually make it a breeze.

One of these libraries is i18next.

If you work with React, you can’t do better than its react-i18next port for the way it seamless exposes the i18next api using all of the major React constructs (Hooks, HOCs, Render Props and Components).

Formik is form management library that promises to allow you to “build forms in React, without the tears” and I can say that so far, my eyes have remained quite dry.

Who says form also says validation and Formik integrates seamlessly with Yup, an JavaScript object schema validator and object parser.

Yup supports localization, but you have to provide it with a custom locale object, and I felt that that functionality should be single handedly handled by i18next.

This article will explore how you can sync the translation of the validation errors in Yup when the user changes the selected page language.

The BugIn the StackBlitz below, we have a basic setup of React, react-i18next, Formik and Yup.

We display a form with a required email field defined in a Yup schema.

This form can also be translated in French.

To observe the bug in question in syncing the translation:Click in the email fieldClick outsideYou should see a Email is required error.

Now click on the Francaislink.

Everything on the page changes to the French translation except for the validation error.

react–18next, Yup and Formik basic example – CodeSandboxCodeSandbox is an online editor tailored for web applications.

codesandbox.

ioI suspect this happens because validation schema is initiated when the component renders with the language set to English initially, and on changing the language, the validation is not re-ran, causing the message to stay in English.

The FixLuckily the i18next exposes events, in particular the languageChanged event that we can listen to and update the validation so the validation message can be translated.

I initially implemented in a global useEffect hook (that I will share later in this article) that listened for this event and re-ran the form validation , but this issue on Github had a more elegant solution, setting all field with an errors to be touched, which should trigger the validation.

The code in question is here:i18n.

on('languageChanged', () => { Object.

keys(errors).

forEach(fieldName => { setFieldTouched(fieldName) })})Here is a blitz of the working translation:react–18next, Yup and Formik basic example – CodeSandboxCodeSandbox is an online editor tailored for web applications.

codesandbox.

ioThe errors object and setFieldTouched function here are the form.

errors and form.

setFieldTouched properties of the Formik form object passed in a prop.

My requirements were different as I only wanted to show an error if the field had indeed been touched.

Use a hookIn my particular case, I was dealing not only with field level validation bugs, but I also had nested forms where the same was happening.

I created a global hook that takes in a Formik form object and sets only the fields that have an error as touched.

Here is the code:This way if the user had previously interacted with the field and gotten a validation error, the translation will re-render the form only with the existing errors translated.

You can adjust depending on your business requirements.

WithTranslateFormErrors HOCI’ve created an HOC that you can add to your Formik form that will set this up for you.

The code is pretty simple:And you would include it in your Formik form like this:You don’t need to use the HOC if you’re rendering your Formik form as a component.

In that case, you can just use the useTranslateFormErrors hook on its own in your render function.

This hook and HOC are available as part of the react-i18next-helpers library I recently released.

I am CTO at AKIL Technologies, an Abidjan, Ivory Coast tech startup where I lead a team of Angular and React devs ready to contribute on interesting projects.

Give us a toot if you need to beef up your front end teams!.. More details

Leave a Reply