Closed Yovach closed 6 months ago
Someone is attempting to deploy a commit to a Personal Account owned by @QuiiBz on Vercel.
@QuiiBz first needs to authorize it.
The latest updates on your projects. Learn more about Vercel for Git ↗︎
Name | Status | Preview | Comments | Updated (UTC) |
---|---|---|---|---|
next-international | ✅ Ready (Inspect) | Visit Preview | 💬 Add feedback | Dec 21, 2023 5:33pm |
Thanks for the update. Unfortunately adding back the artificial delay shows that we now have a loading state when switching locale in client components, which we don't want:
Screen.Recording.2023-12-23.at.08.57.47.mov I believe we'll need to add back the
localesCache
.use()
always triggers suspense so we should only use it when loading the page for the first time.
Based on your feedback, the I18nProvider
now checks if there's a cached value for the current locale
, otherwise it'll call the use
hook with the import and store the result in the localesCache
variable.
I've also added a check in changeLocale
to execute the call the import function only if the newLocale
is supported.
I think in the client.ts
, we can add a parameter here :
// locales/client.ts
export const { useI18n, useScopedI18n, I18nProviderClient, useChangeLocale, defineLocale, useCurrentLocale } =
createI18nClient(
{
en: async (isChanging: boolean = false) => { // <---- HERE
if (!isChanging) {
await new Promise(resolve => setTimeout(resolve, 100));
}
return import('./en');
},
fr: async (isChanging: boolean = false) => { // <---- HERE
if (!isChanging) {
await new Promise(resolve => setTimeout(resolve, 100));
}
return import('./fr');
},
},
{
// Uncomment to set base path
// basePath: '/base',
// Uncomment to use custom segment name
// segmentName: 'locale',
// Uncomment to set fallback locale
// fallbackLocale: en,
},
);
and in the
// packages/next-international/src/app/client/create-use-change-locale.ts
export function createUseChangeLocale<LocalesKeys>(
useCurrentLocale: () => LocalesKeys,
locales: ImportedLocales,
config: I18nClientConfig,
) {
return function useChangeLocale(changeLocaleConfig?: I18nChangeLocaleConfig) {
const { push, refresh } = useRouter();
const currentLocale = useCurrentLocale();
const path = usePathname();
// We call the hook conditionally to avoid always opting out of Static Rendering.
// eslint-disable-next-line react-hooks/rules-of-hooks
const searchParams = changeLocaleConfig?.preserveSearchParams ? useSearchParams().toString() : undefined;
const finalSearchParams = searchParams ? `?${searchParams}` : '';
let pathWithoutLocale = path;
if (config.basePath) {
pathWithoutLocale = pathWithoutLocale.replace(config.basePath, '');
}
if (pathWithoutLocale.startsWith(`/${currentLocale}/`)) {
pathWithoutLocale = pathWithoutLocale.replace(`/${currentLocale}/`, '/');
} else if (pathWithoutLocale === `/${currentLocale}`) {
pathWithoutLocale = '/';
}
return function changeLocale(newLocale: LocalesKeys) {
const importFnLocale = locales[newLocale as keyof typeof locales];
if (!importFnLocale) {
warn(`The locale '${newLocale}' is not supported.`);
return;
}
importFnLocale(true).then(module => { // <---- HERE
localesCache.set(newLocale as string, module.default);
push(`/${newLocale}${pathWithoutLocale}${finalSearchParams}`);
refresh();
});
};
};
}
As we don't need to wait for 100ms when changing the locale from the client
Closes #290
With this fix, I wasn't able to reproduce the crash.
What is this PR ?
It moves the call of
() => import("./en")
fromI18nProvider
toI18nProviderWrapper
.I changed this because according to the React documentation of
use
hook (https://react.dev/reference/react/use#streaming-data-from-server-to-client), the promise is executed and passed as a prop from the parent but awaited in the child.