[codex] ユーザー画面の未翻訳箇所をi18n対応#2039
Conversation
📝 WalkthroughWalkthroughThis PR introduces comprehensive internationalization support for the Fire Equipment application feature and other UI components. Changes include adding English and Japanese translation entries in locale files, updating API types to support English names, replacing hardcoded Japanese strings with i18n translation keys across Fire Equipment components, and converting various UI components to use translation hooks instead of hardcoded text. Changes
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~20 minutes Possibly related PRs
Suggested reviewers
Poem
🚥 Pre-merge checks | ✅ 5✅ Passed checks (5 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches📝 Generate docstrings
🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Review rate limit: 0/1 reviews remaining, refill in 60 minutes.Comment |
There was a problem hiding this comment.
Actionable comments posted: 4
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Inline comments:
In
`@user/src/components/Applications/FireEquipment/components/FireEquipmentForm.tsx`:
- Around line 86-93: In FireEquipmentForm, the rendering of
fireEquipmentTexts.notes.takeaway only inserts a <br /> after the first split
line so multi-line translations collapse; update the map so a line break is
rendered after every line except the last (e.g., compare index to
takeaway.split('\n').length - 1 or join with interleaved <br />), ensuring
fireEquipmentTexts.notes.takeaway is split on '\n' and each line renders its
following <br /> when not the final element.
In `@user/src/components/Applications/FireEquipment/components/schema.ts`:
- Around line 25-29: The current validation only rejects empty-string remarks;
tighten the check in the schema where ctx.addIssue is called by validating
remarks for undefined/null and whitespace-only content: change the conditional
around data.isTakeaway/data.remarks to use a trimmed emptiness test (e.g.,
!data.remarks || data.remarks.trim() === '') before calling ctx.addIssue so
undefined or whitespace-only remarks also trigger the
'applications.fireEquipment.validation.remarkRequired' error on path
['remarks'].
In `@user/src/components/EditButton/EditButton.tsx`:
- Line 13: The EditButton component's <button> lacks an explicit type which
defaults to "submit" and can cause accidental form submissions; update the
button element in EditButton.tsx to include type="button" (while keeping the
existing className and onClick handler reference OnClick) so clicks only trigger
the OnClick callback and do not submit parent forms.
In `@user/src/icons/Icons.tsx`:
- Line 12: The loading container currently uses a plain div with aria-label
which doesn't guarantee SR announcement; update the loading node in Icons (the
div with className="flex justify-center") to be a proper live status region by
adding role="status" and aria-live="polite" (and optionally aria-busy="true")
while keeping the existing aria-label so screen readers announce the loading
state.
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: defaults
Review profile: CHILL
Plan: Pro
Run ID: 72b96d3e-f6e8-48b6-9af7-db2e06320517
📒 Files selected for processing (19)
user/public/locales/en/common.jsonuser/public/locales/ja/common.jsonuser/src/api/groupApi.tsuser/src/api/rentItemsApi.tsuser/src/components/Applications/FireEquipment/FireEquipment.tsxuser/src/components/Applications/FireEquipment/components/FireEquipmentForm.tsxuser/src/components/Applications/FireEquipment/components/FireEquipmentFormView.tsxuser/src/components/Applications/FireEquipment/components/hooks.tsuser/src/components/Applications/FireEquipment/components/schema.tsuser/src/components/Applications/FireEquipment/constant.tsuser/src/components/Applications/FireEquipment/hooks.tsuser/src/components/Applications/Stage/StageForm/StageForm.tsxuser/src/components/EditButton/EditButton.tsxuser/src/components/Form/TextArea/TextArea.tsxuser/src/components/LoginModal/schema.tsuser/src/components/UserModal/UserModal.tsxuser/src/components/UserModal/hooks.tsuser/src/icons/Icons.tsxuser/src/utils/constant.ts
| {fireEquipmentTexts.notes.takeaway | ||
| .split('\n') | ||
| .map((line, index) => ( | ||
| <span key={index}> | ||
| {line} | ||
| {index === 0 && <br />} | ||
| </span> | ||
| ) | ||
| )} | ||
| ))} |
There was a problem hiding this comment.
Handle all translated newline breaks, not just the first one.
Line 86-93 currently adds <br /> only after the first line. If a locale string has 3+ lines, later lines will run together.
💡 Proposed fix
- {fireEquipmentTexts.notes.takeaway
- .split('\n')
- .map((line, index) => (
- <span key={index}>
- {line}
- {index === 0 && <br />}
- </span>
- ))}
+ {fireEquipmentTexts.notes.takeaway
+ .split('\n')
+ .map((line, index, lines) => (
+ <span key={`${line}-${index}`}>
+ {line}
+ {index < lines.length - 1 && <br />}
+ </span>
+ ))}📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| {fireEquipmentTexts.notes.takeaway | |
| .split('\n') | |
| .map((line, index) => ( | |
| <span key={index}> | |
| {line} | |
| {index === 0 && <br />} | |
| </span> | |
| ) | |
| )} | |
| ))} | |
| {fireEquipmentTexts.notes.takeaway | |
| .split('\n') | |
| .map((line, index, lines) => ( | |
| <span key={`${line}-${index}`}> | |
| {line} | |
| {index < lines.length - 1 && <br />} | |
| </span> | |
| ))} |
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.
In
`@user/src/components/Applications/FireEquipment/components/FireEquipmentForm.tsx`
around lines 86 - 93, In FireEquipmentForm, the rendering of
fireEquipmentTexts.notes.takeaway only inserts a <br /> after the first split
line so multi-line translations collapse; update the map so a line break is
rendered after every line except the last (e.g., compare index to
takeaway.split('\n').length - 1 or join with interleaved <br />), ensuring
fireEquipmentTexts.notes.takeaway is split on '\n' and each line renders its
following <br /> when not the final element.
| if (!data.isTakeaway && data.remarks == '') { | ||
| ctx.addIssue({ | ||
| code: z.ZodIssueCode.custom, | ||
| message: '持ち帰りが「いいえ」の場合、備考欄は必須です', | ||
| message: 'applications.fireEquipment.validation.remarkRequired', | ||
| path: ['remarks'], |
There was a problem hiding this comment.
Tighten non-takeaway remark validation.
Line 25 only checks ''; undefined or whitespace-only remarks can bypass this requirement.
Suggested fix
- if (!data.isTakeaway && data.remarks == '') {
+ if (!data.isTakeaway && !data.remarks?.trim()) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: 'applications.fireEquipment.validation.remarkRequired',
path: ['remarks'],
});
}📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| if (!data.isTakeaway && data.remarks == '') { | |
| ctx.addIssue({ | |
| code: z.ZodIssueCode.custom, | |
| message: '持ち帰りが「いいえ」の場合、備考欄は必須です', | |
| message: 'applications.fireEquipment.validation.remarkRequired', | |
| path: ['remarks'], | |
| if (!data.isTakeaway && !data.remarks?.trim()) { | |
| ctx.addIssue({ | |
| code: z.ZodIssueCode.custom, | |
| message: 'applications.fireEquipment.validation.remarkRequired', | |
| path: ['remarks'], |
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.
In `@user/src/components/Applications/FireEquipment/components/schema.ts` around
lines 25 - 29, The current validation only rejects empty-string remarks; tighten
the check in the schema where ctx.addIssue is called by validating remarks for
undefined/null and whitespace-only content: change the conditional around
data.isTakeaway/data.remarks to use a trimmed emptiness test (e.g.,
!data.remarks || data.remarks.trim() === '') before calling ctx.addIssue so
undefined or whitespace-only remarks also trigger the
'applications.fireEquipment.validation.remarkRequired' error on path
['remarks'].
| const { t } = useTranslation('common'); | ||
|
|
||
| return ( | ||
| <button className="flex w-32 gap-3" onClick={OnClick}> |
There was a problem hiding this comment.
Set an explicit button type to prevent unintended form submits.
<button> defaults to submit, so this can trigger accidental form submission when rendered inside a form wrapper.
Suggested fix
- <button className="flex w-32 gap-3" onClick={OnClick}>
+ <button type="button" className="flex w-32 gap-3" onClick={OnClick}>📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| <button className="flex w-32 gap-3" onClick={OnClick}> | |
| <button type="button" className="flex w-32 gap-3" onClick={OnClick}> |
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.
In `@user/src/components/EditButton/EditButton.tsx` at line 13, The EditButton
component's <button> lacks an explicit type which defaults to "submit" and can
cause accidental form submissions; update the button element in EditButton.tsx
to include type="button" (while keeping the existing className and onClick
handler reference OnClick) so clicks only trigger the OnClick callback and do
not submit parent forms.
| const { t } = useTranslation('common'); | ||
|
|
||
| return ( | ||
| <div className="flex justify-center" aria-label={t('general.loading')}> |
There was a problem hiding this comment.
Add status semantics so screen readers announce the loading state.
On a plain div, aria-label is weak for announcement. Mark this as a live status region.
Suggested fix
- <div className="flex justify-center" aria-label={t('general.loading')}>
+ <div
+ className="flex justify-center"
+ role="status"
+ aria-live="polite"
+ aria-label={t('general.loading')}
+ >📝 Committable suggestion
‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.
| <div className="flex justify-center" aria-label={t('general.loading')}> | |
| <div | |
| className="flex justify-center" | |
| role="status" | |
| aria-live="polite" | |
| aria-label={t('general.loading')} | |
| > |
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.
In `@user/src/icons/Icons.tsx` at line 12, The loading container currently uses a
plain div with aria-label which doesn't guarantee SR announcement; update the
loading node in Icons (the div with className="flex justify-center") to be a
proper live status region by adding role="status" and aria-live="polite" (and
optionally aria-busy="true") while keeping the existing aria-label so screen
readers announce the loading state.
resolved #2033
概要
/userの未翻訳表示を既存のnext-i18next構成に合わせて i18n 化name_enを使うように修正背景
英語表示時にも一部の画面文言やマスタ名称が日本語のまま表示されていました。DB/fixture 側に用意されている英語名を使い、UI 文言は locale ファイルに集約しています。
補足
場所名は今年は日本語のままにする方針のため、翻訳対象から外しています。
Summary by CodeRabbit
Release Notes