How to use Lua scripts to implement data caching based on OpenResty and Redis?

Some people may not be familiar with OpenResty, but when it comes to Nginx, they may know something. Nginx, which controls the rate and concurrency, is adopted by many companies, and OpenResty is upgraded on the basis of Nginx, providing Lua extensions, which greatly improves the concurrency processing capability of Nignx, which can reach 10K~1000K. In fact, OpenResty, like Tengine, is based on a derivative version of Nginx, incorporating some new features of their respective businesses.

Here is an example to illustrate the use of Lua scripts to realize the cache of business data through OpenResty and Redis. Generally, the mall system will include various advertisements, and the advertisement visits to the homepage are generally relatively frequent. If you request a Mysql or Oracle database every time you visit it, it will definitely put a certain amount of pressure on the database. So the usual practice is to cache this part of the data that is not easy to change frequently. When the browser accesses, it directly accesses the cache to obtain data, and if there is no request to the database.

As shown in the figure above, the idea of ​​homepage advertisement access is divided into the following steps:

1) The user requests the address, accesses OpenResty, and obtains it from Nginx's local cache (Nginx-Cache). If it is obtained, it returns directly, and if it cannot be obtained, proceed to the next step.

2) Access the data in Redis through the Lua script, if there is, it will return directly [and the data will be put in the local cache of Nginx first], if not, go to the next step directly.

3) Access Mysql through Lua script, get data from Mysql, store the data in Redis, and return the result.

OpenResty installation

Here we only introduce the installation of OpenResty in the Linux environment.

① Execute the following commands to install

# 添加仓库执行命令
yum install yum-utils
yum-config-manager --add-repo https://openresty.org/package/centos/openresty.repo

# 执行安装
yum install openresty

       ② After the installation is successful, there will be corresponding content in the default directory [/usr/local/openresty]. Since OpenResty is derived from Nginx, Nginx [/usr/local/openresty/nginx directory] has already been installed under OpenResty. We also need to modify nginx.conf to set the root used by the configuration file to root. The purpose of this setting is that when using Lua scripts in the future, you can directly add Lua scripts under Root [here set users and directories according to your own needs] .

In addition, since the Nginx cache module will be used, the Nginx cache module needs to be configured in conf in advance.

script writing

According to the above steps, the whole visit is divided into three links. The specific code and detailed explanation are as follows:

ngx.header.content_type="application/json;charset=utf8"
-- 获取请求参数
local uri_args = ngx.req.get_uri_args();
-- 获取请求的ID
local id = uri_args["id"];
-- 获取本地缓存
local cache_ngx = ngx.shared.dis_cache;
-- 根据ID 获取本地缓存数据
local contentCache = cache_ngx:get('content_cache_'..id);
-- 判断从本地是否获取的有数据
if contentCache == "" or contentCache == nil then
    -- 本地没有,则去读取Redis
    -- 加在redis模块
    local redis = require("resty.redis");
    local red = redis:new()
    red:set_timeout(2000)
    -- 连接redis
    red:connect("192.168.132.132", 6379)
    -- 查询数据
    local rescontent=red:get("content_"..id);
    -- 判断从redis是否获取的有数据
    if ngx.null == rescontent then
        -- 没有,则直接从Mysql中获取数据
        local cjson = require("cjson");
        local mysql = require("resty.mysql");
        local db = mysql:new();
        db:set_timeout(2000)
        local props = {
            host = "192.168.132.132",
            port = 3306,
            database = "changgou_content",
            user = "root",
            password = "123456"
        }
        local res = db:connect(props);
        -- 执行SQL并将结果转换成json数据格式
        local select_sql = "select url,pic from tb_content where status ='1' and category_id="..id.." order by sort_order";
        res = db:query(select_sql);
        local responsejson = cjson.encode(res);
        -- 设置到Redis中
        red:set("content_"..id,responsejson);
        -- 返回结果
        ngx.say(responsejson);
        -- 关闭数据库
        db:close()
    else
        -- 设置到Nginx Cache中
        cache_ngx:set('content_cache_'..id, rescontent, 2*60);
        -- 返回结果
        ngx.say(rescontent)
    end
    -- 关闭Redis的连接
    red:close()
else
    -- 返回结果
    ngx.say(contentCache)
end

Configure interception routes

After the script is written, you need to configure the corresponding server to intercept the corresponding path. After intercepting, hand it over to the corresponding Lua script for processing.

server{
    
    listen 80;
    # 监听域名
    server_name localhost;
    
    # 表示所有以localhost/read_content的请求都由该配置处理
    localtion /read_content {
        # 都交给/usr/local/server/lua/read_content.lua脚本进行处理
        content_by_lua_file /usr/local/server/lua/read_content.lua;
    }
}

Every time you modify the Nginx.conf file, you need to restart Nginx [/usr/local/openresty/nginx]. The above can be realized simply by using Lua script and cache of OpenResty and Redis.

Guess you like

Origin blog.csdn.net/qq_35363507/article/details/115520108