通过OpenResty+Redis+MySQL+Lua脚本实现对首页轮播图的优化

 首先我们在没有使用任何的优化前提下,前端首页的响应时间大概在6秒钟,这在测试的人员看来,根据258原则,响应效率明显是有待提高的。这里简单的提一下什么是258原则:

2秒钟之内响应用户是非常好的。
2-5秒钟之内响应用户是可以接受的。
5-8秒钟是用户能接受的响应的上限。
>8秒钟是比较糟糕的,用户会选择离开这个Web站点或发起第二次请求。

我们6秒的响应时间已经岌岌可危了,因此需要进一步的优化;
第一次优化:加Redis缓存
优点:它的好处是减轻了数据库的并发压力,提高了查询的效率。
缺点:当然也有redis缓存的并发问题,这里就不细说了,见我的另一篇文章有详细的说明:Redsi缓存的并发问题。

大致的执行流程图:

绕过Tomcat 直接去OpenResty中的Nginx缓存中获取数据,Nginx先去redis缓存中读取;

这里更新缓存可以加一个socket编程方式去定时任务完成,就不具体说了。 

接下来说一下怎么使用OpenResty连接Redis服务和MysqL服务。

首先我们将Linux版本的Redis启动

进入Redis安装的src目录下 用启动命令启动服务:(带配置文件启动)

./redis-server ../redis.conf

 得到这个界面说明启动成功了

我们需要安装Lua;

Linux系统安装:

curl -R -O http://www.lua.org/ftp/lua-5.3.0.tar.gz
tar zxf lua-5.3.0.tar.gz
cd lua-5.3.0
make linux test
make install

这里就不多介绍Lua脚本了,接下来我们需要去已经安装好的OpenResty的Nginx目录的conf目录下新建一个lua文件夹;命令

mkdir lua

cd lua 进入文件夹 然后创建一个文件直接用 vim redis.lua 快捷新建文件

编写Lua脚本测试连接Redis

--测试连接redis的lua脚本
local redis = require "resty.redis"
local red = redis:new()
red.set_timeout(2000)
local ok, err = red:connect("192.168.64.200,6379")
if not ok then
    ngx.say("connect error: ", err)
    return
end
ngx.say("connected to redis successfully!")

提一下:连接ip是根据Redis是Linux话说windows来配置的,我的是在Linux下所以这是我的虚拟机的IP地址;

 编写完后我们 cd ..退出Nginx中 vim Nginx.conf  文件

添加一下配置:

     server{
        listen 8077;
        server_name localhost;
      location /redis {
        default_type text/html;
        charset utf-8;
        content_by_lua_file conf/lua/redis.lua;
        }
   }

配置端口名和访问地址 在文件的最下方添加即可。

保存后,出来重新启动Nginx

命令:

Nginx -s reload

然后去访问地址:"你的IP:端口/redis"

 连接成功!

接着是MysqL

同样的操作

创建lua脚本,进入编写模式:我用的是windows的MysqL 因此 测试连接时需要关闭Linux的防火墙

暂时关闭防火墙的命令:

systemctl stop firewalld
-- 测试连接MysqL的lua脚本
local MysqL = require "resty.MysqL"
local db = MysqL:new()
db:set_timeout(2000)
local ok, err = db:connect {
    host = "对应的IP地址linux就用Linux-ip,windows就用本机IP",
    port = 3306,
    database = "对应的数据库名称",
    user = root,
    password = root,
    charset = "utf8"
}
if not ok then
    ngx.say("Failed to connect: ", err)
    return
end
ngx.say("connected to MysqL successfully!")

 编写完后我们 cd ..退出Nginx中 vim Nginx.conf  文件

添加配置:

server{
        listen 8076;
        server_name localhost;
      location /MysqL {
        default_type text/html;
        charset utf-8;
        content_by_lua_file conf/lua/MysqLd.lua;
        }
   }

保存后,出来重新启动Nginx   Nginx -s reload 保存文件

接着我们需要将数据库中系统自带MysqL库中user表里的uer名为root的字段的前面的localhost改为%:允许连接

同样测试连接:成功!

提一下本人遇到的问题:连不上MysqL可以尝试管理员身份启动cmd 重启MysqL 

命令 :停止

net stop MysqL

 重启:

net start MysqL

再尝试测试连接。

接着写跟新的lua脚本:

-- 读取redis缓存(缓存预热)
-- 首先获取uri中的sid值
local uri_args = ngx.req.get_uri_args()
local sid = uri_args["sid"]
-- 接着连接MysqL数据库
local MysqL = require "resty.MysqL"
local db = MysqL:new()
db:set_timeout(2000)
local ok, err = db:connect {
    host = "对应的IP地址linux就用Linux-ip,windows就用本机IP",
    port = 3306,
    database = "对应的数据库名称",
    user = root,
    password = root,
    charset = "utf8"
}
if not ok then
    ngx.say("Failed to connect: ", err)
    return
end
ngx.say("connected to MysqL successfully!")
-- 去查询数据库
-- 按区域编号查询轮播图表
local res, err = db:query("select * from promotion_ad where space_id=" .. sid)
if not res then
    ngx.say("bad result: ", err)
    return
end
db:close()
-- 结果转换为json
local cjson = require "cjson"
ngx.say("res->", cjson.encode(res))
-- 连接redis
local redis = require "resty.redis"
local red = redis:new()
red:set_timeout(2000)
local ok, err = red:connect("192.168.64.200", 6379)
if not ok then
    ngx.say("connect error: ", err)
    return
end
-- 保存到redis
red:set("ad_space_" .. sid, cjson.encode(res))
red:close()
ngx.say("updated redis")

我这里是根据sid去查询广告 具体的可以在sql部分替换。

配置Nginx.conf:把后面的ad_load和代理一起配置了

server{
        listen 8011;
         server_name localhost;
         default_type 'application/json;charset=utf8';
         charset utf-8;

      location /ad_update {
        default_type text/html;
        content_by_lua_file conf/lua/ad_update.lua;
        }
      location /ad_load {
        default_type text/html;
        content_by_lua_file conf/lua/ad_load.lua;
        }

      location /{

        root            html;
        index           index.html index.html;
        proxy_pass      http://192.168.110.25:8080/;
        }


 }

同样的步骤,退出保存 执行 Nginx -s reload 

接着访问地址:查询到结果

此时已经将我们需要的数据加载到redis缓存中了,这就是缓存预热的一个过程;

接着我们去读取redis中的数据;

同样写lua脚本:

--更新redis数据库中的缓存
--id参数
local uri_args = ngx.req.get_uri_args()
local sid = uri_args["sid"]
-- 读取内部缓存
local cache = ngx.shared.dis_cache:get('ad_space_'..sid)
if cache == nil then
    -- 内部缓存没有读取redis
    local redis = require "resty.redis"
    local red = redis:new()
    red:set_timeout(2000)
    local ok, err = red:connect("192.168.64.200", 6379)
    local res = red:get('ad_space_'..sid)
    ngx.say(res)
    red:close()
    -- 保存到内部缓存
    ngx.shared.dis_cache:set('ad_space_'..sid, res, 10*60);
else
    ngx.say(cache)
end

 查询到数据:

这是用已经配好的Nginx.conf配置中的路径;

介绍一下最下面的proxy_pass 配置的跨域:后面的IP和端口是前端vue启动后的地址:

接着我们需要替换调原来调取后端的url:改成我们刚刚配置的路径;

 

接着我们需要去执行vue的build:npm run build 

执行完后在目录会生成一个dist

我们将它复制到桌面,再通过Xshell 传到

 

一般将它上传到这个目录即可;

然后访问 虚拟机的IP:加刚刚配置的端口即可访问即可达到效果

 

 

 

相关文章

显卡天梯图2024最新版,显卡是电脑进行图形处理的重要设备,...
初始化电脑时出现问题怎么办,可以使用win系统的安装介质,连...
todesk远程开机怎么设置,两台电脑要在同一局域网内,然后需...
油猴谷歌插件怎么安装,可以通过谷歌应用商店进行安装,需要...
虚拟内存这个名词想必很多人都听说过,我们在使用电脑的时候...