线上nextjs前端发出来的请求没有正确匹配到后端(nginx与nextjs 中的rewrites和bathPath)

391 阅读3分钟

问题描述:线上nextjs前端发出来的请求没有正确匹配到后端

就是得通过rewrites来配置

image.png 这个是在模拟线上环境

当我在服务器单独自己一个端口的时候 从我的localhost 发出来的请求是http://localhost:3000/myapi/login 然后通过rewrites会把http://localhost:3000/myapi/login 去掉/myapi/ 来到 http://server/api/login

为什么后端配置完子路由 就不能去掉/myapi/然后把域名替换成env里面的后端呢 也就是rewrites没有起到作用

没有跑我的next config

配置子路由是通过nginx 代理,检测到 URL 是 admin 开头则将请求转发到我的服务(未重写 URL,保留 URL 中的 admin )

考虑是basePath的问题:

basePath为true就能够将所有路由自动加上基础路径,但是在rewrites中配置basePath为true直接会报错 导致npm run dev崩溃退出

问rewrites是针对请求的路由还是页面路由 ? 请求匹配和页面路由都有

因为配置完子路由,rewrites没有起到作用,没有跑我的next config文件,就考虑是不是和Dockerfile文件有关,而这里前端部署在局域网的时候,在 Dockerfile里面没有涉及到next config文件,所以不是Dockerfile的问题

解决方法:

  1. 在axios中
const http = axios.create({ 
    baseURL: "/admin/myapi/",//这里要加上/admin 前缀,nginx才会转发这个请求到我的服务那里
    //然后我的服务里面的rewrites才会生效
    validateStatus: false,
    withCredentials: true,
    headers: {
        "Content-Type": `application/json`,
    },
});
  1. 在next.config.mjs中
const nextConfig = {
    basePath: '/admin',
    env: {
        HOST: process.env.HOST,
      },
    async rewrites() {
        return [
            {
                source: '/admin/myapi/:path*',//这里也要加上/admin前缀 这样子请求到我的服务之后才能去掉/admin/myapi/ 拼贴上env的地址
                destination: `${process.env.HOST}/:path*`,
                basePath:false
            }
        ]
    },

所以关键点是nginx这一块的知识点。

nginx中 我在服务器69端口跑了一个next前端项目,使用了反向代理,当浏览器访问这个项目的时候,请求第一个页面的document文件,要请求文件中含有的其他对象的时候,这个请求是由next项目发送出来的,如果axios里面的baseUrl没有/admin,在发起对其他对象的请求的时候,这个请求相当于是域名对应的项目发出来的,nginx直接导航到同事的项目去了,不会到我的项目来,所以rewrites没有起作用。

附上nginx基础:

Nginx

安装完Nginx 要访问页面的时候要引入event 和 http块

web服务器

http块内可以通过include引入外部文件 所以server块可以通过include引入

在server块中:

listen 80 因为浏览器一般通过80端口发请求

server_name 服务器地址

location:

root 匹配到的路径要导航到服务器中的哪个文件

redirect 做重定向 但是只能做单个文件的重定向

try_files 做整个文件夹的重定向

proxy_pass 反向代理 访问指定的路径就会去到指定端口运行的项目

proxy_set_header 是 Nginx 中代理请求时用于设置请求头的一个指令,通过它可以在请求转发过程中修改或添加 HTTP 头部信息,以帮助上游服务器更准确地了解客户端请求的细节。