local skynet = require "skynet" local socket = require "skynet.socket" local httpd = require "http.httpd" local sockethelper = require "http.sockethelper" local urllib = require "http.url" local cjson = require "cjson" local settings = require 'settings' local mode = ... if mode == "agent" then local headers = { ['Content-Type'] = 'application/json', ['Access-Control-Allow-Origin'] = '*', -- 这里写允许访问的域名就可以了,允许所有人访问的话就写* ['Access-Control-Allow-Headers'] = 'Origin, X-Requested-With, Content-Type, Accept', ['Access-Control-Allow-Methods'] = 'GET, POST, OPTIONS', } local function response(id, ...) local code, res = ... if code ~= 200 then print("++++response+++++++", code, inspect(res)) end local ok, err = httpd.write_response(sockethelper.writefunc(id), ...) if not ok then print(string.format("fd = %d, %s", id, err)) end end local api_logic = require "api_logic" local function check_api_parms(method, parms) if not parms then return 201 , "参数错误" end if method ~= "POST" then return 202 , "没有此方法" end if parms.server_ca ~= api_server_ca then return 203 , "未认证通过" end if not parms.module then return 204 , "没有此模块" end if not parms.method then return 205 , "未支持方法" end return 0, "成功" end local function do_init() end skynet.start(function() do_init() skynet.dispatch("lua", function (_,_,id) socket.start(id) -- 开始接收一个 socket -- limit request body size to 8192 (you can pass nil to unlimit) -- 一般的业务不需要处理大量上行数据,为了防止攻击,做了一个 8K 限制。这个限制可以去掉。 local code, url, method, header, body = httpd.read_request(sockethelper.readfunc(id), 8192) if code then if code ~= 200 then -- 如果协议解析有问题,就回应一个错误码 code 。 response(id, code, nil, headers) else local path = urllib.parse(url) if string.match(path, "/wx") then local resp = {errcode=0, errmsg="成功", data = {}} local json_body = cjson.decode(body) local errocde, errmsg = check_api_parms(method, json_body) if errocde == 0 then local mod = json_body.module if mod == "wx" then local func = api_logic[json_body.method] if not func then resp.errcode = 201 resp.errmsg = "方法未实现" else resp.errcode, resp.errmsg, resp.data = func(json_body.parms) end else resp.errcode = 201 resp.errmsg = "模块未找到" end else resp.errcode = errocde resp.errmsg = errmsg end response(id, code, cjson.encode(resp), headers) else response(id, 404, nil, headers) end end else -- 如果抛出的异常是 sockethelper.socket_error 表示是客户端网络断开了。 if url == sockethelper.socket_error then skynet.error("socket closed") else skynet.error(url) end end socket.close(id) end) end) else skynet.start(function() local agent = {} for i= 1, settings.nodes[mode].api_slave_count do agent[i] = skynet.newservice(SERVICE_NAME, "agent") end local balance = 1 -- 监听一个 web 端口 DEBUG(" api gate_port_http = ", settings.nodes[mode].gate_port_http) local id = socket.listen("0.0.0.0", settings.nodes[mode].gate_port_http) socket.start(id , function(id, addr) -- 当一个 http 请求到达的时候, 把 socket id 分发到事先准备好的代理中去处理。 skynet.send(agent[balance], "lua", id) balance = balance + 1 if balance > #agent then balance = 1 end end) end) end