Skip to content

Commit

Permalink
add GetWebappTranslationCallback type (#27769)
Browse files Browse the repository at this point in the history
  • Loading branch information
mshima authored Nov 2, 2024
1 parent e0070d9 commit 6aaea8b
Show file tree
Hide file tree
Showing 11 changed files with 50 additions and 43 deletions.
5 changes: 3 additions & 2 deletions generators/angular/support/translate-angular.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
*/
import { inspect } from 'node:util';
import { beforeEach, describe, esmocha, expect, it } from 'esmocha';
import type { GetWebappTranslationCallback } from '../../../lib/types/base/translation.js';
import { createTranslationReplacer } from './translate-angular.js';

describe('generator - angular - transform', () => {
Expand All @@ -28,11 +29,11 @@ describe('generator - angular - transform', () => {
beforeEach(() => {
let value = 0;
const testImpl = (key, data) => (key === 'blank' ? '' : `translated-value-${key}-${data ? `${inspect(data)}-` : ''}${value++}`);
replaceAngularTranslations = createTranslationReplacer(esmocha.fn().mockImplementation(testImpl), {
replaceAngularTranslations = createTranslationReplacer(esmocha.fn<GetWebappTranslationCallback>().mockImplementation(testImpl), {
jhiPrefix: 'jhi',
enableTranslation: false,
});
enabledAngularTranslations = createTranslationReplacer(esmocha.fn().mockImplementation(testImpl), {
enabledAngularTranslations = createTranslationReplacer(esmocha.fn<GetWebappTranslationCallback>().mockImplementation(testImpl), {
jhiPrefix: 'jhi',
enableTranslation: true,
});
Expand Down
34 changes: 15 additions & 19 deletions generators/angular/support/translate-angular.ts
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ import {
escapeHtmlTranslationValue,
escapeTsTranslationValue,
} from '../../languages/support/index.js';
import type { GetWebappTranslationCallback } from '../../../lib/types/base/translation.js';

const PLACEHOLDER_REGEX = /(?:placeholder|title)=['|"](\{\{\s?['|"]([a-zA-Z0-9.\-_]+)['|"]\s?\|\s?translate\s?\}\})['|"]/.source;

Expand All @@ -50,7 +51,7 @@ export type ReplacerOptions = { jhiPrefix: string; enableTranslation: boolean };
* @returns {string}
*/
function replaceTranslationKeysWithText(
getWebappTranslation,
getWebappTranslation: GetWebappTranslationCallback,
content,
regexSource,
{
Expand Down Expand Up @@ -81,7 +82,7 @@ function replaceTranslationKeysWithText(
* @param {string} jsKey
* @returns string with jsKey value replaced
*/
function replaceJSTranslation(getWebappTranslation, content, jsKey) {
function replaceJSTranslation(getWebappTranslation: GetWebappTranslationCallback, content, jsKey) {
return replaceTranslationKeysWithText(
getWebappTranslation,
content,
Expand All @@ -98,23 +99,18 @@ function replaceJSTranslation(getWebappTranslation, content, jsKey) {
* @param {string} content html content
* @returns string with pageTitle replaced
*/
function replacePageTitles(getWebappTranslation, content) {
function replacePageTitles(getWebappTranslation: GetWebappTranslationCallback, content) {
return replaceJSTranslation(getWebappTranslation, content, 'title');
}

/**
* @type {function(import('../generator-base.js'), string): string}
*/
function replacePlaceholders(getWebappTranslation, content) {
function replacePlaceholders(getWebappTranslation: GetWebappTranslationCallback, content) {
return replaceTranslationKeysWithText(getWebappTranslation, content, PLACEHOLDER_REGEX, { keyIndex: 2 });
}

/**
* Replace error code translation key with translated message
*
* @type {function(import('../generator-base.js'), string): string}
*/
function replaceErrorMessage(getWebappTranslation, content) {
function replaceErrorMessage(getWebappTranslation: GetWebappTranslationCallback, content) {
return replaceJSTranslation(getWebappTranslation, content, 'errorMessage');
}

Expand All @@ -123,7 +119,7 @@ function replaceErrorMessage(getWebappTranslation, content) {
* Or the translation value if translation is disabled.
*/
const tagTranslation = (
getWebappTranslation: any,
getWebappTranslation: GetWebappTranslationCallback,
{ enableTranslation, jhiPrefix }: ReplacerOptions,
{ key, parsedInterpolate, prefix, suffix }: JHITranslateConverterOptions,
) => {
Expand All @@ -149,7 +145,7 @@ const tagTranslation = (
* Or the translation value if translation is disabled.
*/
const validationTagTranslation = (
getWebappTranslation: any,
getWebappTranslation: GetWebappTranslationCallback,
{ enableTranslation, jhiPrefix }: ReplacerOptions,
{ key, parsedInterpolate, prefix, suffix }: JHITranslateConverterOptions,
) => {
Expand All @@ -175,7 +171,7 @@ const validationTagTranslation = (
* Or the translation value if translation is disabled.
*/
const tagPipeTranslation = (
getWebappTranslation: any,
getWebappTranslation: GetWebappTranslationCallback,
{ enableTranslation, jhiPrefix }: ReplacerOptions,
{ key, parsedInterpolate, prefix, suffix }: JHITranslateConverterOptions,
) => {
Expand All @@ -201,7 +197,7 @@ const tagPipeTranslation = (
* Or the translation value if translation is disabled.
*/
const tagEnumTranslation = (
getWebappTranslation: any,
getWebappTranslation: GetWebappTranslationCallback,
{ enableTranslation, jhiPrefix }: ReplacerOptions,
{ key, parsedInterpolate, prefix, suffix }: JHITranslateConverterOptions,
) => {
Expand All @@ -222,7 +218,7 @@ const tagEnumTranslation = (
* Or the translation value if translation is disabled.
*/
const pipeTranslation = (
getWebappTranslation: any,
getWebappTranslation: GetWebappTranslationCallback,
{ enableTranslation }: ReplacerOptions,
{ key, prefix, suffix }: JHITranslateConverterOptions,
) => {
Expand All @@ -237,7 +233,7 @@ const pipeTranslation = (
* Get translation value.
*/
const valueTranslation = (
getWebappTranslation: any,
getWebappTranslation: GetWebappTranslationCallback,
_replacerOptions: ReplacerOptions,
{ filePath, key, prefix, suffix }: JHITranslateConverterOptions,
) => {
Expand All @@ -256,7 +252,7 @@ const valueTranslation = (
* Or the translation value if translation is disabled.
*/
const pipeEnumTranslation = (
getWebappTranslation: any,
getWebappTranslation: GetWebappTranslationCallback,
{ enableTranslation }: ReplacerOptions,
{ key, parsedInterpolate, prefix, suffix }: JHITranslateConverterOptions,
) => {
Expand All @@ -274,7 +270,7 @@ const pipeEnumTranslation = (

const replaceImplementations: Record<
string,
(getWebappTranslation: any, replacerOpts: ReplacerOptions, translateOpts: JHITranslateConverterOptions) => string
(getWebappTranslation: GetWebappTranslationCallback, replacerOpts: ReplacerOptions, translateOpts: JHITranslateConverterOptions) => string
> = {
Tag: tagTranslation,
TagPipe: tagPipeTranslation,
Expand All @@ -291,7 +287,7 @@ const replaceImplementations: Record<
* @type {import('../generator-base.js').EditFileCallback}
* @this {import('../generator-base.js')}
*/
export const createTranslationReplacer = (getWebappTranslation, opts: ReplacerOptions | boolean) => {
export const createTranslationReplacer = (getWebappTranslation: GetWebappTranslationCallback, opts: ReplacerOptions | boolean) => {
const htmlJhiTranslateReplacer = createJhiTransformTranslateReplacer(getWebappTranslation, { escapeHtml: true });
const htmlJhiTranslateStringifyReplacer = createJhiTransformTranslateStringifyReplacer(getWebappTranslation);
let translationReplacer: ((content: string, filePath: string) => string) | undefined;
Expand Down
3 changes: 2 additions & 1 deletion generators/base/types.d.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import type { Entity } from '../base-application/index.js';
import type { ExportControlPropertiesFromCommand } from '../../lib/command/index.js';
import type { GetWebappTranslationCallback } from '../../lib/types/base/translation.js';
import type command from './command.ts';

type BaseApplicationControlProperties = ExportControlPropertiesFromCommand<typeof command>;
Expand All @@ -24,5 +25,5 @@ export type Control = BaseApplicationControlProperties & {
* cleanupFiles({ '6.0.0': ['file1', 'file2', [application.shouldRemove, 'file3']] })
*/
cleanupFiles: (cleanup: Record<string, (string | [boolean, ...string[]])[]>) => Promise<void>;
getWebappTranslation?: (s: string, data?: Record<string, any>) => string;
getWebappTranslation?: GetWebappTranslationCallback;
};
2 changes: 1 addition & 1 deletion generators/languages/generator.ts
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,7 @@ const { NO: NO_CLIENT_FRAMEWORK, ANGULAR } = clientFrameworkTypes;
export default class LanguagesGenerator extends BaseApplicationGenerator {
askForMoreLanguages!: boolean;
askForNativeLanguage!: boolean;
translationData;
translationData: TranslationData;
supportedLanguages;
languages;
/**
Expand Down
10 changes: 6 additions & 4 deletions generators/languages/support/translate.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import type { GetWebappTranslationCallback } from '../../../lib/types/base/translation.js';

const TRANSLATE_FUNCTION_ARGS = /\(\s*'(?<key>[^']+)'(?:,\s*(?<interpolate>\{(?:(?!\}\))[\s\S])*\}))?\)/gs.source;

Expand All @@ -36,7 +37,7 @@ export type TranslationReplaceOptions = {
};

export const replaceTranslationKeysWithText = (
getWebappTranslation,
getWebappTranslation: GetWebappTranslationCallback,
body: string,
regexp: string,
{ keyPattern, interpolatePattern, wrapTranslation, escapeHtml, stringify }: TranslationReplaceOptions = {},
Expand Down Expand Up @@ -91,10 +92,11 @@ export const replaceTranslationKeysWithText = (
return body;
};

export const createJhiTransformTranslateReplacer = (getWebappTranslation, translateOptions?: TranslationReplaceOptions) => (body: string) =>
replaceTranslationKeysWithText(getWebappTranslation, body, `__jhiTransformTranslate__${TRANSLATE_FUNCTION_ARGS}`, translateOptions);
export const createJhiTransformTranslateReplacer =
(getWebappTranslation: GetWebappTranslationCallback, translateOptions?: TranslationReplaceOptions) => (body: string) =>
replaceTranslationKeysWithText(getWebappTranslation, body, `__jhiTransformTranslate__${TRANSLATE_FUNCTION_ARGS}`, translateOptions);

export const createJhiTransformTranslateStringifyReplacer = getWebappTranslation => (body: string) =>
export const createJhiTransformTranslateStringifyReplacer = (getWebappTranslation: GetWebappTranslationCallback) => (body: string) =>
replaceTranslationKeysWithText(getWebappTranslation, body, `__jhiTransformTranslateStringify__${TRANSLATE_FUNCTION_ARGS}`, {
stringify: true,
});
Expand Down
2 changes: 1 addition & 1 deletion generators/react/generator.ts
Original file line number Diff line number Diff line change
Expand Up @@ -142,7 +142,7 @@ export default class ReactGenerator extends BaseApplicationGenerator {
filter: file => isFileStateModified(file) && file.path.startsWith(this.destinationPath()) && isTranslatedReactFile(file),
refresh: false,
},
translateReactFilesTransform(control.getWebappTranslation),
translateReactFilesTransform(control.getWebappTranslation!),
);
}
},
Expand Down
9 changes: 4 additions & 5 deletions generators/react/support/translate-react.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
* limitations under the License.
*/
import { beforeEach, describe, esmocha, expect, it } from 'esmocha';
import type { GetWebappTranslationCallback } from '../../../lib/types/base/translation.js';
import { createTranslationReplacer } from './translate-react.js';

describe('generator - react - transform', () => {
Expand All @@ -25,11 +26,9 @@ describe('generator - react - transform', () => {
beforeEach(() => {
let value = 0;
replaceReactTranslations = createTranslationReplacer(
esmocha.fn().mockImplementation((key, interpolation = '') => {
if (interpolation) {
interpolation = `-${JSON.stringify(interpolation)}`;
}
return `${key}${interpolation}-translated-value-${value++}`;
esmocha.fn<GetWebappTranslationCallback>().mockImplementation((key, interpolation) => {
const stringifiedInterpolation = interpolation ? `-${JSON.stringify(interpolation)}` : '';
return `${key}${stringifiedInterpolation}-translated-value-${value++}`;
}),
);
});
Expand Down
7 changes: 4 additions & 3 deletions generators/react/support/translate-react.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
*/
import { passthrough } from '@yeoman/transform';
import { Minimatch } from 'minimatch';
import type { GetWebappTranslationCallback } from '../../../lib/types/base/translation.js';

const TRANSLATE_IMPORT_1 = /import { ?[T|t]ranslate(?:, ?[T|t]ranslate)? ?} from 'react-jhipster';?/.source; // Translate imports
const TRANSLATE_IMPORT_2 = / *[T|t]ranslate,|, ?[T|t]ranslate/.source; // Translate import
Expand All @@ -33,7 +34,7 @@ const TRANSLATE_TAG = `<Translate\\s*(?:(?:${COMPONENT_ATTRIBUTE}|${INTERPOLATE_
type Options = { keyPattern?: string; interpolatePattern?: string; wrapTranslation?: string | string[]; escapeHtml?: boolean };

const replaceTranslationKeysWithText = (
getWebappTranslation,
getWebappTranslation: GetWebappTranslationCallback,
body: string,
regexp: string,
{ keyPattern, interpolatePattern, wrapTranslation, escapeHtml }: Options = {},
Expand Down Expand Up @@ -106,7 +107,7 @@ const replaceTranslationKeysWithText = (
*
* @return {import('../../base/api.js').EditFileCallback}
*/
export const createTranslationReplacer = getWebappTranslation =>
export const createTranslationReplacer = (getWebappTranslation: GetWebappTranslationCallback) =>
function replaceReactTranslations(body: string, filePath: string) {
if (filePath.endsWith('.tsx')) {
body = body.replace(new RegExp(TRANSLATE_IMPORT, 'g'), '');
Expand All @@ -124,7 +125,7 @@ export const createTranslationReplacer = getWebappTranslation =>
const minimatch = new Minimatch('**/*.tsx');
export const isTranslatedReactFile = file => minimatch.match(file.path);

const translateReactFilesTransform = getWebappTranslation => {
const translateReactFilesTransform = (getWebappTranslation: GetWebappTranslationCallback) => {
const translate = createTranslationReplacer(getWebappTranslation);
return passthrough(file => {
file.contents = Buffer.from(translate(file.contents.toString(), file.path));
Expand Down
3 changes: 2 additions & 1 deletion generators/vue/support/translate-vue.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@
*/
import { inspect } from 'node:util';
import { describe, expect, it } from 'esmocha';
import type { GetWebappTranslationCallback } from '../../../lib/types/base/translation.js';
import { removeDeclarations, replaceTranslationTags, replaceTranslations } from './translate-vue.js';

const FULL_BODY = `
Expand Down Expand Up @@ -52,7 +53,7 @@ const FULL_BODY = `
<label class="form-control-label" v-text="t$('jhipsterVueApp.mapsIdGrandchildEntityWithoutDTO.date')" for="maps-id-grandchild-entity-without-dto-date">Date</label>
`;
const getWebappTranslation = (s, data) => `getWebappTranslation('${s}'${data ? `, ${inspect(data)}` : ''})`;
const getWebappTranslation: GetWebappTranslationCallback = (s, data) => `getWebappTranslation('${s}'${data ? `, ${inspect(data)}` : ''})`;

describe('generator - vue - transform', () => {
describe('removeDeclarations', () => {
Expand Down
17 changes: 11 additions & 6 deletions generators/vue/support/translate-vue.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,10 +19,15 @@
import { passthrough } from '@yeoman/transform';
import { Minimatch } from 'minimatch';
import type CoreGenerator from '../../base-core/index.js';
import type { GetWebappTranslationCallback } from '../../../lib/types/base/translation.js';

type GetWebappTranslation = (s: string, data?: Record<string, any>) => string;

function replaceTranslationAttributes({ content, getWebappTranslation }: { content: string; getWebappTranslation: GetWebappTranslation }) {
function replaceTranslationAttributes({
content,
getWebappTranslation,
}: {
content: string;
getWebappTranslation: GetWebappTranslationCallback;
}) {
return content.replaceAll(/:(?<tag>(?:placeholder|title|label))="(?<translate>t\$\([^"]+\))"/g, (_complete, ...args) => {
const groups: Record<string, string> = args.pop();
if (groups.translate.includes('+')) {
Expand All @@ -49,7 +54,7 @@ export function replaceTranslationTags(
}: {
body: string;
enableTranslation: boolean;
getWebappTranslation: GetWebappTranslation;
getWebappTranslation: GetWebappTranslationCallback;
},
) {
body = body.replaceAll(
Expand Down Expand Up @@ -93,7 +98,7 @@ export function replaceTranslations({
}: {
content: string;
type: 'vue' | 'ts';
getWebappTranslation: GetWebappTranslation;
getWebappTranslation: GetWebappTranslationCallback;
}) {
const regex =
type === 'ts'
Expand Down Expand Up @@ -155,7 +160,7 @@ function translateVueFilesTransform(
getWebappTranslation,
}: {
enableTranslation: boolean;
getWebappTranslation: GetWebappTranslation;
getWebappTranslation: GetWebappTranslationCallback;
},
) {
return passthrough(file => {
Expand Down
1 change: 1 addition & 0 deletions lib/types/base/translation.d.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export type GetWebappTranslationCallback = (s: string, data?: Record<string, any>) => string;

0 comments on commit 6aaea8b

Please sign in to comment.