|
- local MBSocket = EapClass("MBSocket")
- local scheduler = import(".scheduler")
- local proto = import(".proto")
-
- local SOCKET_NUM_COUNT = 1
-
- function MBSocket:ctor()
- self._mbSocket = nil
- self._listener = {}
- self._adapter = {}
- self._sendData = {}
- self._address = nil
- self._connected = false
- self._schedulerID = -1
-
- self._closeBack = nil --断线回调
-
- self:initData()
- end
- function MBSocket:initData()
-
- end
- -- 心跳时间
- local KEEP_ALIVE_TIMEOUT = 30
-
- function MBSocket:isConnected()
- return self._connected
- end
- -- 地址,端口,链接成功回调,链接失败回调,收到消息回调
- function MBSocket:connect(address, closeBack, connectBack)
- if (self._connected) then
- if (connectBack) then
- connectBack(true)
- end
- return true
- end
- if (not address) then
- return false
- end
- self._mbSocket = cc.WebSocket:create(address)
- if not self._mbSocket then
- print("创建连接失败" .. address)
- return false
- end
-
- if (self._mbSocket:getReadyState()>=2) then
- if (self._mbSocket) then
- self._mbSocket.close()
- self._mbSocket = nil
- end
- if (connectBack) then
- connectBack(false)
- return false
- end
- return false
- end
- self._address = address
- self._closeBack = closeBack
- self._connectBack = connectBack
-
- local function OnOpen(strData)
- print("MBSocket OnOpen")
- if (self._connectBack) then
- local callback = self._connectBack
- self._connectBack = nil
- callback(true);
- end
- -- 发送极限数据
- if (#self._sendData>0) then
- self._mbSocket:sendString(self._sendData[1])
- table.remove(self._sendData, 1)
- end
- end
- local function OnMessage(strData)
- if type(strData) == "table" then
- strData = string.char(unpack(strData))
- end
- local opcode, data = self:parsePacket(strData)
- -- local data = G_EapSdkJson.decode(strData)
- self:onReceivedData(opcode, data)
- end
- --区分是否当前创建的socket
- local curSocketNum = SOCKET_NUM_COUNT + 1
- SOCKET_NUM_COUNT = SOCKET_NUM_COUNT + 1
- self._mbSocket.socketNum = curSocketNum
-
- local function OnClose(strData)
- print("MBSocket OnClose", self._mbSocket.socketNum, curSocketNum)
- self._connected = false;
- if (self._mbSocket and self._mbSocket.socketNum == curSocketNum)then
- self:onclose()
- end
- end
- local function OnError(strData)
- print("MBSocket OnClose", self._mbSocket.socketNum, curSocketNum)
- if (self._mbSocket and self._mbSocket.socketNum == curSocketNum)then
- self:onclose()
- end
- end
-
- -- 注册回调以上的函数
- if nil ~= self._mbSocket then
- self._mbSocket:registerScriptHandler(OnOpen,cc.WEBSOCKET_OPEN)
- self._mbSocket:registerScriptHandler(OnMessage,cc.WEBSOCKET_MESSAGE)
- self._mbSocket:registerScriptHandler(OnClose,cc.WEBSOCKET_CLOSE)
- self._mbSocket:registerScriptHandler(OnError,cc.WEBSOCKET_ERROR)
- end
- self._connected = true
- self._schedulerID = scheduler.scheduleGlobal(handler(self, self.peakPacket), 0.1)
- return true
- end
- --重新连接
- function MBSocket:reConnect()
- return self:connect(self._address, self._onClose)
- end
- -- 关闭连接
- function MBSocket:close()
- self:onclose()
- end
- function MBSocket:onclose()
- self._connected = false
- self._sendData = {}
- if (self._mbSocket) then
- scheduler.unscheduleGlobal(self._schedulerID)
- self._mbSocket:unregisterScriptHandler(cc.WEBSOCKET_OPEN)
- self._mbSocket:unregisterScriptHandler(cc.WEBSOCKET_MESSAGE)
- self._mbSocket:unregisterScriptHandler(cc.WEBSOCKET_CLOSE)
- self._mbSocket:unregisterScriptHandler(cc.WEBSOCKET_ERROR)
- self._mbSocket:close();
- self._mbSocket = nil;
- end
- if (self._connectBack) then
- local callback = self._connectBack
- self._connectBack = nil;
- callback(false);
- elseif (self._closeBack) then
- local callback = self._closeBack
- self._closeBack = nil;
- callback(false);
- end
- end
- -- 这里是提供给LUA逻辑层的网络协议发送接口
- function MBSocket:sendPacket(opcode, data)
- if (self._mbSocket) then
- if (self._mbSocket:getReadyState() == cc.WEBSOCKET_STATE_CONNECTING) then
- local buffer = self:serializePacket(opcode, data)
- self._sendData[#self._sendData+1] = buffer
- return
- end
- else
- print("连接断开,不重新连接服务器")
- if (self._serType == SER_TYPE_LOGIN) then
- local buffer = self:serializePacket(opcode, data)
- self._sendData[#self._sendData+1] = buffer
- self:reConnect()
- end
- return
- end
- if (self._mbSocket) then
- local buffer = self:serializePacket(opcode, data)
- self._sendData[#self._sendData+1] = buffer
- --self._mbSocket:sendString(data)
- end
- end
- function MBSocket:peakPacket()
- if (self._mbSocket and #self._sendData>0) then
- print("MBSocket:peakPacket = ", type(self._sendData[1]), string.len(self._sendData[1]))
- self._mbSocket:sendString(self._sendData[1])
- table.remove(self._sendData, 1)
- end
- end
- function MBSocket:onReceivedData(opcode, data)
- assert(false, "MBSocket:onReceivedData 此方法需要被继承")
- end
-
- -- | compress | 1 | 0:未压缩, 1:压缩,只针对data字段压缩 |
- -- | format | 7 | 0:自定义, 1:protobuf, 2:json,3:xml |
- -- | 扩展字段 | 8 | 自定义数据格式,原样返回, app用来定义消息id用的,自增,app可以用来区分是哪条消息的返回数据
- -- | opcode | 16 | 网络协议的类型标识,根据该标识进行反序列化 |
- -- | len | 16 | 网络包的长度,其值为除len字段外的其它所有长度 |
- -- len可以没有,如果compress==0;没有len;compress==1;才有len字段
-
- function MBSocket:serializePacket(opcode, data)
- if data and opcode and G_EapProtos[opcode] then
- print("发送数据:", opcode)
- EapDump(data)
- local len = 0
- local buffer = proto.serialize(data, G_EapProtos[opcode])
- len = len + string.len(buffer)
- local opcodeStr = proto.int16ToBufStr(opcode)
-
- local op1 = 1
- local op1Str = string.char(op1)
- local op2 = 0
- local op2Str = string.char(op2)
- len = len + 4
-
- if op1 == 1 then
- buffer = op1Str..op2Str..opcodeStr..buffer
- elseif op1 == 129 then
- local op3 = len
- local op3Str = string.char(op3)
- buffer = op1Str..op2Str..opcodeStr..op3Str..buffer
- end
-
- return buffer
- end
- end
-
- function MBSocket:parsePacket(buffer)
- local tbl = nil
- local opcode = nil
-
- local op1 = string.byte(buffer, 1, 1)
- local compress = bit.rshift(op1, 7)
- local type = bit.band(op1, 0x7f)
- local dataIndex = 5
- if compress == 1 then
- dataIndex = 7
- end
-
- local op2, op3 = string.byte(buffer, 3, 4)
- opcode = proto.buffToInt16(op2, op3)
- print("MBSocket:parsePacket Opcode == ", opcode, compress, type, string.len(buffer))
-
- if G_EapProtos[opcode] then
- local leftBuff = string.sub(buffer, dataIndex)
- tbl = proto.parse(leftBuff, G_EapProtos[opcode])
- EapDump(tbl)
- else
- print("MBSocket:parsePacket proto not exist!!!")
- end
- return opcode, tbl
- end
-
- return MBSocket
|