-
Notifications
You must be signed in to change notification settings - Fork 2.9k
feat(i18n): localize tool display names in TUI and web-shell badges #5220
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
a79be46
dc70552
fc477df
8dccb17
a6156f8
0122df4
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -153,3 +153,59 @@ describe('supported language resolution', () => { | |
| expect(resolveSupportedLanguage('zh-HK')).toBe('zh'); | ||
| }); | ||
| }); | ||
|
|
||
| describe('localizeToolDisplayName', () => { | ||
| beforeEach(() => { | ||
| vi.resetModules(); | ||
| }); | ||
|
|
||
| it('translates tool badges without colliding with generic UI strings', async () => { | ||
| const { setLanguageAsync, localizeToolDisplayName, t } = await import( | ||
| './index.js' | ||
| ); | ||
| await setLanguageAsync('zh'); | ||
|
|
||
| // The namespaced `toolDisplayName.*` key translates the badge... | ||
| expect(localizeToolDisplayName('Shell')).toBe('运行命令'); | ||
| expect(localizeToolDisplayName('TodoWrite')).toBe('任务清单'); | ||
| // Proper tool names / acronyms are intentionally kept in English. | ||
| expect(localizeToolDisplayName('Agent')).toBe('Agent'); | ||
| expect(localizeToolDisplayName('Grep')).toBe('Grep'); | ||
| expect(localizeToolDisplayName('Glob')).toBe('Glob'); | ||
| expect(localizeToolDisplayName('Lsp')).toBe('LSP'); | ||
| // ...while a same-spelled standalone UI string keeps its own value. | ||
| expect(t('Shell')).toBe('Shell'); | ||
| }); | ||
|
|
||
| it('falls back to the English display name for untranslated tools', async () => { | ||
| const { setLanguageAsync, localizeToolDisplayName } = await import( | ||
| './index.js' | ||
| ); | ||
| await setLanguageAsync('en'); | ||
|
|
||
| expect(localizeToolDisplayName('TodoWrite')).toBe('TodoWrite'); | ||
| expect(localizeToolDisplayName('Shell')).toBe('Shell'); | ||
| // An unknown tool name passes through unchanged. | ||
| expect(localizeToolDisplayName('MysteryTool')).toBe('MysteryTool'); | ||
| }); | ||
|
|
||
| it('has a zh translation for every core tool display name', async () => { | ||
|
Collaborator
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. [Suggestion] The completeness test validates Consider adding a parallel test: it('has a zh-TW translation for every core tool display name', async () => {
const { setLanguageAsync, localizeToolDisplayName } = await import('./index.js');
const { ToolDisplayNames } = await import('@qwen-code/qwen-code-core');
const { SHELL_COMMAND_NAME } = await import('../../ui/constants.js');
await setLanguageAsync('zh-TW');
const names = [...Object.values(ToolDisplayNames), SHELL_COMMAND_NAME];
const untranslated = names.filter(
(name) => localizeToolDisplayName(name) === name,
);
expect(untranslated).toEqual([]);
});— qwen3.7-max via Qwen Code /review |
||
| const { setLanguageAsync, localizeToolDisplayName } = await import( | ||
| './index.js' | ||
| ); | ||
| const { ToolDisplayNames } = await import('@qwen-code/qwen-code-core'); | ||
| await setLanguageAsync('zh'); | ||
|
|
||
| // Guards against a new tool landing without a `toolDisplayName.*` entry: | ||
| // every English display name (except the intentionally-English ones below) | ||
| // must resolve to a different (translated) zh string. check-i18n can't catch | ||
| // this because the keys are built dynamically, never as | ||
| // `t('toolDisplayName.X')` string literals. | ||
| const KEEP_ENGLISH = new Set(['Agent', 'Grep', 'Glob']); | ||
| const untranslated = Object.values(ToolDisplayNames).filter( | ||
| (name) => | ||
| !KEEP_ENGLISH.has(name) && localizeToolDisplayName(name) === name, | ||
| ); | ||
| expect(untranslated).toEqual([]); | ||
| }); | ||
| }); | ||
Uh oh!
There was an error while loading. Please reload this page.