包装 unix 套接字以使其兼容 HTTP

包装 unix 套接字以使其兼容 HTTP

我想使用信号通过网络。signald 是一个提供 unix 套接字并以 JSON 进行通信的应用程序。

我可以使用 nginx 通过 HTTP(S) 连接到 unix 套接字。但是 signald 不理解 HTTP,只理解纯 JSON。它会产生如下错误:

com.fasterxml.jackson.core.JsonParseException: Unrecognized token 'GET': was expecting (JSON String, Number, Array, Object or token 'null', 'true' or 'false') at [Source: (String)"GET / HTTP/1.0"; line: 1, column: 4]

有没有办法将 JSON 发送到我的 Web 转发的 Unix 套接字,就像 Web 服务器提供的任何 API 一样?我想象类似 nginx <-> http 包装器 <-> unix 套接字的东西。

答案1

虽然花了一些时间,但我找到了一个解决方案。基本上,您必须使用 Lua 获取请求主体,将其发送到 unix 套接字,读取行并将其作为服务器响应发送回去。像这样使用 nginx 和 lua:

首次安装nginx-extras

加载模块 ndk_http_module 和 ngx_http_lua_module (按此顺序)在 nginx.conf 中像这样:

load_module modules/ndk_http_module.so;
load_module modules/ngx_http_lua_module.so;

这是location用于 lua 增强型 unix 套接字连接的块。它将请求数据发送到 unix 套接字并使用以下方式读取tcpsocket:接收()。 它会说()该线路作为响应。

    location / {
        content_by_lua_block {
            ngx.req.read_body()
            local body_data = ngx.req.get_body_data()

            local sock = ngx.socket.tcp()
            local ok, err = sock:connect("unix:/var/run/signald/signald.sock")

            local bytes = sock:send(body_data)

            local line, err, part = sock:receive()
            if line then
                ngx.say(line)
            end

            ok, err = sock:close()
        }
    }

使用这样的 curl 调用来测试它(您不必关心Content-Type或方法):

curl -d '{"type":"version"}' https://example.com:1234

相关内容