Apache APISIX 2.15.3 完整安装指南
一、环境要求
组件 | 最低版本 | 验证命令 | 说明 |
---|---|---|---|
etcd | 3.5.x | etcdctl version |
配置中心 |
OpenResty | 1.19.x | openresty -v |
运行环境 |
LuaRocks | 3.x | luarocks --version |
Lua包管理工具 |
APISIX | 2.15.3 | apisix version |
API网关核心 |
系统 | CentOS 7 | cat /etc/redhat-release |
推荐操作系统 |
二、etcd 3.5.6 安装
安装节点:172.25.69.180
安装位置:/data01/zhenghaosheng/project/etcd-v3.5.6-linux-amd64/data
参考安装教程:https://www.cnblogs.com/freeweb/p/17726690.html
三、OpenResty 1.19.x 安装
安装节点:172.25.71.28
安装位置:/home/zhs/openresty/nginx/
参考安装教程:https://www.cnblogs.com/freeweb/p/13446663.html
1. 下载源码
https://openresty.org/cn/download.html
2. 编译安装
./configure --prefix=/home/zhs/openresty --with-http_stub_status_module --with-http_realip_module --with-http_ssl_module --with-http_v2_module --with-http_gunzip_module --with-stream --with-stream_ssl_module --with-threads --with-pcre-jit --with-file-aio
gmake && gmake install
3. 配置环境变量
echo 'export PATH=/usr/local/openresty/nginx/sbin:$PATH' >> ~/.bashrcsource ~/.bashrc
4. 验证安装
openresty -v# 应输出:nginx version: openresty/1.19.3.2
四、LuaRocks 3.10.0 安装
1. 下载源码
下载地址:http://luarocks.org/rocks/luarocks-3.9.1.tar.gz
2. 解决依赖问题
sudo yum install lua-devel -y
3. 编译安装
./configure --prefix=/usr/local/luarocks --with-lua-include=/usr/include/makemake install
4. 配置环境变量
export PATH=/usr/local/luarocks/bin:$PATH # 添加系统环境变量source ~/.bashrc
5. 验证安装
luarocks --version# 应输出:/usr/local/luarocks/bin/luarocks 3.10.0
6. 卸载旧版本(如存在)
sudo yum remove luarocks -y# 查看安装的版本
/usr/local/luarocks/bin/luarocks --versionluarocks --version
7. 永久设置系统环境变量
[root@szdpl592 apisix-2.15.3]# echo $PATH # 查看原来的系统环境变量配置
/root/.luarocks/bin:/sbin:/bin:/usr/sbin:/usr/bin
[root@szdpl592 apisix-2.15.3]# echo 'export PATH=$PATH:/usr/local/luarocks/bin' >> ~/.bashrc
[root@szdpl592 apisix-2.15.3]# source ~/.bashrc
五、APISIX 2.15.3 安装
1. 下载源码
wget https://downloads.apache.org/apisix/2.15.3/apache-apisix-2.15.3-src.tgztar -zxvf apache-apisix-2.15.3-src.tgzcd apache-apisix-2.15.3
2. 解决依赖
make deps
3. 安装APISIX
make install
4. 修改配置文件
编辑 conf/config.yaml
,确保etcd配置正确:
deployment: role: traditional role_traditional: config_provider: etcdetcd: host: - "http://172.25.69.180:2379"
5. 初始化APISIX
apisix init
6. 启动服务
apisix start
7. 验证安装
curl http://127.0.0.1:9080/apisix/admin/routes -H 'X-API-KEY: edd1c9f034335f136f87ad84b625c8f1'# 应返回路由信息
六、常见问题解决方案
问题1:LuaRocks编译时报头文件缺失
lua.h for Lua 5.1 not found
解决方案:
sudo yum install lua-devel./configure --prefix=/usr/local/luarocks --with-lua-include=/usr/include/
问题2:LuaRocks版本冲突
$ luarocks --version # 显示旧版本
解决方案:
# 删除旧版本sudo yum remove luarocks -y # 更新PATHecho 'export PATH=/usr/local/luarocks/bin:$PATH' >> ~/.bashrcsource ~/.bashrc
问题3:APISIX启动失败
排查步骤:
-
检查etcd是否正常运行:
etcdctl endpoint health
-
检查端口冲突:
netstat -tunlp | grep 9080
-
查看日志:
tail -f /usr/local/apisix/logs/error.log
问题4:插件安装失败
解决方案:
-
确保LuaRocks配置正确:
luarocks config --scope system
-
清除缓存后重试:
luarocks purge --tree=/home/zhs/apisix-2.15.3/depsluarocks make --tree=/home/zhs/apisix-2.15.3/deps
五、APISIX 2.15.3 安装
1. 下载源码
wget https://downloads.apache.org/apisix/2.15.3/apache-apisix-2.15.3-src.tgztar -zxvf apache-apisix-2.15.3-src.tgzcd apache-apisix-2.15.3
2. 解决依赖
make deps
3. 安装APISIX
make install
4. 修改配置文件
编辑 conf/config.yaml
,确保etcd配置正确:
deployment: role: traditional role_traditional: config_provider: etcdetcd: host: - "http://172.25.69.180:2379"
5. 初始化APISIX
apisix init
6. 启动服务
apisix start
7. 验证安装
curl http://127.0.0.1:9080/apisix/admin/routes -H 'X-API-KEY: edd1c9f034335f136f87ad84b625c8f1'# 应返回路由信息
六、常见问题解决方案
问题1:LuaRocks编译时报头文件缺失
lua.h for Lua 5.1 not found
解决方案:
sudo yum install lua-devel./configure --prefix=/usr/local/luarocks --with-lua-include=/usr/include/
问题2:LuaRocks版本冲突
$ luarocks --version # 显示旧版本
解决方案:
# 删除旧版本sudo yum remove luarocks -y # 更新PATHecho 'export PATH=/usr/local/luarocks/bin:$PATH' >> ~/.bashrcsource ~/.bashrc
问题3:APISIX启动失败
排查步骤:
-
检查etcd是否正常运行:
etcdctl endpoint health
-
检查端口冲突:
netstat -tunlp | grep 9080
-
查看日志:
tail -f /usr/local/apisix/logs/error.log
问题4:插件安装失败
解决方案:
-
确保LuaRocks配置正确:
luarocks config --scope system
-
清除缓存后重试:
luarocks purge --tree=/home/zhs/apisix-2.15.3/depsluarocks make --tree=/home/zhs/apisix-2.15.3/deps
local consumer_label_value_def = {anyOf = {{ type = "string" },{type = "array",items = {type = "object",properties = {api_code = { type = "string", minLength = 1, maxLength = 64 },api_id = { type = "string", minLength = 1, maxLength = 64 }},required = { "api_code", "api_id" }}},{type = "object",patternProperties = {[".*"] = {type = "object",properties = {api_code = { type = "string", minLength = 1, maxLength = 64 },api_id = { type = "string", minLength = 1, maxLength = 64 }},required = { "api_code", "api_id" }}}}}
}
_M.consumer_label_value_def = consumer_label_value_def_M.consumer = {type = "object",properties = {username = {type = "string", minLength = 1, maxLength = rule_name_def.maxLength,pattern = [[^[a-zA-Z0-9_]+$]]},plugins = plugins_schema,labels = {description = "key/value pairs to specify attributes",type = "object",patternProperties = {[".*"] = consumer_label_value_def},maxProperties = 16},create_time = timestamp_def,update_time = timestamp_def,desc = desc_def,},required = {"username"},
}
问题2:鉴权插件加载失败
size of C type is unknown or too large at line 39
参考地址:https://blog.csdn.net/songfeihu0810232/article/details/127003632
hmac.lua 源码地址:https://github.com/jkeys089/lua-resty-hmac/blob/master/lib/resty/hmac.lua
全量替换 resty.hmac.lua
local str_util = require "resty.string"
local to_hex = str_util.to_hex
local ffi = require "ffi"
local ffi_new = ffi.new
local ffi_str = ffi.string
local ffi_gc = ffi.gc
local ffi_typeof = ffi.typeof
local C = ffi.C
local setmetatable = setmetatablelocal _M = { _VERSION = '0.06' }local mt = { __index = _M }ffi.cdef[[
typedef struct engine_st ENGINE;
typedef struct evp_pkey_ctx_st EVP_PKEY_CTX;
typedef struct hmac_ctx_st HMAC_CTX;//OpenSSL 1.0
void HMAC_CTX_init(HMAC_CTX *ctx);
void HMAC_CTX_cleanup(HMAC_CTX *ctx);//OpenSSL 1.1
HMAC_CTX *HMAC_CTX_new(void);
void HMAC_CTX_free(HMAC_CTX *ctx);
]]local buf = ffi_new("unsigned char[64]")
local res_len = ffi_new("unsigned int[1]")local ctx_new, ctx_free
local openssl11, e = pcall(function ()local ctx = C.HMAC_CTX_new()C.HMAC_CTX_free(ctx)
end)
if openssl11 thenffi.cdef [[typedef struct evp_md_ctx_st EVP_MD_CTX;typedef struct evp_md_st EVP_MD;]]ctx_new = function ()return C.HMAC_CTX_new()endctx_free = function (ctx)C.HMAC_CTX_free(ctx)end
elseffi.cdef [[typedef struct env_md_ctx_st EVP_MD_CTX;typedef struct env_md_st EVP_MD;struct env_md_ctx_st{const EVP_MD *digest;ENGINE *engine;unsigned long flags;void *md_data;EVP_PKEY_CTX *pctx;int (*update)(EVP_MD_CTX *ctx,const void *data,size_t count);};struct env_md_st{int type;int pkey_type;int md_size;unsigned long flags;int (*init)(EVP_MD_CTX *ctx);int (*update)(EVP_MD_CTX *ctx,const void *data,size_t count);int (*final)(EVP_MD_CTX *ctx,unsigned char *md);int (*copy)(EVP_MD_CTX *to,const EVP_MD_CTX *from);int (*cleanup)(EVP_MD_CTX *ctx);int (*sign)(int type, const unsigned char *m, unsigned int m_length, unsigned char *sigret, unsigned int *siglen, void *key);int (*verify)(int type, const unsigned char *m, unsigned int m_length, const unsigned char *sigbuf, unsigned int siglen, void *key);int required_pkey_type[5];int block_size;int ctx_size;int (*md_ctrl)(EVP_MD_CTX *ctx, int cmd, int p1, void *p2);};struct hmac_ctx_st{const EVP_MD *md;EVP_MD_CTX md_ctx;EVP_MD_CTX i_ctx;EVP_MD_CTX o_ctx;unsigned int key_length;unsigned char key[128];};]]local ctx_ptr_type = ffi_typeof("HMAC_CTX[1]")ctx_new = function ()local ctx = ffi_new(ctx_ptr_type)C.HMAC_CTX_init(ctx)return ctxendctx_free = function (ctx)C.HMAC_CTX_cleanup(ctx)end
end
ffi.cdef [[
int HMAC_Init_ex(HMAC_CTX *ctx, const void *key, int len, const EVP_MD *md, ENGINE *impl);
int HMAC_Update(HMAC_CTX *ctx, const unsigned char *data, size_t len);
int HMAC_Final(HMAC_CTX *ctx, unsigned char *md, unsigned int *len);const EVP_MD *EVP_md5(void);
const EVP_MD *EVP_sha1(void);
const EVP_MD *EVP_sha256(void);
const EVP_MD *EVP_sha384(void);
const EVP_MD *EVP_sha512(void);
]]local hashes = {MD5 = C.EVP_md5(),SHA1 = C.EVP_sha1(),SHA256 = C.EVP_sha256(),SHA384 = C.EVP_sha384(),SHA512 = C.EVP_sha512()
}_M.ALGOS = hashesfunction _M.new(self, key, hash_algo)local ctx = ctx_new()local _hash_algo = hash_algo or hashes.MD5if C.HMAC_Init_ex(ctx, key, #key, _hash_algo, nil) == 0 thenreturn nilendffi_gc(ctx, ctx_free)return setmetatable({ _ctx = ctx }, mt)
endfunction _M.update(self, s)return C.HMAC_Update(self._ctx, s, #s) == 1
endfunction _M.final(self, s, hex_output)if s ~= nil thenif C.HMAC_Update(self._ctx, s, #s) == 0 thenreturn nilendendif C.HMAC_Final(self._ctx, buf, res_len) == 1 thenif hex_output == true thenreturn to_hex(ffi_str(buf, res_len[0]))endreturn ffi_str(buf, res_len[0])endreturn nil
end
function _M.reset(self)return C.HMAC_Init_ex(self._ctx, nil, 0, nil, nil) == 1
endreturn _M
问题3:调用接口时出现异常
lua entry thread aborted: runtime error: /home/zhs/apisix-2.15.3/apisix/plugins/vivo-hmac-auth.lua:185: attempt to call field 'plugin' (a nil value)
解决方案:
根据apisix 2.15.3提供 的自定义插件模板修改源插件中的部分代码
问题4:access 日志中不打印服务code
解决方案:
apisix/init.lua http_access_phase
方法中添加
if route.value.service_protocol == "grpc" thenreturn ngx.exec("@grpc_pass")end--add X-Gateway-Serve field to header for every query and print it in access.loglocal serve = route.value.labels and route.value.labels.serveif not serve thenif core.string.has_prefix(route.value.id, "route_") thenserve = string.sub(route.value.id, 7)endendif serve thencore.request.set_header("X-Gateway-Serve", serve)end