PageRenderTime 31ms CodeModel.GetById 23ms RepoModel.GetById 1ms app.codeStats 0ms

/js/lib/Socket.IO-node/support/socket.io-client/lib/transport.js

http://github.com/onedayitwillmake/RealtimeMultiplayerNodeJs
JavaScript | 142 lines | 115 code | 19 blank | 8 comment | 25 complexity | e0995767d65c44d423bf2e1cc9d2b3ab MD5 | raw file
Possible License(s): GPL-2.0, LGPL-2.1, MPL-2.0-no-copyleft-exception, BSD-3-Clause
  1. /**
  2. * Socket.IO client
  3. *
  4. * @author Guillermo Rauch <guillermo@learnboost.com>
  5. * @license The MIT license.
  6. * @copyright Copyright (c) 2010 LearnBoost <dev@learnboost.com>
  7. */
  8. // abstract
  9. (function(){
  10. var io = this.io;
  11. var frame = '~m~',
  12. stringify = function(message){
  13. if (Object.prototype.toString.call(message) == '[object Object]'){
  14. if (!('JSON' in window)){
  15. if ('console' in window && console.error) console.error('Trying to encode as JSON, but JSON.stringify is missing.');
  16. return '{ "$error": "Invalid message" }';
  17. }
  18. return '~j~' + JSON.stringify(message);
  19. } else {
  20. return String(message);
  21. }
  22. };
  23. Transport = io.Transport = function(base, options){
  24. this.base = base;
  25. this.options = {
  26. timeout: 15000 // based on heartbeat interval default
  27. };
  28. io.util.merge(this.options, options);
  29. };
  30. Transport.prototype.send = function(){
  31. throw new Error('Missing send() implementation');
  32. };
  33. Transport.prototype.connect = function(){
  34. throw new Error('Missing connect() implementation');
  35. };
  36. Transport.prototype.disconnect = function(){
  37. throw new Error('Missing disconnect() implementation');
  38. };
  39. Transport.prototype._encode = function(messages){
  40. var ret = '', message,
  41. messages = io.util.isArray(messages) ? messages : [messages];
  42. for (var i = 0, l = messages.length; i < l; i++){
  43. message = messages[i] === null || messages[i] === undefined ? '' : stringify(messages[i]);
  44. ret += frame + message.length + frame + message;
  45. }
  46. return ret;
  47. };
  48. Transport.prototype._decode = function(data){
  49. var messages = [], number, n;
  50. do {
  51. if (data.substr(0, 3) !== frame) return messages;
  52. data = data.substr(3);
  53. number = '', n = '';
  54. for (var i = 0, l = data.length; i < l; i++){
  55. n = Number(data.substr(i, 1));
  56. if (data.substr(i, 1) == n){
  57. number += n;
  58. } else {
  59. data = data.substr(number.length + frame.length);
  60. number = Number(number);
  61. break;
  62. }
  63. }
  64. messages.push(data.substr(0, number)); // here
  65. data = data.substr(number);
  66. } while(data !== '');
  67. return messages;
  68. };
  69. Transport.prototype._onData = function(data){
  70. this._setTimeout();
  71. var msgs = this._decode(data);
  72. if (msgs && msgs.length){
  73. for (var i = 0, l = msgs.length; i < l; i++){
  74. this._onMessage(msgs[i]);
  75. }
  76. }
  77. };
  78. Transport.prototype._setTimeout = function(){
  79. var self = this;
  80. if (this._timeout) clearTimeout(this._timeout);
  81. this._timeout = setTimeout(function(){
  82. self._onTimeout();
  83. }, this.options.timeout);
  84. };
  85. Transport.prototype._onTimeout = function(){
  86. this._onDisconnect();
  87. };
  88. Transport.prototype._onMessage = function(message){
  89. if (!this.sessionid){
  90. this.sessionid = message;
  91. this._onConnect();
  92. } else if (message.substr(0, 3) == '~h~'){
  93. this._onHeartbeat(message.substr(3));
  94. } else if (message.substr(0, 3) == '~j~'){
  95. this.base._onMessage(JSON.parse(message.substr(3)));
  96. } else {
  97. this.base._onMessage(message);
  98. }
  99. },
  100. Transport.prototype._onHeartbeat = function(heartbeat){
  101. this.send('~h~' + heartbeat); // echo
  102. };
  103. Transport.prototype._onConnect = function(){
  104. this.connected = true;
  105. this.connecting = false;
  106. this.base._onConnect();
  107. this._setTimeout();
  108. };
  109. Transport.prototype._onDisconnect = function(){
  110. this.connecting = false;
  111. this.connected = false;
  112. this.sessionid = null;
  113. this.base._onDisconnect();
  114. };
  115. Transport.prototype._prepareUrl = function(){
  116. return (this.base.options.secure ? 'https' : 'http')
  117. + '://' + this.base.host
  118. + ':' + this.base.options.port
  119. + '/' + this.base.options.resource
  120. + '/' + this.type
  121. + (this.sessionid ? ('/' + this.sessionid) : '/');
  122. };
  123. })();