-
-
Notifications
You must be signed in to change notification settings - Fork 110
Add locale-aware date formatting for UI dates #471
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
base: main
Are you sure you want to change the base?
Conversation
| return format(date, 'MMM dd', { | ||
| locale: getSupportedLanguages().find((lang) => lang.code === todayTranslation.usedLng) | ||
| ?.dateLocale, | ||
| }); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I suppose we could just use new Intl.DateTimeFormat(todayTranslation.usedLng, {day: '2-digit', month: 'short'}).format(date)?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I tried that, but this Intl API is kind of weird. At least for pt-BR and pt-PT, the results are awful, so I'm not sure what other languages would look like to native speakers.
pt-PT:
I don't know why it would format "short" month to "11" (we have "numeric" for that, right?).
pt-BR:
The word "de" here is just a preposition that we can totally ignore when we want it to be shorter.
Maybe we could have a specific function only for this expense date prefix and use the Intl for other places, which would probably make this look better:
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not a native speaker in either of these, but maybe it is simply the proper way to format this in Portugal? For the brazilian version, yeah it looks kind of bad.
Personally I would prefer fixing locale specific edge cases rather than to import the bulky date-fns locale and pass it around.
For the expense list, we could format the day and month separately and remove dots for now?
new Intl.DateTimeFormat('pt-PT', {month: 'short'}).format(new Date()).replace('.', '')Actually returns the month name, so we could just built this in a consistent format. What do you think?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Formatting day and month separately makes sense.
Do we need to care about the order, though? Some locales use MM/DD, others DD/MM.
There’s a way to detect that order if we really want to (expand for an example)
function formatDayMonth(locale: string, date: Date): string {
// Format day and short month separately
const day = new Intl.DateTimeFormat(locale, { day: 'numeric' }).format(date);
const monthName = new Intl.DateTimeFormat(locale, { month: 'short' }).format(date)
.replace('.', '');
// Detect whether day comes before month for this locale
const orderParts = new Intl.DateTimeFormat(locale, {
day: 'numeric',
month: 'numeric'
}).formatToParts(date);
const dayIndex = orderParts.findIndex(p => p.type === 'day');
const monthIndex = orderParts.findIndex(p => p.type === 'month');
const isDayFirst = dayIndex < monthIndex;
return isDayFirst ? `${day} ${monthName}` : `${monthName} ${day}`;
}
// Examples:
formatDayMonth('pt-BR', new Date('2025-10-11'));
// "11 out"
formatDayMonth('pt-PT', new Date('2025-10-11'));
// "11 out"
formatDayMonth('de', new Date('2025-10-11'));
// "11 Okt"
formatDayMonth('en-GB', new Date('2025-10-11'))
// "11 Oct"
formatDayMonth('en-US', new Date('2025-10-11'));
// "Oct 11"
formatDayMonth('en', new Date('2025-10-11'));
// "Oct 11"
formatDayMonth('zh', new Date('2025-10-11'))
// "10月 11日"Feels a bit over-engineered, but it works. In pt-BR I wouldn't mind if it stayed as "MM DD", since the layout stacks them on top of each other in the expense list. Not sure how that reads in other locales... |
What do you think? We just keep "MM DD" specifically in the expenses list for now? In that case, the following should be enough:
const day = new Intl.DateTimeFormat(todayTranslation.usedLng, { day: 'numeric' }).format(date);
const monthName = new Intl.DateTimeFormat(todayTranslation.usedLng, { month: 'short' }).format(date).replace('.', '');
return `${monthName} ${day}`;There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looks good to me. One change would be to change day to 2-digit maybe?



Description
Adds locale-aware dates, fixes #470.
Demo
Checklist
CONTRIBUTING.mdin its entirety