我已按照此处提供的官方指南在 Next.js 14 应用程序中实现了国际化:https://nextjs.org/docs/app/building-your-application/routing/internationalization。该设置运行良好,使我能够通过 URL 参数访问服务器和客户端组件中的国际化。但是,我在将其集成到服务器操作中时遇到了问题。
具体来说,我正在使用使用 zod 进行验证的服务器操作。此操作验证表单输入并返回错误消息。现在,我需要集成国际化系统以提供特定于区域设置的错误消息。
以下是 Next.js 文档的摘录,说明了服务器操作设置:
'use server'
import { z } from 'zod'
const schema = z.object({
email: z.string({
invalid_type_error: 'Invalid Email', // <-- Need to integrate internationalization here
}),
})
export default async function createUser(formData: FormData) {
const validatedFields = schema.safeParse({
email: formData.get('email'),
})
// Return early if the form data is invalid
if (!validatedFields.success) {
return {
errors: validatedFields.error.flatten().fieldErrors,
}
}
// Mutate data
}
尽管进行了深入的研究,我还是找不到将国际化无缝集成到服务器操作中的解决方案。如果您能提供有关如何有效实现这一目标的见解或指导,我将不胜感激。谢谢!
我一直在努力解决同样的问题,并最终找到了解决方案。 我正在使用 https://next-intl-docs.vercel.app 包,NextJS 文档中也提到了该包。这是在服务器操作中使用的解决方法https://next-intl-docs.vercel.app/blog/translations-outside-of-react-components#the-exception-that-proves-the-rule
我更喜欢使用
NEXT_LOCALE
cookie 来存储每个请求的区域设置。所以我的 i18n 文件看起来像:
//i18n.ts
import {getRequestConfig} from 'next-intl/server';
import {cookies} from "next/headers";
export default getRequestConfig(async () => {
// here is the recognition of clients locale
const locale = cookies().get('NEXT_LOCALE')?.value ?? 'ua';
return {
locale,
messages: (await import(`../messages/${locale}.json`)).default
};
});
然后,在服务器操作文件中使用它就像
import { getTranslations } from 'next-intl/server';
export async function someAction(input) {
const t = await getTranslations();
return t('common.some_message'),
}
对于你的问题,我看到两种可能的解决方案:
'use server'
import { z } from 'zod'
import { getTranslations } from 'next-intl/server';
const schema = z.object({
email: z.string({
invalid_type_error: 'user.creation.invalid_email',
}),
})
export default async function createUser(formData: FormData) {
const validatedFields = schema.safeParse({
email: formData.get('email'),
})
// Return early if the form data is invalid
if (!validatedFields.success) {
const t = await getTranslations();
return {
errors: validatedFields.error..errors.map(e => {
return t(e.message);
}),
};
}
}