Vue3项目部署注意事项,特别是如果有路径分发,没有独立域名的情况,会遇到各种刷新404页面的问题,那怎么解决呢?
root和alias的区别
nginx配置文件中,指定静态资源路径时,root和alias的区别
路径拼接方式: 使用root时,location块中指定的URI将会直接拼接到root路径后面。而alias则会将location中匹配的部分路径替换为alias指定的路径。
适用场景: root适用于网站的广泛区域,常在server或location块中定义。alias适用于单独改变特定location的路径,适合更细粒度的路径控制。
举个例子:createWebHistory()模式
createWebHistory()模式是HTML5的模式,路由跳转没有#号,所以比较复杂,对于路径分发的话。
假设我们有个vue项目,因为生产环境没有独立的域名,所以只能用路径来跟别的项目做区分。假设我们分配的路径是/abc。那么我们要怎么部署呢?
1、打包
因为前面是用路径分发,所以最后浏览器访问肯定会带有/abc,比如
localhost/abc
那么里面路由切换也需要是有abc前缀,假设我们的vue项目有如下两个路由
<RouterLink to="/">Go to Home</RouterLink><br/>
<RouterLink to="/about">Go to About</RouterLink>
那么,我们的请求应该是
localhost/abc/
localhost/abc/about
如果不带上abc,那么刷新页面因为nginx配置路abc路径才能分发,就会找不到报404.因此打包的时候,必须指定根路径
const router = createRouter({
//history: createMemoryHistory(),
//history:createWebHashHistory(),//会带有#
history:createWebHistory("/abc"),//HTML5 模式 推荐
routes,
})
这里用的是HTML5模式,也就是没有#的,有机会再尝试其他模式。
另外,因为有前缀,所以静态资源的访问也要用相对路径,所以要修改vite.config.js
export default defineConfig({
plugins: [vue()],
base:"./",
})
这样就可以了。
2、alias的配置
alias会将location中匹配的部分路径替换为alias指定的路径,所以配置如下
location /abc {
alias F:\\Workspace\\html\\cesi;
try_files $uri $uri/ /abc/index.html;
index index.html index.htm;
}
这里我们把静态资源文件放到了F:\Workspace\html\cesi目录下,因为用的是alias,所以请求/abc想到于去该目录下找index.html。
try_files $uri $uri/ /abc/index.html;
这个的作用是,如果找不到,就找/abc/index.html。因为我们的vue项目是有路由的,如果不加上这个,路由到/abc/about路径后,刷新页面,F:\Workspace\html\cesi\about
下面是肯定没有index.html就会404.又因为是单页面应用,所以只要找不到我们就去唯一的目录下面找就可以了。
3、root的配置
使用root时,location块中指定的URI将会直接拼接到root路径后面。这种情况下肯定会带有/abc,所以我们直接把静态文件放在abc目录下
location /abc {
root F:\\Workspace\\html;
try_files $uri $uri/ /abc/index.html;
index index.html index.htm;
}
上面是在html下面建立abc目录,所以访问的时候也是可以找到去的,因为是用root,会自动拼上abc,所以下面的root配置不要写上abc
4、proxy转发
假设我们的静态资源是在容器的nginx服务启动的,如果我们想在当前的nginx根据路径分发,那么打包也要指定根路径,但是这里静态资源不能指定相对路径,因为下面的配置静态资源相当于是放在根/
下面的。然后启动的配置如下
server {
listen 8080;
server_name localhost;
location / {
root html;
try_files $uri $uri/ /index.html;
index index.html index.htm;
}
}
nginx启动后,访问是正常的,不管访问
http://localhost:8080/abc
http://localhost:8080/abc/
http://localhost:8080/abc/about
此时我们当前的nginx转发配置如下
location /abc {
set $path $1;
proxy_pass http://localhost:8080/;
proxy_set_header Host $host:$server_port;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
这样就可以了。
http://localhost/abc/
这种情况下不管proxy后面有没有/都没有关系,因为要代理的nginx里面以及处理了,就算没有也可以找到。
5、不用分发路径
那当然最简单啦,也不用搞什么相对路径,根路径。
举个例子:createWebHashHistory()模式
createWebHashHistory()模式是#的的模式,这种模式比较简单。
假设我们有个vue项目,因为生产环境没有独立的域名,所以只能用路径来跟别的项目做区分。假设我们分配的路径是/abc。那么我们要怎么部署呢?
1、打包
这里打包静态资源相对路径,毕竟前缀有abc
export default defineConfig({
plugins: [vue()],
base:"./",
})
但是路由不需要拼上abc,毕竟只是后面加上#
const router = createRouter({
//history: createMemoryHistory(),
history:createWebHashHistory(),//会带有#
//history:createWebHistory(),//HTML5 模式 推荐
routes,
})
2、alias模式
location /abc {
alias F:\\Workspace\\html\\cesi;
try_files $uri $uri/ /abc/index.html;
index index.html index.htm;
}
就可以了。
3、root模式
location /abc {
root F:\\Workspace\\html;
try_files $uri $uri/ /abc/index.html;
index index.html index.htm;
}
就可以了,但是静态资源要放html下面的abc目录下。
4、proxy模式
模仿容器nginx
server {
listen 8080;
server_name localhost;
location / {
root html;
try_files $uri $uri/ /index.html;
index index.html index.htm;
}
}
本地nginx
location /abc{
set $path $1;
proxy_pass http://localhost:8080;
proxy_set_header Host $host:$server_port;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
}
就可以了,然后我发现,打包静态资源用不用相对路径都可以.
总结
1、createWebHistory模式
alias和root,静态资源要相对路径,发布路径也需要,proxy静态资源不要指定相对路径,发布路要。
2、createWebHashHistory模式
alias和root,静态资源要相对路径,发布路径不需要,proxy静态资源想不相对都可以,发布路不需要。也就是说,这种模式只要你静态资源用相对路径,发布不路径不需要指定就可以了。
搞得这么麻烦,都是没有独立域名的锅,二级域名也好啊!