Skynet快速入门
Skynet可以做什么
- 利用多核性能
- 封装了socket api
- mysql mogodb redis作为外部服务
- 逻辑开发使用lua
- 支持集群,并把cluser作为一个外部服务,还有并不推荐的多节点模式。
Skynet的消息
- Skynet通过消息进行服务间的通讯,每个服务通过skynet.disptch设置自身监听的消息类型和回调,在收到一个消息后通过回调函数执行。
- Skynet对网络连接,内部的调用进行了封装,并提供了6种预制的类型,包括: 回应消息、网络消息、调试消息、文本消息、Lua 消息、错误.
- Skynet的消息类型可以通过register_protocol接口注册一个新的消息类型,并设置其解包的函数,消息回调函数。
Skynet的服务
可以看作Skynet的消息处理器,但是同时也可以把一些外部服务作为Skynet的服务,也许还需要给一个外部服务写一个驱动,像使用数据库mongodb。 Skynet服务通过dispatch,设置要处理的消息类型。
主要接口
skynet.newservice(name), 搜索service/路径,并启动模块以name命名的lua脚本。
skynet.start(func), 通过func函数执行服务的初始化,在skynet.newservice执行时加载并调用func.
skynet.init(func), 在skynet.start执行后,执行后续的初始化。
skynet.dispatch(type,func), 注册类型为 type,的消息处理器。
skynet.register_protocol(class), 在当前服务内创建一个新类型的消息处理机制,class包含有,name(类型标识),id(消息类型数字标识),dispatch,unpack(解包函数)。
skynet.call(addr,type,...), 发送消息,addr指向服务的地址,type消息类型,...设置服务的消息类型的参数。获取返回值
skynet.send(addr,type,...),发送消息,不获取返回值
skynet.redirect(addr,source,type,...),伪装成source指向的服务发送消息。
调试
- 需要启动debug_console服务
nc 127.0.0.1 8000
help 查看支持的命令
list 列出服务名和服务地址
debug 调试一个服务。这里的每个服务都是一个lua vm. debug vm状态下输入 cont命令退出。debug 后面跟一个服务地址.
- debug vm时允许的输入
1. 基本的lua脚本和命令,例如:print
2. watch 设置断点
watch("lua", function(_,_,cmd) return cmd=="get" end)
断点时可以使用n 运行下一样,s进入函数, c继续运行,退出行调试。
3. cont 退出调试vm
DebugConsole DebugConsole Blog
Skynet Service加载机制
-- 配置:
luaservice = root.."service/?.lua;"..root.."test/?.lua;"..root.."examples/?.lua"
-- skynet/lualib/loader.lua 中的代码片段:
for pat in string.gmatch(LUA_SERVICE, "([^;]+);*") do
local filename = string.gsub(pat, "?", SERVICE_NAME)
local f, msg = loadfile(filename)
if not f then
table.insert(err, msg)
else
pattern = pat
main = f
break
end
-- 解析
LUA_SERVICE 配置项值字符串,以分号分隔每个是一个文件路径,问号(?)将被替换为require的 SERVICE_NAME。
string.gmatch(LUA_SERVICE, "([^;]+);*") 分隔配置项的路径。
for pat in XXX do -- 遍历路径并查找,随后查到第一个后break退出循环。
也就是说, 当你使用newservice(name)开始一个新service时,其name并不只是文件名。例如:通过添加luaservice搜索路径 "?/aa.lua", 可以把一个文件夹当作一个模块,从而加载模块下的aa.lua作为service的初始化入口。
Skynet官网Watchdog示例解析
- example/main.lua
- watchdog服务
- gate服务
- agent服务
- watchdog 负责启动gate,并通过socket连接为每个连接创建一个agent处理该连接。 watchdog接受socket类型的消息,socket类型的消息则有gate监听到客户端连接时发送。
- gate通过一个hander处理网络连接的不同声明周期,hander中把正确的消息转发给另一个服务,连接状态相关的消息则交给watchdog去处理(打印日志,通知gate主动断开)。其中hander的message阶段,将会在数据包接受完毕后回调,此时将获取到一个fd句柄用于响应。解包请求的数据流通过register_protocol的unpack。