OpenResty快速入门

一、前言:为什么你需要 OpenResty?

你是否遇到过这些痛点?

  • ❌ 业务逻辑必须放在后端,Nginx 只能做简单转发
  • ❌ 鉴权、限流、日志等通用功能重复开发
  • ❌ 高并发下后端压力大,响应慢

OpenResty = Nginx + LuaJIT ,让你在 Nginx 层直接编写业务逻辑 ,实现:

毫秒级响应

百万 QPS 承载能力

统一网关控制(鉴权、限流、日志、灰度)

本文将带你10 分钟快速上手 OpenResty,从配置到写第一个 Lua 脚本!


二、OpenResty 核心优势

能力 说明
🚀 高性能 基于 Nginx 事件驱动 + LuaJIT JIT 编译
💡 可编程 在 Nginx 配置中嵌入 Lua 代码
🔌 丰富生态 内置 Redis、MySQL、HTTP 客户端
🛡️ 企业级应用 被阿里、腾讯、360、Kong 等广泛使用

💡 一句话理解:OpenResty 让 Nginx 从"静态代理"变成"动态网关"。


三、OpenResty 请求处理阶段(关键!)

OpenResty 在 Nginx 的基础上扩展了多个 Lua 执行阶段,最常用的是:

XML 复制代码
server {
    location /test {
        # 1. 初始化(全局)
        init_by_lua_block { ... }

        # 2. 重写阶段(改写 URI/参数)
        rewrite_by_lua_block { ... }

        # 3. 访问阶段(核心逻辑)
        access_by_lua_block { ... }

        # 4. 内容生成阶段(返回响应)
        content_by_lua_block { ... }

        # 5. 日志阶段
        log_by_lua_block { ... }
    }
}

新手重点掌握access_by_lua_block(鉴权/限流)和 content_by_lua_block(返回数据)


四、实战 1:Hello World!

4.1 修改配置文件

编辑 /usr/local/openresty/nginx/conf/nginx.conf(或 /etc/openresty/nginx.conf):

XML 复制代码
server {
    listen 80;
    server_name localhost;

    location /hello {
        default_type 'text/plain';
        content_by_lua_block {
            ngx.say("Hello, OpenResty!")
            ngx.say("Current time: ", ngx.now())
        }
    }
}

4.2 重载配置 & 测试

bash 复制代码
# 重载配置(不中断服务)
sudo openresty -s reload

# 测试
curl http://localhost/hello

输出

复制代码
Hello, OpenResty!
Current time: 1730123456.789

🎉 恭喜!你已成功运行第一个 OpenResty 脚本!


五、实战 2:实现 IP 黑名单(access 阶段)

bash 复制代码
location /api/ {
    access_by_lua_block {
        local black_ips = {
            ["192.168.1.100"] = true,
            ["10.0.0.5"] = true
        }
        local client_ip = ngx.var.remote_addr
        if black_ips[client_ip] then
            ngx.log(ngx.WARN, "Blocked IP: ", client_ip)
            ngx.exit(403)  -- 直接返回 403
        end
        -- 继续后续处理(如反向代理)
    }

    # 反向代理到后端
    proxy_pass http://backend;
}

优势 :在 Nginx 层拦截恶意请求,不消耗后端资源


六、实战 3:调用 Redis 实现限流

6.1 安装 lua-resty-redis(通常已内置)

OpenResty 默认包含 resty.redis 模块。

6.2 限流脚本(每秒最多 5 次)

bash 复制代码
location /limited {
    access_by_lua_block {
        local redis = require "resty.redis"
        local red = redis:new()
        red:set_timeout(1000)  -- 1s 超时

        local ok, err = red:connect("127.0.0.1", 6379)
        if not ok then
            ngx.log(ngx.ERR, "Redis connect failed: ", err)
            ngx.exit(500)
        end

        local key = "rate_limit:" .. ngx.var.remote_addr
        local requests = red:get(key)

        if not requests or requests == ngx.null then
            red:set(key, 1)
            red:expire(key, 1)  -- 1秒过期
        elseif tonumber(requests) >= 5 then
            ngx.log(ngx.WARN, "Rate limit exceeded for ", ngx.var.remote_addr)
            ngx.exit(429)
        else
            red:incr(key)
        end

        red:close()
    }

    content_by_lua_block {
        ngx.say("Request allowed!")
    }
}

🔥 效果:单 IP 每秒最多 5 次请求,超限返回 429。


七、常用 Lua 模块与 API

模块/变量 用途
ngx.var.remote_addr 客户端 IP
ngx.req.get_headers() 获取请求头
ngx.req.read_body() + ngx.req.get_post_args() 获取 POST 参数
ngx.redirect(url) 重定向
ngx.print() / ngx.say() 输出响应
ngx.exit(code) 终止请求并返回状态码
require "resty.redis" Redis 客户端
require "resty.http" HTTP 客户端

八、调试技巧

8.1 查看日志

bash 复制代码
# 错误日志
tail -f /usr/local/openresty/nginx/logs/error.log

# 访问日志(需配置 log_by_lua_block)

8.2 打印调试信息

Lua 复制代码
ngx.log(ngx.INFO, "Debug: user_id=", user_id)

⚠️ 注意:生产环境避免打印敏感信息!


九、最佳实践建议

轻量逻辑 :Lua 脚本执行时间 < 10ms,避免阻塞 Nginx

连接池 :使用 resty.redis 的连接池(set_keepalive

错误处理 :始终检查 ok, err = ...

配置分离 :复杂逻辑抽离为 .lua 文件,用 content_by_lua_file 引入

Lua 复制代码
location /complex {
    content_by_lua_file /etc/openresty/lua/my_logic.lua;
}

十、结语

感谢您的阅读!如果你有任何疑问或想要分享的经验,请在评论区留言交流!

相关推荐
许彰午5 天前
39_Java单元测试JUnit入门
java·junit·单元测试
骇客之技术5 天前
AutoLua:在安卓上写 Lua 脚本
android·junit·lua
闪电悠米5 天前
黑马点评-Redis ZSet-实现关注 Feed 流
服务器·网络·数据库·redis·缓存·junit·lua
小小龙学IT8 天前
C++20 协程深度解析:从原理到高性能异步框架实战
junit·c++20
IT策士9 天前
Redis 从入门到精通:事务与 Lua 脚本
redis·junit·lua
北极星日淘9 天前
日淘平台优惠券系统的设计:从规则引擎到防超领
junit
慧都小妮子9 天前
不想频繁改 PLC?用 DeviceXPlorer Lua 脚本把产线业务逻辑放到 OPC Server 层
java·junit·lua·takebishi·dxpserver·设备数据采集软件·opc server
闪电悠米11 天前
黑马点评-Redis 消息队列-03_stream_consumer_group
开发语言·数据库·redis·分布式·缓存·junit·lua
闪电悠米11 天前
黑马点评-Redis 消息队列-04_stream_seckill_order
数据库·redis·分布式·缓存·oracle·junit·lua
摇滚侠11 天前
Spring 零基础入门到进阶 单元测试 JUnit 52-60
spring·junit·单元测试