清风听雨 发表于 2017-2-23 11:27:41

as3与node.js的socket通信


  这里使用了一个单例的SocketManager类:

   
   1: conn = new Socket();

   2:            

   3: conn.addEventListener(Event.CLOSE, onSocketCloseHandler);

   4: conn.addEventListener(Event.CONNECT, onSocketConnectHandler);

   5: conn.addEventListener(IOErrorEvent.IO_ERROR, onSocketIOErrorHandler);

   6: conn.addEventListener(SecurityErrorEvent.SECURITY_ERROR, onSocketSecurityHandler);

   7: conn.addEventListener(ProgressEvent.SOCKET_DATA, onSocketDataHandler);
  SocketManager最多在连接失败时,进行5次重连。建立socket连接代码:





   1: public function connSocket(url:String, port:Number, _endian:String=""):void

   2: {

   3:   if (conn == null)

   4:   {

   5:         initSocket();

   6:   }

   7:   

   8:   if (_endian == '')

   9:   {

10:         _endian = Endian.BIG_ENDIAN;

11:   }

12:   

13:   CURR_RECONN_NUM = 0;

14:   

15:   conn.endian = _endian;

16:   

17:   socket_url = url;

18:   socket_port = port;

19:   

20:   conn.connect(socket_url, socket_port);

21: }
  如果需要发送socket数据,直接调用send方法:





   1: /**

   2:* 发送数据

   3:*/

   4: private function send(bytes:IMeteoricByteArray):Boolean

   5: {

   6:   if (checkConnIsSuc() == false)

   7:   {

   8:         return false;

   9:   }

10:   

11:   var bytes_len:uint = bytes.size();

12:   

13:   var byteArr:ByteArray = new ByteArray();

14:   

15:   byteArr.writeInt(bytes_len + headLen);

16:   byteArr.writeBytes(bytes.getByte());

17:   

18:   conn.writeBytes(byteArr);

19:   conn.flush();

20:   

21:   bytes.dispose();

22:   

23:   return true;

24: }
  格式:数据包头部长度(int-带符号的32位整数)|消息标识(short-16位整数)|消息返回标识(short-16位整数)|…
  bytes.writeInt();
  bytes.writeShort();
  bytes.writeShort();
  bytes…
  根据不同的消息标识(唯一),后台获取标识后调用不同的解析方法,解析客户端发送的数据
  前台as3建立socket,发送数据、解析数据,网上很多例子,这里不重点说了。这里重点介绍node.js如何解析消息(不使用任何第三方库):





   1: var net= require('net');

   2: var clients = [];

   3:

   4: var HOST = '127.0.0.1';

   5: var PORT = 7000;

   6:

   7: net.createServer(function(socket) {   

   8:

   9:   console.log('Connected: ' + socket.remoteAddress +':'+ socket.remotePort);

10:

11:   clients.push(socket);

12:

13:   socket.on('data', function(data) {

14:         console.log('receive data:' + socket.remoteAddress +':'+ socket.remotePort);

15:

16:         var isBuffer = Buffer.isBuffer(data);

17:

18:         if (isBuffer) {

19:             var offset = data['readInt32BE'](0);

20:             var headCode = data['readInt16BE'](offset);

21:             offset += 2;

22:             var headBackCode = data['readInt16BE'](offset);

23:             offset += 2;         

24:            

25:            

26:             var len = data['readInt16BE'](offset);

27:             offset += 2;

28:            

29:             var msg = data.toString('utf8', offset, offset + len)

30:

31:             console.log(headCode + '-' + headBackCode + '-' + msg);

32:

33:             broadcast(msg, socket);

34:         } else {

35:             console.log('Message is not Buffer!');

36:         }

37:         

38:   });

39:

40:   socket.on('end', function() {

41:         console.log('Close Connected: ' + socket);      

42:         clients.splice(clients.indexOf(socket));

43:   });

44:

45:   function broadcast(message, sender) {

46:         clients.forEach(function(client) {

47:             //if (client === sender) {

48:               client.write(message);

49:             // }

50:         });

51:   }

52:

53: }).listen(PORT, HOST);

54:

55:

56: console.log('服务已启动');
  如果一切正常,前台发送数据时,控制台上能看到解析的数据:


  1000是头标识,10为消息返回标识,abcdefg为发送的字符串。





   1: var data:MeteoricSocketSendDataProxy = SocketManager.getInstance().getSocketSendDataProxy(1000, 10) as MeteoricSocketSendDataProxy;

   2: data.addStringData(msg);

   3:

   4: SocketManager.getInstance().sendDataProxy(data);
  上面的解析过程可能比较繁琐,你可以使用Node.js的ByteBuffer (nodejs的ByteBuffer,和C++通信的利器!)
  作者:play175
  https://npmjs.org/package/ByteBuffer
  使用方法也比较简单:



//使用ByteBuffer进行解包操作
var buf = new ByteBuffer(data);
var arr = buf.int32()                  
      .short()
      .short()
      .string()            
      .unpack();
console.log(arr);
broadcast(arr, socket);

/*************************************************/
//原方法
var offset = data['readInt32BE'](0);
var headCode = data['readInt16BE'](offset);
offset += 2;
var headBackCode = data['readInt16BE'](offset);
offset += 2;         

var len = data['readInt16BE'](offset);
offset += 2;
var msg = data.toString('utf8', offset, offset + len)
console.log(headCode + '-' + headBackCode + '-' + msg);
broadcast(msg, socket);

  有兴趣的可以下载全部源码(Flex-SDK4.5 + node.js),点此立即下载>>
  参考资料:
  AS3 Socket类
  Node.js ByteBuffer
  Node.js Buffer
  http://nodejs.org/api/buffer.html
  JavaScript解析二进制数据>>
页: [1]
查看完整版本: as3与node.js的socket通信