skynet.dispatch 使用详解
skynet.dispatch 是 Skynet 框架(轻量级分布式游戏服务器框架) 的核心 API,用于定义当前服务(service)接收消息时的处理逻辑,即注册消息处理器。
1. 核心作用
为当前 Skynet 服务绑定“消息类型-处理函数”的映射关系,当服务收到对应类型的消息时,自动触发指定函数执行。
2. 基础语法
skynet.dispatch(message_type, handler_func)
- message_type :消息类型,Skynet 支持两种核心类型:
- skynet.PTYPE_LUA :默认的 Lua 消息类型(最常用),消息内容为 Lua 数据(需通过 skynet.pack / skynet.unpack 序列化)。
- skynet.PTYPE_TEXT :文本消息类型,消息内容为字符串(无需额外序列化)。
- handler_func :消息处理函数,接收 3 个固定参数,格式如下:
local function handler_func(session, address, ...)
-- session:消息会话 ID(用于区分请求/响应,0 表示无响应需求)
-- address:发送方服务的地址(Skynet 内部唯一标识)
-- ...:消息内容(根据 message_type 格式不同,内容形式不同)
end
3. 关键参数解析
参数 说明
session - 正数:表示“需要响应”的请求消息,需用 skynet.ret 回传结果; - 0:表示“无需响应”的通知消息。
address 发送方服务的地址,可用于 skynet.send / skynet.call 主动回发消息。
... - 若为 PTYPE_LUA :是 skynet.pack 序列化后的 Lua 数据(如字符串、表等); - 若为 PTYPE_TEXT :直接是字符串内容。
4. 常用示例
示例 1:处理 Lua 类型消息(最常用)
local skynet = require "skynet"
-- 注册 Lua 消息处理器
skynet.dispatch("lua", function(session, address, cmd, ...)
-- cmd:自定义命令(如 "add"、"query",用于区分不同业务逻辑)
-- ...:命令对应的参数
if cmd == "add" then
local a, b = ...
local result = a + b
-- 若有 session(需要响应),则回传结果
if session > 0 then
skynet.ret(skynet.pack(result)) -- 用 skynet.pack 序列化结果
end
elseif cmd == "query" then
-- 处理查询逻辑...
end
end)
-- 启动服务(必须调用,否则服务无法运行)
skynet.start(function()
-- 可选:设置服务别名(方便其他服务通过别名调用)
skynet.register("my_service")
end)
示例 2:处理文本类型消息
local skynet = require "skynet"
skynet.dispatch("text", function(session, address, text)
print("收到文本消息:", text) -- 直接使用字符串,无需 unpack
-- 无需响应(session=0),故不调用 skynet.ret
end)
skynet.start(function()
skynet.register("text_service")
end)
5. 注意事项
1. 每个服务仅需注册一次处理器: skynet.dispatch 通常在服务初始化时( skynet.start 前或内部)调用一次,无需重复注册。
2. skynet.ret 必须配合 session>0 使用:若消息无需响应( session=0 ),调用 skynet.ret 会导致错误。
3. 消息序列化规则:
- PTYPE_LUA 消息必须用 skynet.pack (发送方)和 skynet.unpack (接收方,示例中省略是因为 ... 已自动 unpack)处理。
- PTYPE_TEXT 消息无需序列化,直接传递字符串。
4. 服务启动依赖:注册处理器后,必须调用 skynet.start 启动服务,否则服务会退出。

浙公网安备 33010602011771号