分享web开发知识

注册/登录|最近发布|今日推荐

主页 IT知识网页技术软件开发前端开发代码编程运营维护技术分享教程案例
当前位置:首页 > IT知识

skynet之使用sproto

发布时间:2023-09-06 01:23责任编辑:白小东关键词:暂无标签

????sproto的简介略过,这里直接上代码,新建proto.lua文件,内容如下:

local sprotoparser =require"sprotoparser"

local proto ={}

proto.c2s = sprotoparser.parse [[
.package {
????type 0 : integer
????session 1 : integer
}

handshake 1 {
????response {
????????msg 0 ?: string
????}
}

say 2 {
????request {
????????name 0 : string
????????msg 1 : string
????}
}

quit 3 {}

]]

proto.s2c = sprotoparser.parse [[
.package {
????type 0 : integer
????session 1 : integer
}

heartbeat 1 {}
]]

return proto

新建client1.lua文件,内容如下:

package.cpath="luaclib/?.so"
package.path="lualib/?.lua;myexample/?.lua"

if_VERSION~="Lua 5.3"then
????error"Use lua 5.3"
end

local socket =require"client.socket"

-- 通信协议
local proto =require"proto"
local sproto =require"sproto"

local host = sproto.new(proto.s2c):host "package"
local request = host:attach(sproto.new(proto.c2s))

local fd =assert(socket.connect("127.0.0.1",8888))

local session =0
localfunction send_request(name, args)
????session = session +1
????local str = request(name, args, session)

????-- 解包测试
????-- local host2 = sproto.new(proto.c2s):host "package"
????-- local type,str2 = host2:dispatch(str)
????-- print(type)
????-- print(str2)

????socket.send(fd, str)

????print("Request:", session)
end

send_request("handshake")
send_request("say",{ name ="soul", msg ="hello world"})

whiletruedo
????-- 接收服务器返回消息
????local str ??= socket.recv(fd)

????-- print(str)
????if str~=niland str~=""then
????????????print("server says: "..str)
????????????-- socket.close(fd)
????????????-- break;
????end

????-- 读取用户输入消息
????local readstr = socket.readstdin()

????if readstr then
????????if readstr =="quit"then
????????????send_request("quit")
????????????-- socket.close(fd)
????????????-- break;
????????else
????????????-- 把用户输入消息发送给服务器
????????????send_request("say",{ name ="soul", msg = readstr })
????????end
????else
????????socket.usleep(100)
????end

end

新建socket1.lua,内容如下:

local skynet =require"skynet"
require"skynet.manager"????-- import skynet.register
local socket =require"skynet.socket"

local proto =require"proto"
local sproto =require"sproto"

local host

local REQUEST ={}

function REQUEST:say()
????print("say", self.name, self.msg)
end

function REQUEST:handshake()
????print("handshake")
end

function REQUEST:quit()
????print("quit")
end

localfunction request(name, args, response)
????local f =assert(REQUEST[name])
????local r = f(args)
????if response then
????????-- 生成回应包(response是一个用于生成回应包的函数。)
????????-- 处理session对应问题
????????-- return response(r)
????end
end

localfunction send_package(fd,pack)
????-- 协议与客户端对应(两字节长度包头+内容)
????localpackage= string.pack(">s2", pack)
????socket.write(fd,package)
end

localfunction accept(id)
????-- 每当 accept 函数获得一个新的 socket id 后,并不会立即收到这个 socket 上的数据。这是因为,我们有时会希望把这个 socket 的操作权转让给别的服务去处理。
????-- 任何一个服务只有在调用 socket.start(id) 之后,才可以收到这个 socket 上的数据。

????socket.start(id)

????host = sproto.new(proto.c2s):host "package"
????-- request = host:attach(sproto.new(proto.c2s))

????whiletruedo
????????local str = socket.read(id)
????????if str then
????????????localtype,str2,str3,str4 = host:dispatch(str)

????????????iftype=="REQUEST"then
????????????????-- REQUEST : 第一个返回值为 "REQUEST" 时,表示这是一个远程请求。如果请求包中没有 session 字段,表示该请求不需要回应。这时,第 2 和第 3 个返回值分别为消息类型名(即在 sproto 定义中提到的某个以 . 开头的类型名),以及消息内容(通常是一个 table );如果请求包中有 session 字段,那么还会有第 4 个返回值:一个用于生成回应包的函数。
????????????????local ok, result ?=pcall(request, str2,str3,str4)

????????????????if ok then
????????????????????if result then
????????????????????????socket.write(id,"收到了")
????????????????????????-- 暂时不使用回应包回应
????????????????????????-- print("response:"..result)
????????????????????????-- send_package(id,result)
????????????????????end
????????????????else
????????????????????skynet.error(result)
????????????????end
????????????end

????????????iftype=="RESPONSE"then
????????????????-- RESPONSE :第一个返回值为 "RESPONSE" 时,第 2 和第 3 个返回值分别为 session 和消息内容。消息内容通常是一个 table ,但也可能不存在内容(仅仅是一个回应确认)。
????????????????-- 暂时不处理客户端的回应
????????????????print("client response")
????????????end????????

????????else
????????????socket.close(id)
????????????return
????????end
????end
end

skynet.start(function()
????print("==========Socket Start=========")
????local id = socket.listen("127.0.0.1",8888)
????print("Listen socket :","127.0.0.1",8888)

????socket.start(id ,function(id, addr)
????????????-- 接收到客户端连接或发送消息()
????????????print("connect from ".. addr .." ".. id)

????????????-- 处理接收到的消息
????????????accept(id)
????????end)
????--可以为自己注册一个别名。(别名必须在 32 个字符以内)
????skynet.register "SOCKET1"
end)

?

?

?

?

?

?

?

skynet之使用sproto

原文地址:http://www.cnblogs.com/skiing886/p/7805254.html

知识推荐

我的编程学习网——分享web前端后端开发技术知识。 垃圾信息处理邮箱 tousu563@163.com 网站地图
icp备案号 闽ICP备2023006418号-8 不良信息举报平台 互联网安全管理备案 Copyright 2023 www.wodecom.cn All Rights Reserved