Next实现国际化,接口反向代理,冲突了

最近在写next的项目,用到了国际化,使用了 react-i18next 但是感觉很费劲,配置起来很麻烦,所以换了一种方式,那就是:next-intl

发现还不错,后来要做接口,发现跨域,然后增加反向代理,则两者出现了冲突

国际化

第一步,需要安装

npm install next-intl

第二步,配置

import createNextIntlPlugin from 'next-intl/plugin';
const withNextIntl = createNextIntlPlugin();

/** @type {import('next').NextConfig} */
const nextConfig = {};
export default withNextIntl(nextConfig)

src 目录下创建 i18n-config.ts i18n.ts middleware.ts 文件 与 messages 目录

export const i18n = {
    defaultLocale: "en",
    locales: ["en", "zh"],
} as const;
export const locales = i18n.locales;
export const defaultLocale = i18n.defaultLocale;
import { notFound } from "next/navigation";
import { getRequestConfig } from 'next-intl/server';
import { locales } from '@/i18n-config'

export default getRequestConfig(async ({ locale }: any) => {
    if (!locales.includes(locale)) notFound();

    console.log(locale)
    return {
        messages: (await import(`./messages/${locale}.json`)).default
    };
});
import createMiddleware from 'next-intl/middleware';
import { locales, defaultLocale } from '@/i18n-config';

export default createMiddleware({
    locales,
    defaultLocale,
    // 默认语言不重定向
    localePrefix: 'as-needed'
});

export const config = {
    matcher: ['/((?!api|_next|_vercel|.*\\..*).*)']
};

在这里插入图片描述

messages目录结构

{
    "head": {
        "Login":"Login"
    }
}

项目结构:

在这里插入图片描述

要把以前写的页面 放到 [locale] 中,这样路由则会走 /语言/index

第三步:使用

服务端:

import {useTranslations} from 'next-intl';
export default function Page() {
  const t = useTranslations('Head');
  return (
    <div className="note--empty-state">
      <span className="note-text--empty-state">
        {t('login')}
      </span>
    </div>
  )
}
import {getTranslations} from 'next-intl/server';

export default async function Page() {
  const t = await getTranslations('Head');
  return (
    <div className="note--empty-state">
      <span className="note-text--empty-state">
        {t('initText')}
      </span>
    </div>
  )
}

客户端:

import {useTranslations} from 'next-intl';
export default function Sidebar() {
  const t = useTranslations('Head');
  return (
    <>
      <section className="col sidebar">
        <section className="sidebar-menu" role="menubar">
          <SidebarSearchField search={t('search')} />
          <EditButton noteId={null}>{t('new')}</EditButton>
        </section>
      </section>
    </>
  )
}

如果不能如期使用则需要在父组件增加 NextIntlClientProvider 传递message参数 完成该结果

// 部分代码省略
import { NextIntlClientProvider, useMessages } from "next-intl";

// 渲染部分

const RootLayout = ({
  children,
  params,
}: Readonly<{
  children: React.ReactNode;
  params: { lang: Locale };
}>) => {
  const messages = useMessages();
  return (
    <html lang={params.lang}>
      <body className={inter.className}>
        <Provider>
          <NextIntlClientProvider messages={{ head: messages.head }}>
            <LayoutHead ></LayoutHead>
            {children}
            <LayoutFoot></LayoutFoot>
          </NextIntlClientProvider>
        </Provider>
      </body>
    </html>
  );
}

接口反向代理

为了配置反向代理,我以为需要配置 proxy 才可以,next 则不需要,只需要更改重写规则即可。

/** @type {import('next').NextConfig} */
const nextConfig = {
    async rewrites() {
        return {
            fallback: [
                {
                    source: '/capi/:path*',
                    destination: `http://127.0.0.1:3000/:path*`,
                },
            ],
        }
    },
};
export default nextConfig;
import axios from 'axios'

let baseURL: string = "";
baseURL = "/capi"
// 拦截器
axios.interceptors.response.use((response) => {
    return response
}, (error) => {
    return Promise.reject(error)
})
axios.interceptors.request.use((config) => {
    console.log(config)
    config.headers['Accept'] = 'application/vnd.dpexpo.v1+json'
    config.baseURL = baseURL;
    config.timeout = 10000
    return config;
}, (error) => {
    return Promise.reject(error)
})

// axios的get请求
export function getAxios({
    url,
    params = {}
}: { url: string, params: any }) {
    return new Promise((resolve, reject) => {
        axios.get(url, {
            params,
        }).then(res => {
            resolve(res.data)
        }).catch(err => {
            console.log(err, '1')
            reject(err)
        })
    })
}

// axios的post请求
export function postAxios({
    url,
    data
}: any) {
    return new Promise((resolve, reject) => {
        axios({
            url,
            method: 'post',
            data
        }).then(res => {
            resolve(res.data)
        }).catch(err => {
            reject(err)
        })
    })
}

export default axios

import { getAxios, postAxios } from '@/utils/axios'

export const getArticle = (params: any) => {
    return getAxios({
        url: "/getArticleList",
        params
    })
}

请求 /getArticleList 则对应请求的是 /capi/getArticleList

重写规则,则重定向到 [http://127.0.0.1:3000](http://127.0.0.1:3000)/getArticleList

问题来了

现在都可以实现,但是两者结合,则会报错,请求404

那怎么办?

很简单

import createMiddleware from 'next-intl/middleware';
import { locales, defaultLocale } from '@/i18n-config';

export default createMiddleware({
    locales,
    defaultLocale,
    // 默认语言不重定向
    localePrefix: 'as-needed'
});

export const config = {
   //注意观察这一样的不同 多了capi 忽略了capi的路由
    matcher: ['/((?!api|_next|_vercel|capi|.*\\..*).*)']
};
  • 6
    点赞
  • 4
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: 可以在nginx配置中使用proxy_next_upstream指令来实现请求失败再反向代理一次的功能。具体配置如下: ``` http { upstream backend { server backend1; server backend2; } server { location / { proxy_pass http://backend; proxy_next_upstream error timeout; } } } ``` 在上述配置中,当请求后端服务器失败或超时时,nginx会自动尝试访问下一个服务器。如果所有的后端服务器都访问失败,则nginx会返回一个错误响应。这样就可以实现请求失败再反向代理一次的功能。 ### 回答2: 实现nginx反向代理处理的请求失败再反向代理一次的方法如下: 1. 配置nginx反向代理:首先需要在nginx的配置文件中设置反向代理的相关配置。通过使用`proxy_pass`指令将请求转发到后端服务。例如: ``` location / { proxy_pass http://backend; } ``` 上述配置将会将所有的请求转发到名为`backend`的后端服务。 2. 添加错误处理机制:在配置文件中添加错误处理的相关配置。使用`error_page`指令可以对不同类型的错误进行自定义处理。例如: ``` error_page 502 = @fallback; location @fallback { proxy_pass http://fallback_backend; } ``` 上述配置将会在发生502错误时,将请求转发到名为`fallback_backend`的后端服务。 3. 配置失败的反向代理:为了实现请求失败再次反向代理的功能,可以配置一个备用的后端服务。在发生错误时,将请求转发到该备用后端服务。例如: ``` upstream backend { server backend_server1; server backend_server2 backup; } ``` 上述配置中的`backend_server1`和`backend_server2`是两个后端服务的地址。其中`backend_server2`设置为`backup`类型,表示只有在前一个后端服务(`backend_server1`)不可用时才会使用`backend_server2`。 4. 重启nginx服务:修改完配置文件后,需要重启nginx服务使配置生效。使用命令`sudo service nginx restart`即可重启。 当一个后端服务出现故障或无法处理请求时,nginx会自动将请求转发到备用的后端服务。这样可以提高整个系统的可靠性和稳定性,确保请求能够得到处理和响应。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值