cometd-rails 0.0.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.gitignore +23 -0
- data/Gemfile +4 -0
- data/LICENSE +202 -0
- data/README.md +39 -0
- data/Rakefile +2 -0
- data/cometd-rails.gemspec +23 -0
- data/lib/cometd/rails/version.rb +5 -0
- data/lib/cometd/rails.rb +18 -0
- data/vendor/assets/javascripts/.DS_Store +0 -0
- data/vendor/assets/javascripts/cometd-dojox-rails.js +2 -0
- data/vendor/assets/javascripts/cometd-jquery-rails.js +2 -0
- data/vendor/assets/javascripts/common/.DS_Store +0 -0
- data/vendor/assets/javascripts/common/AckExtension.js +112 -0
- data/vendor/assets/javascripts/common/CallbackPollingTransport.js +166 -0
- data/vendor/assets/javascripts/common/CometD.js +2090 -0
- data/vendor/assets/javascripts/common/LongPollingTransport.js +111 -0
- data/vendor/assets/javascripts/common/ReloadExtension.js +254 -0
- data/vendor/assets/javascripts/common/RequestTransport.js +297 -0
- data/vendor/assets/javascripts/common/TimeStampExtension.js +42 -0
- data/vendor/assets/javascripts/common/TimeSyncExtension.js +216 -0
- data/vendor/assets/javascripts/common/Transport.js +142 -0
- data/vendor/assets/javascripts/common/TransportRegistry.js +116 -0
- data/vendor/assets/javascripts/common/Utils.js +58 -0
- data/vendor/assets/javascripts/common/WebSocketTransport.js +410 -0
- data/vendor/assets/javascripts/common/cometd-amd.js +7 -0
- data/vendor/assets/javascripts/common/cometd-header.js +15 -0
- data/vendor/assets/javascripts/common/cometd-json.js +5 -0
- data/vendor/assets/javascripts/common/cometd-namespace.js +3 -0
- data/vendor/assets/javascripts/common/cometd.require.js +16 -0
- data/vendor/assets/javascripts/dojox/.DS_Store +0 -0
- data/vendor/assets/javascripts/dojox/ack.js +22 -0
- data/vendor/assets/javascripts/dojox/dojox.require.js +5 -0
- data/vendor/assets/javascripts/dojox/main.js +95 -0
- data/vendor/assets/javascripts/dojox/reload.js +26 -0
- data/vendor/assets/javascripts/dojox/timestamp.js +22 -0
- data/vendor/assets/javascripts/dojox/timesync.js +22 -0
- data/vendor/assets/javascripts/jquery/.DS_Store +0 -0
- data/vendor/assets/javascripts/jquery/jquery.cometd-ack.js +33 -0
- data/vendor/assets/javascripts/jquery/jquery.cometd-reload.js +41 -0
- data/vendor/assets/javascripts/jquery/jquery.cometd-timestamp.js +33 -0
- data/vendor/assets/javascripts/jquery/jquery.cometd-timesync.js +33 -0
- data/vendor/assets/javascripts/jquery/jquery.cometd.js +140 -0
- data/vendor/assets/javascripts/jquery/jquery.cometd.require.js +5 -0
- metadata +115 -0
@@ -0,0 +1,216 @@
|
|
1
|
+
/*
|
2
|
+
* Copyright (c) 2010 the original author or authors.
|
3
|
+
*
|
4
|
+
* Licensed under the Apache License, Version 2.0 (the "License");
|
5
|
+
* you may not use this file except in compliance with the License.
|
6
|
+
* You may obtain a copy of the License at
|
7
|
+
*
|
8
|
+
* http://www.apache.org/licenses/LICENSE-2.0
|
9
|
+
*
|
10
|
+
* Unless required by applicable law or agreed to in writing, software
|
11
|
+
* distributed under the License is distributed on an "AS IS" BASIS,
|
12
|
+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
13
|
+
* See the License for the specific language governing permissions and
|
14
|
+
* limitations under the License.
|
15
|
+
*/
|
16
|
+
|
17
|
+
(function()
|
18
|
+
{
|
19
|
+
function bind(org_cometd)
|
20
|
+
{
|
21
|
+
/**
|
22
|
+
* With each handshake or connect, the extension sends timestamps within the
|
23
|
+
* ext field like: <code>{ext:{timesync:{tc:12345567890,l:23,o:4567},...},...}</code>
|
24
|
+
* where:<ul>
|
25
|
+
* <li>tc is the client timestamp in ms since 1970 of when the message was sent.
|
26
|
+
* <li>l is the network lag that the client has calculated.
|
27
|
+
* <li>o is the clock offset that the client has calculated.
|
28
|
+
* </ul>
|
29
|
+
*
|
30
|
+
* <p>
|
31
|
+
* A cometd server that supports timesync, can respond with an ext
|
32
|
+
* field like: <code>{ext:{timesync:{tc:12345567890,ts:1234567900,p:123,a:3},...},...}</code>
|
33
|
+
* where:<ul>
|
34
|
+
* <li>tc is the client timestamp of when the message was sent,
|
35
|
+
* <li>ts is the server timestamp of when the message was received
|
36
|
+
* <li>p is the poll duration in ms - ie the time the server took before sending the response.
|
37
|
+
* <li>a is the measured accuracy of the calculated offset and lag sent by the client
|
38
|
+
* </ul>
|
39
|
+
*
|
40
|
+
* <p>
|
41
|
+
* The relationship between tc, ts & l is given by <code>ts=tc+o+l</code> (the
|
42
|
+
* time the server received the messsage is the client time plus the offset plus the
|
43
|
+
* network lag). Thus the accuracy of the o and l settings can be determined with
|
44
|
+
* <code>a=(tc+o+l)-ts</code>.
|
45
|
+
* </p>
|
46
|
+
* <p>
|
47
|
+
* When the client has received the response, it can make a more accurate estimate
|
48
|
+
* of the lag as <code>l2=(now-tc-p)/2</code> (assuming symmetric lag).
|
49
|
+
* A new offset can then be calculated with the relationship on the client
|
50
|
+
* that <code>ts=tc+o2+l2</code>, thus <code>o2=ts-tc-l2</code>.
|
51
|
+
* </p>
|
52
|
+
* <p>
|
53
|
+
* Since the client also receives the a value calculated on the server, it
|
54
|
+
* should be possible to analyse this and compensate for some asymmetry
|
55
|
+
* in the lag. But the current client does not do this.
|
56
|
+
* </p>
|
57
|
+
*
|
58
|
+
* @param configuration
|
59
|
+
*/
|
60
|
+
return org_cometd.TimeSyncExtension = function(configuration)
|
61
|
+
{
|
62
|
+
var _cometd;
|
63
|
+
var _maxSamples = configuration && configuration.maxSamples || 10;
|
64
|
+
var _lags = [];
|
65
|
+
var _offsets = [];
|
66
|
+
var _lag = 0;
|
67
|
+
var _offset = 0;
|
68
|
+
|
69
|
+
function _debug(text, args)
|
70
|
+
{
|
71
|
+
_cometd._debug(text, args);
|
72
|
+
}
|
73
|
+
|
74
|
+
this.registered = function(name, cometd)
|
75
|
+
{
|
76
|
+
_cometd = cometd;
|
77
|
+
_debug('TimeSyncExtension: executing registration callback');
|
78
|
+
};
|
79
|
+
|
80
|
+
this.unregistered = function()
|
81
|
+
{
|
82
|
+
_debug('TimeSyncExtension: executing unregistration callback');
|
83
|
+
_cometd = null;
|
84
|
+
_lags = [];
|
85
|
+
_offsets = [];
|
86
|
+
};
|
87
|
+
|
88
|
+
this.incoming = function(message)
|
89
|
+
{
|
90
|
+
var channel = message.channel;
|
91
|
+
if (channel && channel.indexOf('/meta/') === 0)
|
92
|
+
{
|
93
|
+
if (message.ext && message.ext.timesync)
|
94
|
+
{
|
95
|
+
var timesync = message.ext.timesync;
|
96
|
+
_debug('TimeSyncExtension: server sent timesync', timesync);
|
97
|
+
|
98
|
+
var now = new Date().getTime();
|
99
|
+
var l2 = (now - timesync.tc - timesync.p) / 2;
|
100
|
+
var o2 = timesync.ts - timesync.tc - l2;
|
101
|
+
|
102
|
+
_lags.push(l2);
|
103
|
+
_offsets.push(o2);
|
104
|
+
if (_offsets.length > _maxSamples)
|
105
|
+
{
|
106
|
+
_offsets.shift();
|
107
|
+
_lags.shift();
|
108
|
+
}
|
109
|
+
|
110
|
+
var samples = _offsets.length;
|
111
|
+
var lagsSum = 0;
|
112
|
+
var offsetsSum = 0;
|
113
|
+
for (var i = 0; i < samples; ++i)
|
114
|
+
{
|
115
|
+
lagsSum += _lags[i];
|
116
|
+
offsetsSum += _offsets[i];
|
117
|
+
}
|
118
|
+
_lag = parseInt((lagsSum / samples).toFixed());
|
119
|
+
_offset = parseInt((offsetsSum / samples).toFixed());
|
120
|
+
_debug('TimeSyncExtension: network lag', _lag, 'ms, time offset with server', _offset, 'ms', _lag, _offset);
|
121
|
+
}
|
122
|
+
}
|
123
|
+
return message;
|
124
|
+
};
|
125
|
+
|
126
|
+
this.outgoing = function(message)
|
127
|
+
{
|
128
|
+
var channel = message.channel;
|
129
|
+
if (channel && channel.indexOf('/meta/') === 0)
|
130
|
+
{
|
131
|
+
if (!message.ext)
|
132
|
+
{
|
133
|
+
message.ext = {};
|
134
|
+
}
|
135
|
+
message.ext.timesync = {
|
136
|
+
tc: new Date().getTime(),
|
137
|
+
l: _lag,
|
138
|
+
o: _offset
|
139
|
+
};
|
140
|
+
_debug('TimeSyncExtension: client sending timesync', org_cometd.JSON.toJSON(message.ext.timesync));
|
141
|
+
}
|
142
|
+
return message;
|
143
|
+
};
|
144
|
+
|
145
|
+
/**
|
146
|
+
* Get the estimated offset in ms from the clients clock to the
|
147
|
+
* servers clock. The server time is the client time plus the offset.
|
148
|
+
*/
|
149
|
+
this.getTimeOffset = function()
|
150
|
+
{
|
151
|
+
return _offset;
|
152
|
+
};
|
153
|
+
|
154
|
+
/**
|
155
|
+
* Get an array of multiple offset samples used to calculate
|
156
|
+
* the offset.
|
157
|
+
*/
|
158
|
+
this.getTimeOffsetSamples = function()
|
159
|
+
{
|
160
|
+
return _offsets;
|
161
|
+
};
|
162
|
+
|
163
|
+
/**
|
164
|
+
* Get the estimated network lag in ms from the client to the server.
|
165
|
+
*/
|
166
|
+
this.getNetworkLag = function()
|
167
|
+
{
|
168
|
+
return _lag;
|
169
|
+
};
|
170
|
+
|
171
|
+
/**
|
172
|
+
* Get the estimated server time in ms since the epoch.
|
173
|
+
*/
|
174
|
+
this.getServerTime = function()
|
175
|
+
{
|
176
|
+
return new Date().getTime() + _offset;
|
177
|
+
};
|
178
|
+
|
179
|
+
/**
|
180
|
+
*
|
181
|
+
* Get the estimated server time as a Date object
|
182
|
+
*/
|
183
|
+
this.getServerDate = function()
|
184
|
+
{
|
185
|
+
return new Date(this.getServerTime());
|
186
|
+
};
|
187
|
+
|
188
|
+
/**
|
189
|
+
* Set a timeout to expire at given time on the server.
|
190
|
+
* @param callback The function to call when the timer expires
|
191
|
+
* @param atServerTimeOrDate a js Time or Date object representing the
|
192
|
+
* server time at which the timeout should expire
|
193
|
+
*/
|
194
|
+
this.setTimeout = function(callback, atServerTimeOrDate)
|
195
|
+
{
|
196
|
+
var ts = (atServerTimeOrDate instanceof Date) ? atServerTimeOrDate.getTime() : (0 + atServerTimeOrDate);
|
197
|
+
var tc = ts - _offset;
|
198
|
+
var interval = tc - new Date().getTime();
|
199
|
+
if (interval <= 0)
|
200
|
+
{
|
201
|
+
interval = 1;
|
202
|
+
}
|
203
|
+
return org_cometd.Utils.setTimeout(_cometd, callback, interval);
|
204
|
+
};
|
205
|
+
};
|
206
|
+
}
|
207
|
+
|
208
|
+
if (typeof define === 'function' && define.amd)
|
209
|
+
{
|
210
|
+
define(['org/cometd'], bind);
|
211
|
+
}
|
212
|
+
else
|
213
|
+
{
|
214
|
+
bind(org.cometd);
|
215
|
+
}
|
216
|
+
})();
|
@@ -0,0 +1,142 @@
|
|
1
|
+
/**
|
2
|
+
* Base object with the common functionality for transports.
|
3
|
+
*/
|
4
|
+
org.cometd.Transport = function()
|
5
|
+
{
|
6
|
+
var _type;
|
7
|
+
var _cometd;
|
8
|
+
|
9
|
+
/**
|
10
|
+
* Function invoked just after a transport has been successfully registered.
|
11
|
+
* @param type the type of transport (for example 'long-polling')
|
12
|
+
* @param cometd the cometd object this transport has been registered to
|
13
|
+
* @see #unregistered()
|
14
|
+
*/
|
15
|
+
this.registered = function(type, cometd)
|
16
|
+
{
|
17
|
+
_type = type;
|
18
|
+
_cometd = cometd;
|
19
|
+
};
|
20
|
+
|
21
|
+
/**
|
22
|
+
* Function invoked just after a transport has been successfully unregistered.
|
23
|
+
* @see #registered(type, cometd)
|
24
|
+
*/
|
25
|
+
this.unregistered = function()
|
26
|
+
{
|
27
|
+
_type = null;
|
28
|
+
_cometd = null;
|
29
|
+
};
|
30
|
+
|
31
|
+
this._debug = function()
|
32
|
+
{
|
33
|
+
_cometd._debug.apply(_cometd, arguments);
|
34
|
+
};
|
35
|
+
|
36
|
+
this._mixin = function()
|
37
|
+
{
|
38
|
+
return _cometd._mixin.apply(_cometd, arguments);
|
39
|
+
};
|
40
|
+
|
41
|
+
this.getConfiguration = function()
|
42
|
+
{
|
43
|
+
return _cometd.getConfiguration();
|
44
|
+
};
|
45
|
+
|
46
|
+
this.getAdvice = function()
|
47
|
+
{
|
48
|
+
return _cometd.getAdvice();
|
49
|
+
};
|
50
|
+
|
51
|
+
this.setTimeout = function(funktion, delay)
|
52
|
+
{
|
53
|
+
return org.cometd.Utils.setTimeout(_cometd, funktion, delay);
|
54
|
+
};
|
55
|
+
|
56
|
+
this.clearTimeout = function(handle)
|
57
|
+
{
|
58
|
+
org.cometd.Utils.clearTimeout(handle);
|
59
|
+
};
|
60
|
+
|
61
|
+
/**
|
62
|
+
* Converts the given response into an array of bayeux messages
|
63
|
+
* @param response the response to convert
|
64
|
+
* @return an array of bayeux messages obtained by converting the response
|
65
|
+
*/
|
66
|
+
this.convertToMessages = function (response)
|
67
|
+
{
|
68
|
+
if (org.cometd.Utils.isString(response))
|
69
|
+
{
|
70
|
+
try
|
71
|
+
{
|
72
|
+
return org.cometd.JSON.fromJSON(response);
|
73
|
+
}
|
74
|
+
catch(x)
|
75
|
+
{
|
76
|
+
this._debug('Could not convert to JSON the following string', '"' + response + '"');
|
77
|
+
throw x;
|
78
|
+
}
|
79
|
+
}
|
80
|
+
if (org.cometd.Utils.isArray(response))
|
81
|
+
{
|
82
|
+
return response;
|
83
|
+
}
|
84
|
+
if (response === undefined || response === null)
|
85
|
+
{
|
86
|
+
return [];
|
87
|
+
}
|
88
|
+
if (response instanceof Object)
|
89
|
+
{
|
90
|
+
return [response];
|
91
|
+
}
|
92
|
+
throw 'Conversion Error ' + response + ', typeof ' + (typeof response);
|
93
|
+
};
|
94
|
+
|
95
|
+
/**
|
96
|
+
* Returns whether this transport can work for the given version and cross domain communication case.
|
97
|
+
* @param version a string indicating the transport version
|
98
|
+
* @param crossDomain a boolean indicating whether the communication is cross domain
|
99
|
+
* @return true if this transport can work for the given version and cross domain communication case,
|
100
|
+
* false otherwise
|
101
|
+
*/
|
102
|
+
this.accept = function(version, crossDomain, url)
|
103
|
+
{
|
104
|
+
throw 'Abstract';
|
105
|
+
};
|
106
|
+
|
107
|
+
/**
|
108
|
+
* Returns the type of this transport.
|
109
|
+
* @see #registered(type, cometd)
|
110
|
+
*/
|
111
|
+
this.getType = function()
|
112
|
+
{
|
113
|
+
return _type;
|
114
|
+
};
|
115
|
+
|
116
|
+
this.send = function(envelope, metaConnect)
|
117
|
+
{
|
118
|
+
throw 'Abstract';
|
119
|
+
};
|
120
|
+
|
121
|
+
this.reset = function()
|
122
|
+
{
|
123
|
+
this._debug('Transport', _type, 'reset');
|
124
|
+
};
|
125
|
+
|
126
|
+
this.abort = function()
|
127
|
+
{
|
128
|
+
this._debug('Transport', _type, 'aborted');
|
129
|
+
};
|
130
|
+
|
131
|
+
this.toString = function()
|
132
|
+
{
|
133
|
+
return this.getType();
|
134
|
+
};
|
135
|
+
};
|
136
|
+
|
137
|
+
org.cometd.Transport.derive = function(baseObject)
|
138
|
+
{
|
139
|
+
function F() {}
|
140
|
+
F.prototype = baseObject;
|
141
|
+
return new F();
|
142
|
+
};
|
@@ -0,0 +1,116 @@
|
|
1
|
+
/**
|
2
|
+
* A registry for transports used by the CometD object.
|
3
|
+
*/
|
4
|
+
org.cometd.TransportRegistry = function()
|
5
|
+
{
|
6
|
+
var _types = [];
|
7
|
+
var _transports = {};
|
8
|
+
|
9
|
+
this.getTransportTypes = function()
|
10
|
+
{
|
11
|
+
return _types.slice(0);
|
12
|
+
};
|
13
|
+
|
14
|
+
this.findTransportTypes = function(version, crossDomain, url)
|
15
|
+
{
|
16
|
+
var result = [];
|
17
|
+
for (var i = 0; i < _types.length; ++i)
|
18
|
+
{
|
19
|
+
var type = _types[i];
|
20
|
+
if (_transports[type].accept(version, crossDomain, url) === true)
|
21
|
+
{
|
22
|
+
result.push(type);
|
23
|
+
}
|
24
|
+
}
|
25
|
+
return result;
|
26
|
+
};
|
27
|
+
|
28
|
+
this.negotiateTransport = function(types, version, crossDomain, url)
|
29
|
+
{
|
30
|
+
for (var i = 0; i < _types.length; ++i)
|
31
|
+
{
|
32
|
+
var type = _types[i];
|
33
|
+
for (var j = 0; j < types.length; ++j)
|
34
|
+
{
|
35
|
+
if (type === types[j])
|
36
|
+
{
|
37
|
+
var transport = _transports[type];
|
38
|
+
if (transport.accept(version, crossDomain, url) === true)
|
39
|
+
{
|
40
|
+
return transport;
|
41
|
+
}
|
42
|
+
}
|
43
|
+
}
|
44
|
+
}
|
45
|
+
return null;
|
46
|
+
};
|
47
|
+
|
48
|
+
this.add = function(type, transport, index)
|
49
|
+
{
|
50
|
+
var existing = false;
|
51
|
+
for (var i = 0; i < _types.length; ++i)
|
52
|
+
{
|
53
|
+
if (_types[i] === type)
|
54
|
+
{
|
55
|
+
existing = true;
|
56
|
+
break;
|
57
|
+
}
|
58
|
+
}
|
59
|
+
|
60
|
+
if (!existing)
|
61
|
+
{
|
62
|
+
if (typeof index !== 'number')
|
63
|
+
{
|
64
|
+
_types.push(type);
|
65
|
+
}
|
66
|
+
else
|
67
|
+
{
|
68
|
+
_types.splice(index, 0, type);
|
69
|
+
}
|
70
|
+
_transports[type] = transport;
|
71
|
+
}
|
72
|
+
|
73
|
+
return !existing;
|
74
|
+
};
|
75
|
+
|
76
|
+
this.find = function(type)
|
77
|
+
{
|
78
|
+
for (var i = 0; i < _types.length; ++i)
|
79
|
+
{
|
80
|
+
if (_types[i] === type)
|
81
|
+
{
|
82
|
+
return _transports[type];
|
83
|
+
}
|
84
|
+
}
|
85
|
+
return null;
|
86
|
+
};
|
87
|
+
|
88
|
+
this.remove = function(type)
|
89
|
+
{
|
90
|
+
for (var i = 0; i < _types.length; ++i)
|
91
|
+
{
|
92
|
+
if (_types[i] === type)
|
93
|
+
{
|
94
|
+
_types.splice(i, 1);
|
95
|
+
var transport = _transports[type];
|
96
|
+
delete _transports[type];
|
97
|
+
return transport;
|
98
|
+
}
|
99
|
+
}
|
100
|
+
return null;
|
101
|
+
};
|
102
|
+
|
103
|
+
this.clear = function()
|
104
|
+
{
|
105
|
+
_types = [];
|
106
|
+
_transports = {};
|
107
|
+
};
|
108
|
+
|
109
|
+
this.reset = function()
|
110
|
+
{
|
111
|
+
for (var i = 0; i < _types.length; ++i)
|
112
|
+
{
|
113
|
+
_transports[_types[i]].reset();
|
114
|
+
}
|
115
|
+
};
|
116
|
+
};
|
@@ -0,0 +1,58 @@
|
|
1
|
+
org.cometd.Utils = {};
|
2
|
+
|
3
|
+
org.cometd.Utils.isString = function(value)
|
4
|
+
{
|
5
|
+
if (value === undefined || value === null)
|
6
|
+
{
|
7
|
+
return false;
|
8
|
+
}
|
9
|
+
return typeof value === 'string' || value instanceof String;
|
10
|
+
};
|
11
|
+
|
12
|
+
org.cometd.Utils.isArray = function(value)
|
13
|
+
{
|
14
|
+
if (value === undefined || value === null)
|
15
|
+
{
|
16
|
+
return false;
|
17
|
+
}
|
18
|
+
return value instanceof Array;
|
19
|
+
};
|
20
|
+
|
21
|
+
/**
|
22
|
+
* Returns whether the given element is contained into the given array.
|
23
|
+
* @param element the element to check presence for
|
24
|
+
* @param array the array to check for the element presence
|
25
|
+
* @return the index of the element, if present, or a negative index if the element is not present
|
26
|
+
*/
|
27
|
+
org.cometd.Utils.inArray = function(element, array)
|
28
|
+
{
|
29
|
+
for (var i = 0; i < array.length; ++i)
|
30
|
+
{
|
31
|
+
if (element === array[i])
|
32
|
+
{
|
33
|
+
return i;
|
34
|
+
}
|
35
|
+
}
|
36
|
+
return -1;
|
37
|
+
};
|
38
|
+
|
39
|
+
org.cometd.Utils.setTimeout = function(cometd, funktion, delay)
|
40
|
+
{
|
41
|
+
return window.setTimeout(function()
|
42
|
+
{
|
43
|
+
try
|
44
|
+
{
|
45
|
+
cometd._debug('Invoking timed function', funktion);
|
46
|
+
funktion();
|
47
|
+
}
|
48
|
+
catch (x)
|
49
|
+
{
|
50
|
+
cometd._debug('Exception invoking timed function', funktion, x);
|
51
|
+
}
|
52
|
+
}, delay);
|
53
|
+
};
|
54
|
+
|
55
|
+
org.cometd.Utils.clearTimeout = function(timeoutHandle)
|
56
|
+
{
|
57
|
+
window.clearTimeout(timeoutHandle);
|
58
|
+
};
|