Published

How to detect Google Translate and other machine translation

Machine translation, such as done natively by Google Translate inside the Google Chrome browser, provides users with dynamic translation of webpages from within their browser tab.

There may be many reasons to want to detect when this happens, such as to deal with issues caused by the behavior of these tools, to offer to change the language within your app, or to track which languages users are translating to as a means to offer more locales in your app.

Most machine translators can be detected simply by monitoring the html element's lang attribute for changes. Any proper machine translator will update its value to reflect the new language inside your page after translation is applied.

Note

Make sure your html element has the correct lang attribute set initially. If it is omitted, detection will not work.

You can detect most machine translations, including Google Translate, with the following code snippet:

const originalLanguge = document.documentElement.lang;
// Works at least for Chrome, Firefox, Safari and probably more. Not Microsoft
// Edge though. They're special.
// Yell at clouds if a translator doesn't change it
const observer = new MutationObserver(() => {
const lang = document.documentElement.lang;
if (lang !== originalLanguge) {
console.log(
'Page translation detected (Generic)',
`lang="${document.documentElement.lang}" (original="${originalLanguge}")`
);
}
});
observer.observe(document.documentElement, {
attributes: true,
attributeFilter: ['lang'],
childList: false,
characterData: false,
});

Unfortunately Microsoft Edge (the new Internet Explorer) doesn't actually update the lang attribute when translating, so it needs its own detector;

const title = document.getElementsByTagName('title')[0];
if (!title) {
return;
}
const observer = new MutationObserver(() => {
if (title.hasAttribute('_msttexthash')) {
// This gets triggered twice when translation is on
console.log('Page translation detected (Microsoft Edge)');
}
});
observer.observe(title, {
attributes: true,
attributeFilter: ['_msttexthash'],
childList: false,
characterData: false,
});

With these code snippets, in place of the console.log, you can trigger anything you want to trigger when your page gets translated. You could apply a monkey patch, update some global state to make your rendering library show a (more prominent) language switcher, or send an event to GTM.

Hope that helps.

Aside

Machine translators' DOM changes often interfere with tools like React, leading to crashes. For React I plan to write a more extensive gist about ways to mitigate this.

More like this