core-{app,plugin}-api: switch i18n JSX support to no longer requrie explicit format

Signed-off-by: Patrik Oldsberg <poldsberg@gmail.com>
This commit is contained in:
Patrik Oldsberg
2025-04-29 22:27:02 +02:00
parent b5733414ab
commit 0bc1804ce5
11 changed files with 237 additions and 157 deletions
@@ -94,6 +94,52 @@ describe('MockTranslationApi', () => {
expect(snapshot.t('foo', { qux: 'Deep' })).toBe('Foo Nested Baz Deep');
});
it('should support jsx interpolation', () => {
const snapshot = snapshotWithMessages({
empty: 'derp',
jsx: '={{ x }}',
jsxNested: '={{ x.y.z }}',
jsxDeep: '<$t(jsx)>',
});
expect(snapshot.t('jsx', { x: <h1>hello</h1> })).toMatchInlineSnapshot(`
<React.Fragment>
=
<h1>
hello
</h1>
</React.Fragment>
`);
expect(snapshot.t('jsx', { replace: { x: <h1>hello</h1> } }))
.toMatchInlineSnapshot(`
<React.Fragment>
=
<h1>
hello
</h1>
</React.Fragment>
`);
expect(
snapshot.t('jsxNested', { replace: { x: { y: { z: <h1>hello</h1> } } } }),
).toMatchInlineSnapshot(`
<React.Fragment>
=
<h1>
hello
</h1>
</React.Fragment>
`);
expect(snapshot.t('jsxDeep', { x: <h1>hello</h1> })).toMatchInlineSnapshot(`
<React.Fragment>
&lt;=
<h1>
hello
</h1>
&gt;
</React.Fragment>
`);
});
it('should support formatting', () => {
const snapshot = snapshotWithMessages({
plain: '= {{ x }}',
@@ -104,8 +150,6 @@ describe('MockTranslationApi', () => {
relativeSecondsShort:
'= {{ x, relativeTime(range: second; style: short) }}',
list: '= {{ x, list }}',
jsx: '={{ x, jsx }}',
nestedJsx: '<$t(jsx)>',
});
expect(snapshot.t('plain', { x: '5' })).toBe('= 5');
@@ -148,19 +192,6 @@ describe('MockTranslationApi', () => {
expect(snapshot.t('list', { x: ['a'] })).toBe('= a');
expect(snapshot.t('list', { x: ['a', 'b'] })).toBe('= a and b');
expect(snapshot.t('list', { x: ['a', 'b', 'c'] })).toBe('= a, b, and c');
expect(snapshot.t('jsx', { x: 'hello' })).toMatchInlineSnapshot(`
<React.Fragment>
=
hello
</React.Fragment>
`);
expect(snapshot.t('nestedJsx', { x: 'hello' })).toMatchInlineSnapshot(`
<React.Fragment>
&lt;=
hello
&gt;
</React.Fragment>
`);
});
it('should support plurals', () => {
@@ -42,6 +42,8 @@ export class MockTranslationApi implements TranslationApi {
supportedLngs: [DEFAULT_LANGUAGE],
interpolation: {
escapeValue: false,
// Used for the JsxInterpolator format hook
alwaysFormat: true,
},
ns: [],
defaultNS: false,
@@ -56,8 +58,7 @@ export class MockTranslationApi implements TranslationApi {
throw new Error('i18next was unexpectedly not initialized');
}
const interpolator = JsxInterpolator.create({ marker: '123456' });
i18n.services.formatter?.add('jsx', interpolator.format);
const interpolator = JsxInterpolator.fromI18n(i18n);
return new MockTranslationApi(i18n, interpolator);
}
@@ -88,7 +89,7 @@ export class MockTranslationApi implements TranslationApi {
}
const t = this.#interpolator.wrapT<TMessages>(
this.#i18n.getFixedT(null, internalRef.id) as any,
this.#i18n.getFixedT(null, internalRef.id),
);
return {