接前篇:Nginx+Tomcat实现Web服务器的负载均衡
采用Nginx的反向代理搭建了一个负载均衡的web服务器,然后部署了一套自己的web应用,在使用中呢,还是发现了一些问题:
自己的应用采用前后的端分离开发,后端用java编写,前端使用VUE开发,而搭建的负载均衡,实际上是对前端的负载均衡,后台java还是一个单独的服务器运行的,这里只看vue的前端

项目正常访问地址 http://10.50.200.66:11180 完全没有问题,正常登录,正常使用
比如,正常登录首页,展示:
应用登录首页
但是如果,对应用浏览器刷新(F5)的时候,就会发现有问题了,浏览器提示404异常:
vue刷新异常
其实这问题主要在于VUE,当vue项目的vue-router的mode为history路由模式时,若服务器未进行相应的配置,就会发生这种情况。

前端路由,即由前端来维护一个路由规则。实现有两种,一种时利用url的hash,也就是常说的锚点(#),JS通过hashChange事件来监听url的改变,IE7及以下需要轮询;另一种是HTML5的History模式,它使url看起来像普通网站那样,以“/”分割,没有#,但页面并没有跳转,不过使用这种模式需要服务端的支持,服务端在接受到所有请求后,都指向index.html文件,或设置404页面为index.html。不然刷新时页面会出现404。1

那怎么解决呢?

其实也比较简单,一种是不要使用history模式,但是不推荐这样做!另一种,就是把自己的vue项目copy一份放到nginx服务器的应用目录下,配置nginx,在访问不到其他地址,如上图 /nfs-qd/main/home这样的地址的时候,强制映射到vue单页应用项目的index.html即可。
具体如下,修改nginx配置

server {
    listen       80;
    server_name  localhost;

    #charset koi8-r;
    #access_log  /var/log/nginx/host.access.log  main;

    location / {
        # 将访问请求转向至服务器集群,mycluster和http中upstream mycluster 对应
        proxy_pass http://mycluster;
        # nginx服务器本身的应用服务路径,把自己的vue应用copy一份到这个路径下
        root   /usr/share/nginx/html;
        index  index.html index.htm;
        # URL 匹配不到任何静态资源,就强映射到本地应用的index.html,这样就解决了页面刷新404问题
        try_files $uri $uri/ /index.html;
    }

    #error_page  404              /404.html;

    # redirect server error pages to the static page /50x.html
    #
    error_page   500 502 503 504  /50x.html;
    location = /50x.html {
        root   /usr/share/nginx/html;
    }
}

这样配置还有一个好处

nginx服务器本身也能提供资源服务了,前篇简单nginx反向代理的时候,客户端并不知道nginx服务器资源是否其本身提供还是nginx服务器请求其他服务器提供的,这里nginx服务器仍然是反向代理,同时它也提供web资源;
另外nginx在没有配置本身的服务功能时候,vue项目的favicon.ico图标在客户端访问nginx服务器是访问不到的,但是当配置nginx提供服务时候,这个问题也解决了。

另外还有一个要说的

上面是使用tomcat作为web容器对外提供服务,实际上没有必要,对应vue这样的单页应用没必要使用tomcat,使用前面说的apache http server就行,这个要比tomcat轻量,当然更好的还是使用nginx就行,它本身也能发布静态页应用,方法正如本文介绍的,在目录 /usr/shar/nginx/html下放入自己的vue单页应用即可,这样更好了!
之所以用tomcat,是为了将来的java后台服务提供web容器环境。

还有什么要说的?

有没有发现nginx做反向代理和负载均衡很简单?真的是这样吗?
前面有说到,上面演示的都是对vue前端做的负载均衡,这样真的有用吗?真正的压力是在前端吗?
好像不是,压力是在后台呀,java部分,后台只有那么一台服务器,所有前端的响应都是来自一台后台,真正要做的是对java后台负载均衡才对!
那么为什么不对java后台负载均衡呢?

那是后端不跟前台一样,有一个问题不解决,就无法负载均衡,那就是用户session的共享问题-- 一个用户在服务器A上登录后,经过负载均衡后,后面的请求可就不能还在服务器A上了,到了服务器B上,如何知道当前用户已经登录了,还是没登录呢?

关注博主,后续博文吧!



  1. 《Vue.js实战》 ↩︎

Logo

前往低代码交流专区

更多推荐