Description
I am delegating translations to the front-end by sending the message through REST API requests to a React component.
The problem I'm facing is that I am forced to create a decoder ring that seems like boilerplate code: and pretty tedious:
import {
trans,
...
OTP_FIELD_LABEL,
OTP_EXCEPTIONS_USERNAME_NOT_FOUND
} from '../../../translator';
const messages = {
'OTP_EXCEPTIONS_USERNAME_NOT_FOUND' : OTP_EXCEPTIONS_USERNAME_NOT_FOUND
};
That decoder ring is const messages
.
While reading the documentation, I noticed two things:
https://symfony.com/doc/current/translation.html#using-real-or-keyword-messages
The first is that I could refer to this translation in the backend as "otp.exceptions.username_not_found".
The second is that, I wrote the translations in YAML... had I written it in PHP I could send the whole translation file as a JSON object (not efficent obviously.
While importing consts from the translator is usable, it is also an error prone process, and more than once I've found myself using a const that I didn't import.
The feature request is to either or both be able to:
- Use
trans()
with the key notation and not having to import consts:
trans("otp.exceptions.username_not_found")
- Have a single objects to import, instead of all the consts:
import{
trans,
otp, //or OTP, but lowercase would make it consistent
} from '../../../translator';
...
trans(otp.exceptions.username_not_found);
...
trans(otp.field.label);
Why I think this is important:
- As it turned out, the decoder ring is sort of worth the effort because I have REST API unit tests (well, integration tests)... and sending the key notation as the message to delegate translation makes my tests very anti-fragile / not brittle / resilient.
I could be switching around the text and even the variables inside the text (I'm using the ICU format) and as long as the message id / structure remains the same, the tests don't break
- Either the key notation or the const object adds consistency, and also reduce redundant work. As pretty as the caps are (e.g. "const OTP_EXCEPTIONS_USERNAME_NOT_FOUND"... this is totally different than what one would use in PHP.
One of the goals of Symfony UX Translator (I assume) is to reuse translations in the front-end to reduce redundant work. The object const notation not only would make it look consistent with the key notation in PHP, but also reduce cognitive load and boilerplate code (multiple imports).
Boilerplate code not only makes the task longer, boring, but is also error prone.
-
Having the key notation available in Javascript would mean that one wouldn't even have to import the translation consts (could be imported in the background). This would make it super simple to understand the process, help improve API consistency when the translations are being delegated by the backend and make the whole process less error proof.
-
There is a term in the manufacturing world in quality management systems for "error-proofing" called poka-yoke. Error-proofing would essentially translate to Developer Experience :)
In summary
This feature would lead to more consistent, less error prone, less boilerplate and less cognitive load while working with front-end translation, and also make it very easy to delegate translations from the backend while making enabling more anti-fragile API testing.
I think this feature can be added without compatibility issues by enabling something like this for the key notation:
trans.key("otp.exceptions.username_not_found", ...)
And for the const objects, just generating that code in addition to the uppercase consts:
const otp = {
field : {
label: OTP_FIELD_LABEL
},
exceptions: {
username_not_found: OTP_EXCEPTIONS_USERNAME_NOT_FOUND
}
};
import {trans, otp } from '../../../translator';
...
trans(otp.exceptions.username_not_found);
...
trans(otp.field.label);