skynet api
常用的api
skynet.newservice
skynet.fork
skynet.start
skynet.dispatch
socket.listen
socket.start
socket.read,write(require "socket") !!!
socket.recv,send(require "client.socket")
cjson.decode
cjson.encode
main.lua
--[[
常用的api
skynet.newservice
skynet.fork
skynet.start
skynet.dispatch
socket.listen
socket.start
socket.read,write(require "socket") !!!
socket.recv,send(require "client.socket")
cjson.decode
cjson.encode
]]
local skynet = require "skynet"
local socket = require "skynet.socket"
local function accept(clientfd, addr)
skynet.newservice("agent", clientfd, addr)
end
skynet.start(function ()
local listenfd = socket.listen("0.0.0.0", 8888)
skynet.error("listen on 0.0.0.0, 8888")
socket.start(listenfd, accept)
end)
agent.lua
local skynet = require "skynet"
local socket = require "skynet.socket"
local cjson = require "cjson"
local clientfd, addr=...
clientfd = tonumber(clientfd)
-- 打包发送一个数据包,加上大端2字节的头部
local function send_package(fd, pack)
local package = string.pack(">s2", pack)
socket.write(fd, package)
end
-- 解析数据包 返回值第一个为完整的包,第二个为剩余的
local function unpack_package(text)
if text == nil then
return nil, text
end
local size = #text
if size < 2 then
return nil, text
end
local s = text:byte(1) * 256 + text:byte(2) --数据包的长度
if size < s+2 then
return nil, text
end
-- 从第三个字节开始,到数据包结束,
return text:sub(3,2+s), text:sub(3+s)--前一个完整数据包的后续
end
-- 返回一个完整包,读取数据,拼接剩余的
local function recv_package(last)
local result
result, last = unpack_package(last)
if result then
return result, last --result是完整的数据包
end
local r = socket.read(clientfd)
if not r then
return nil, last
end
if r == "" then
error "Server closed"
end
return unpack_package(last .. r)
end
local last = ""
local function process_socket_events()
--[[
while true do
local r = socket.read(clientfd)
if r then
print(r)
else
print("recv nil")
end
end
]]
while true do
local v
v, last = recv_package(last)
if not v then
skynet.error("fd = ",clientfd," socket closed")
skynet.exit()
break
end
print(v)
send_package(clientfd,v)
end
end
skynet.start(function ()
print("recv a connection:", clientfd, addr)
socket.start(clientfd) -- 绑定 fd actorid 与epoll事件
skynet.fork(process_socket_events)
skynet.dispatch("lua", function (_, _, cmd, ...)
end)
end)
client.lua
package.cpath = "../../skynet/luaclib/?.so;../../lua-cjson/?.so;"
package.path = "../../skynet/lualib/?.lua;./skynet/examples/?.lua;;../../lua-cjson/?.lua"
local cjson = require "cjson"
local socket = require "client.socket"
local fd = assert(socket.connect("127.0.0.1", 8888))
local function send_package(fd, pack)
local json = {}
json["cmd"] = "login"
json["data"] = pack
local data = cjson.encode(json);
local package = string.pack(">s2", data)
socket.send(fd, package)
end
local function unpack_package(text)
local size = #text
if size < 2 then
return nil, text
end
local s = text:byte(1) * 256 + text:byte(2)
if size < s+2 then
return nil, text
end
return text:sub(3,2+s), text:sub(3+s)
end
local function recv_package(last)
local result
result, last = unpack_package(last)
if result then
return result, last
end
local r = socket.recv(fd)
if not r then
return nil, last
end
if r == "" then
error "Server closed"
end
return unpack_package(last .. r)
end
local session = 0
local function send_request(str)
print("send msg:",str)
send_package(fd, str)
end
local last = ""
local function dispatch_package()
while true do
local v
v, last = recv_package(last)
if not v then
break
end
v = cjson.decode(v)
print("recv msg;",v)
print("cmd = ",v.cmd)
print("data = ",v.data)
end
end
send_request("handshake")
while true do
dispatch_package()
local cmd = socket.readstdin()
if cmd then
if cmd == "quit" then
socket.close(fd)
break
else
send_request(cmd)
end
else
socket.usleep(100)
end
end
config.skynet_json
thread=8--工作线程数目
logger=nil
harbor=0
start="main" -- 启动第一服务
lua_path="./skynet/lualib/?.lua;".."./test/lualib/?.lua;".."./skynet/lualib/?/init.lua;".."./lua-cjson/?.lua"
luaservice = "./skynet/service/?.lua;".."./myexample/skynet_json/?.lua;".."./skynet/test/?.lua;".."./lua-cjson/?.lua;"
lualoader = "./skynet/lualib/loader.lua"
cpath = "./skynet/cservice/?.so;./lua-cjson/?.so" -- actor 内存块 + 消息队列
lua_cpath = "./skynet/luaclib/?.so;".."./lua-cjson/?.so" -- C语言写的lua库
gdut17@ubuntu:~/skynet_test$ ./skynet/skynet config.skynet_json
[:00000002] LAUNCH snlua bootstrap
[:00000003] LAUNCH snlua launcher
[:00000004] LAUNCH snlua cdummy
[:00000005] LAUNCH harbor 0 4
[:00000006] LAUNCH snlua datacenterd
[:00000007] LAUNCH snlua service_mgr
[:00000008] LAUNCH snlua main
[:00000008] listen on 0.0.0.0, 8888
[:00000002] KILL self
[:0000000a] LAUNCH snlua agent 2 127.0.0.1:48656
recv a connection: 2 127.0.0.1:48656
{“data”:“handshake”,“cmd”:“login”}
[:0000000a] 2 socket closed
[:0000000a] KILL self
[:00000012] LAUNCH snlua agent 3 127.0.0.1:48658
recv a connection: 3 127.0.0.1:48658
{“cmd”:“login”,“data”:“handshake”}
{“cmd”:“login”,“data”:“wangwu”}
{“cmd”:“login”,“data”:“lisi”}
gdut17@ubuntu:~/skynet_test/myexample/skynet_json$ lua client.lua
send msg: handshake
recv msg; table: 0x5624fcaf0a50
cmd = login
data = handshake
wangwu
send msg: wangwu
recv msg; table: 0x5624fcaf0cd0
cmd = login
data = wangwu
lisi
send msg: lisi
recv msg; table: 0x5624fcaf0f10
cmd = login
data = lisi
本文档展示了如何在Skynet中使用JSON进行数据收发。通过启动配置文件`config.skynet_json`,Skynet API 启动了多个服务,包括一个监听8888端口的主服务。客户端`client.lua`发送登录消息`handshake`,接收到响应后,继续发送用户名`wangwu`和`lisi`,并成功接收对应的登录确认数据。
1406

被折叠的 条评论
为什么被折叠?



