Guard against es6/jsx template literal translations

Description

Template literals, which are a new feature in es6, should not be used for gettext-marked strings.

For example: gettext(`Hello, ${user}`) – gettext() will see `Hello, mike` and fail to match it to a translation in its catalog. (Transpiling doesn't fix this for us, as it results in gettext('Hello,'+user) code.)

We should guard against that in our linting or somewhere, edx-wide. Otherwise we might accidentally end up with untranslated strings.

It's a very similar problem to doing gettext('Hi, {}'.format()) rather than gettext('Hi, {}').format(), which ideally we also guard against?

Notes

  • edx-platform has some strings like this in lms/djangoapps/support/** and also CourseGoals.js (but they aren't even being extracted right now... (see below extraction talk)

  • Only edx-mktg actually correctly extracts the string in the first place. And it doesn't use this construct yet. Django's built in js support (which we use in platform at least) doesn't notice backticks and we aren't even extracting strings from jsx code currectly today (see below extraction talk for more details there).

Extraction details

So I recently noticed that gettext-marked strings from edx-platform that were in jsx files were not ending up in the po files.

This is because i18n_tool was not extracting them. It uses django's support for js files. I've modified it to also scan jsx files to pick them up. (by just telling django to also look at *.jsx files – no special support)
https://github.com/edx/i18n-tools/commit/2d3232874e1325bca74c238836f5d8f237d467e3

But Django's js support is real dumb. It renames the file to a .c file and does some simple replacements so that xgettext doesn't choke.
https://github.com/django/django/blob/9718fa2e8abe430c3526a9278dd976443d4ae3c6/django/utils/jslex.py#L185

In the files I tested, it seemed to work just fine for .jsx files. So I figured good enough for now.

But django doesn't understand es6 – it doesn't try to handle backticks at all, so any backtick strings don't get extracted. Which, because of this ticket, I'm OK with. But there might be some other es6 constructs it doesn't work for? In which case, we should probably switch to something heavier-weight for js/jsx extraction, like babel, which we already use elsewhere.

Steps to Reproduce

None

Current Behavior

None

Expected Behavior

None

Reason for Variance

None

Release Notes

None

User Impact Summary

None

Status

Assignee

Unassigned

Reporter

Michael Terry

Labels

None

Reach

None

Impact

None

Platform Area

None

Customer

None

Partner Manager

None

URL

None

Contributor Name

None

Groups with Read-Only Access

None

Actual Points

None

Category of Work

None

Platform Map Area (Levels 1 & 2)

None

Platform Map Area (Levels 3 & 4)

None

Priority

Unset
Configure