ably 1.1.2 → 1.1.6
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 +4 -4
- data/.github/workflows/check.yml +27 -0
- data/CHANGELOG.md +67 -0
- data/COPYRIGHT +1 -0
- data/LICENSE +172 -11
- data/MAINTAINERS.md +1 -0
- data/README.md +11 -21
- data/SPEC.md +1020 -922
- data/ably.gemspec +4 -4
- data/lib/ably/auth.rb +12 -2
- data/lib/ably/exceptions.rb +2 -2
- data/lib/ably/modules/ably.rb +11 -1
- data/lib/ably/realtime/channel.rb +7 -11
- data/lib/ably/realtime/channel/channel_manager.rb +2 -2
- data/lib/ably/realtime/channel/channel_properties.rb +24 -0
- data/lib/ably/realtime/client.rb +9 -0
- data/lib/ably/realtime/connection.rb +5 -4
- data/lib/ably/realtime/connection/websocket_transport.rb +67 -1
- data/lib/ably/realtime/presence.rb +0 -14
- data/lib/ably/rest/channel.rb +27 -19
- data/lib/ably/rest/client.rb +31 -15
- data/lib/ably/rest/middleware/fail_if_unsupported_mime_type.rb +4 -1
- data/lib/ably/version.rb +1 -1
- data/spec/acceptance/realtime/auth_spec.rb +3 -3
- data/spec/acceptance/realtime/channel_spec.rb +10 -0
- data/spec/acceptance/realtime/client_spec.rb +72 -16
- data/spec/acceptance/realtime/connection_failures_spec.rb +26 -11
- data/spec/acceptance/realtime/connection_spec.rb +36 -17
- data/spec/acceptance/realtime/presence_history_spec.rb +0 -58
- data/spec/acceptance/realtime/presence_spec.rb +54 -0
- data/spec/acceptance/realtime/push_admin_spec.rb +3 -19
- data/spec/acceptance/rest/auth_spec.rb +6 -75
- data/spec/acceptance/rest/base_spec.rb +8 -4
- data/spec/acceptance/rest/channel_spec.rb +42 -4
- data/spec/acceptance/rest/client_spec.rb +121 -26
- data/spec/acceptance/rest/push_admin_spec.rb +3 -19
- data/spec/shared/client_initializer_behaviour.rb +131 -8
- data/spec/spec_helper.rb +1 -0
- data/spec/support/serialization_helper.rb +21 -0
- data/spec/support/test_app.rb +2 -2
- data/spec/unit/realtime/client_spec.rb +19 -6
- metadata +20 -15
- data/.travis.yml +0 -19
data/lib/ably/rest/client.rb
CHANGED
@@ -3,6 +3,9 @@ require 'json'
|
|
3
3
|
require 'logger'
|
4
4
|
require 'uri'
|
5
5
|
|
6
|
+
require 'typhoeus'
|
7
|
+
require 'typhoeus/adapters/faraday'
|
8
|
+
|
6
9
|
require 'ably/rest/middleware/exceptions'
|
7
10
|
|
8
11
|
module Ably
|
@@ -32,6 +35,13 @@ module Ably
|
|
32
35
|
|
33
36
|
FALLBACK_RETRY_TIMEOUT = 10 * 60
|
34
37
|
|
38
|
+
# Faraday 1.0 introduced new error types, however we want to support Faraday <1 too which only used Faraday::ClientError
|
39
|
+
FARADAY_CLIENT_OR_SERVER_ERRORS = if defined?(Faraday::ParsingError)
|
40
|
+
[Faraday::ClientError, Faraday::ServerError, Faraday::ConnectionFailed, Faraday::SSLError, Faraday::ParsingError]
|
41
|
+
else
|
42
|
+
Faraday::ClientError
|
43
|
+
end
|
44
|
+
|
35
45
|
def_delegators :auth, :client_id, :auth_options
|
36
46
|
|
37
47
|
# Custom environment to use such as 'sandbox' when testing the client library against an alternate Ably environment
|
@@ -174,16 +184,18 @@ module Ably
|
|
174
184
|
@idempotent_rest_publishing = options.delete(:idempotent_rest_publishing) || Ably.major_minor_version_numeric > 1.1
|
175
185
|
|
176
186
|
|
177
|
-
if options[:fallback_hosts_use_default] && options[:
|
178
|
-
raise ArgumentError, "fallback_hosts_use_default cannot be set to
|
187
|
+
if options[:fallback_hosts_use_default] && options[:fallback_hosts]
|
188
|
+
raise ArgumentError, "fallback_hosts_use_default cannot be set to try when fallback_hosts is also provided"
|
179
189
|
end
|
180
190
|
@fallback_hosts = case
|
181
191
|
when options.delete(:fallback_hosts_use_default)
|
182
192
|
Ably::FALLBACK_HOSTS
|
183
193
|
when options_fallback_hosts = options.delete(:fallback_hosts)
|
184
194
|
options_fallback_hosts
|
185
|
-
when
|
195
|
+
when custom_host || options[:realtime_host] || custom_port || custom_tls_port
|
186
196
|
[]
|
197
|
+
when environment
|
198
|
+
CUSTOM_ENVIRONMENT_FALLBACKS_SUFFIXES.map { |host| "#{environment}#{host}" }
|
187
199
|
else
|
188
200
|
Ably::FALLBACK_HOSTS
|
189
201
|
end
|
@@ -195,6 +207,8 @@ module Ably
|
|
195
207
|
@http_defaults = HTTP_DEFAULTS.dup
|
196
208
|
options.each do |key, val|
|
197
209
|
if http_key = key[/^http_(.+)/, 1]
|
210
|
+
# Typhoeus converts decimal durations to milliseconds, so 0.0001 timeout is treated as 0 (no timeout)
|
211
|
+
val = 0.001 if val.kind_of?(Numeric) && (val > 0) && (val < 0.001)
|
198
212
|
@http_defaults[http_key.to_sym] = val if val && @http_defaults.has_key?(http_key.to_sym)
|
199
213
|
end
|
200
214
|
end
|
@@ -336,14 +350,14 @@ module Ably
|
|
336
350
|
#
|
337
351
|
# @return [Ably::Models::HttpPaginatedResponse<>]
|
338
352
|
def request(method, path, params = {}, body = nil, headers = {}, options = {})
|
339
|
-
raise "Method #{method.to_s.upcase} not supported" unless
|
353
|
+
raise "Method #{method.to_s.upcase} not supported" unless %i(get put patch post delete).include?(method.to_sym)
|
340
354
|
|
341
355
|
response = case method.to_sym
|
342
|
-
when :get
|
356
|
+
when :get, :delete
|
343
357
|
reauthorize_on_authorization_failure do
|
344
358
|
send_request(method, path, params, headers: headers)
|
345
359
|
end
|
346
|
-
when :post
|
360
|
+
when :post, :patch, :put
|
347
361
|
path_with_params = Addressable::URI.new
|
348
362
|
path_with_params.query_values = params || {}
|
349
363
|
query = path_with_params.query
|
@@ -559,12 +573,14 @@ module Ably
|
|
559
573
|
request.options.context = {} if request.options.context.nil?
|
560
574
|
request.options.context[:request_id] = request_id
|
561
575
|
end
|
576
|
+
if options[:qs_params]
|
577
|
+
request.params.merge!(options[:qs_params])
|
578
|
+
end
|
562
579
|
unless options[:send_auth_header] == false
|
563
580
|
request.headers[:authorization] = auth.auth_header
|
564
|
-
|
565
|
-
|
566
|
-
|
567
|
-
end
|
581
|
+
|
582
|
+
options[:headers].to_h.merge(auth.extra_auth_headers).map do |key, val|
|
583
|
+
request.headers[key] = val
|
568
584
|
end
|
569
585
|
end
|
570
586
|
end.tap do
|
@@ -578,7 +594,7 @@ module Ably
|
|
578
594
|
end
|
579
595
|
end
|
580
596
|
|
581
|
-
rescue Faraday::TimeoutError,
|
597
|
+
rescue *([Faraday::TimeoutError, Ably::Exceptions::ServerError] + FARADAY_CLIENT_OR_SERVER_ERRORS) => error
|
582
598
|
retry_sequence_id ||= SecureRandom.urlsafe_base64(4)
|
583
599
|
time_passed = Time.now - requested_at
|
584
600
|
|
@@ -598,7 +614,7 @@ module Ably
|
|
598
614
|
case error
|
599
615
|
when Faraday::TimeoutError
|
600
616
|
raise Ably::Exceptions::ConnectionTimeout.new(error.message, nil, Ably::Exceptions::Codes::CONNECTION_TIMED_OUT, error, { request_id: request_id })
|
601
|
-
when
|
617
|
+
when *FARADAY_CLIENT_OR_SERVER_ERRORS
|
602
618
|
# request_id is also available in the request context
|
603
619
|
raise Ably::Exceptions::ConnectionError.new(error.message, nil, Ably::Exceptions::Codes::CONNECTION_FAILED, error, { request_id: request_id })
|
604
620
|
else
|
@@ -656,7 +672,7 @@ module Ably
|
|
656
672
|
}
|
657
673
|
end
|
658
674
|
|
659
|
-
# Return a Faraday middleware stack to initiate the Faraday::
|
675
|
+
# Return a Faraday middleware stack to initiate the Faraday::RackBuilder with
|
660
676
|
#
|
661
677
|
# @see http://mislav.uniqpath.com/2011/07/faraday-advanced-http/
|
662
678
|
def middleware
|
@@ -668,8 +684,8 @@ module Ably
|
|
668
684
|
|
669
685
|
setup_incoming_middleware builder, logger, fail_if_unsupported_mime_type: true
|
670
686
|
|
671
|
-
# Set Faraday's HTTP adapter
|
672
|
-
builder.adapter :
|
687
|
+
# Set Faraday's HTTP adapter with support for HTTP/2
|
688
|
+
builder.adapter :typhoeus, http_version: :httpv2_0
|
673
689
|
end
|
674
690
|
end
|
675
691
|
|
@@ -7,7 +7,10 @@ module Ably
|
|
7
7
|
class FailIfUnsupportedMimeType < Faraday::Response::Middleware
|
8
8
|
def on_complete(env)
|
9
9
|
unless env.response_headers['Ably-Middleware-Parsed'] == true
|
10
|
-
|
10
|
+
# Ignore empty body with success status code for no body response
|
11
|
+
return if env.body.to_s.empty? && env.status == 204
|
12
|
+
|
13
|
+
unless (500..599).include?(env.status)
|
11
14
|
raise Ably::Exceptions::InvalidResponseBody,
|
12
15
|
"Content Type #{env.response_headers['Content-Type']} is not supported by this client library"
|
13
16
|
end
|
data/lib/ably/version.rb
CHANGED
@@ -1058,7 +1058,7 @@ describe Ably::Realtime::Auth, :event_machine do
|
|
1058
1058
|
|
1059
1059
|
it 'disconnected includes and invalid signature message' do
|
1060
1060
|
client.connection.once(:disconnected) do |state_change|
|
1061
|
-
expect(state_change.reason.message.match(/
|
1061
|
+
expect(state_change.reason.message.match(/signature verification failed/i)).to_not be_nil
|
1062
1062
|
expect(state_change.reason.code).to eql(40144)
|
1063
1063
|
stop_reactor
|
1064
1064
|
end
|
@@ -1111,7 +1111,7 @@ describe Ably::Realtime::Auth, :event_machine do
|
|
1111
1111
|
|
1112
1112
|
it 'authentication fails and reason for disconnection is invalid signature' do
|
1113
1113
|
client.connection.once(:disconnected) do |state_change|
|
1114
|
-
expect(state_change.reason.message.match(/
|
1114
|
+
expect(state_change.reason.message.match(/signature verification failed/i)).to_not be_nil
|
1115
1115
|
expect(state_change.reason.code).to eql(40144)
|
1116
1116
|
stop_reactor
|
1117
1117
|
end
|
@@ -1143,7 +1143,7 @@ describe Ably::Realtime::Auth, :event_machine do
|
|
1143
1143
|
|
1144
1144
|
it 'fails with an invalid signature error' do
|
1145
1145
|
client.connection.once(:disconnected) do |state_change|
|
1146
|
-
expect(state_change.reason.message.match(/
|
1146
|
+
expect(state_change.reason.message.match(/signature verification failed/i)).to_not be_nil
|
1147
1147
|
expect(state_change.reason.code).to eql(40144)
|
1148
1148
|
stop_reactor
|
1149
1149
|
end
|
@@ -83,6 +83,16 @@ describe Ably::Realtime::Channel, :event_machine do
|
|
83
83
|
end
|
84
84
|
end
|
85
85
|
|
86
|
+
it 'sets attach_serial property after the attachment (#RTL15a)' do
|
87
|
+
expect(channel.properties.attach_serial).to be_nil
|
88
|
+
|
89
|
+
channel.attach
|
90
|
+
channel.on(:attached) do
|
91
|
+
expect(channel.properties.attach_serial).to_not be_nil
|
92
|
+
stop_reactor
|
93
|
+
end
|
94
|
+
end
|
95
|
+
|
86
96
|
it 'sends an ATTACH and waits for an ATTACHED (#RTL4c)' do
|
87
97
|
connection.once(:connected) do
|
88
98
|
attach_count = 0
|
@@ -87,22 +87,6 @@ describe Ably::Realtime::Client, :event_machine do
|
|
87
87
|
end
|
88
88
|
end
|
89
89
|
end
|
90
|
-
|
91
|
-
context 'with client_id' do
|
92
|
-
let(:client_options) do
|
93
|
-
default_options.merge(client_id: random_str)
|
94
|
-
end
|
95
|
-
it 'connects using token auth' do
|
96
|
-
run_reactor do
|
97
|
-
connection.on(:connected) do
|
98
|
-
expect(connection.state).to eq(:connected)
|
99
|
-
expect(auth_params[:access_token]).to_not be_nil
|
100
|
-
expect(auth_params[:key]).to be_nil
|
101
|
-
stop_reactor
|
102
|
-
end
|
103
|
-
end
|
104
|
-
end
|
105
|
-
end
|
106
90
|
end
|
107
91
|
end
|
108
92
|
|
@@ -249,6 +233,8 @@ describe Ably::Realtime::Client, :event_machine do
|
|
249
233
|
|
250
234
|
context '#request (#RSC19*)' do
|
251
235
|
let(:client_options) { default_options.merge(key: api_key) }
|
236
|
+
let(:device_id) { random_str }
|
237
|
+
let(:endpoint) { subject.rest_client.endpoint }
|
252
238
|
|
253
239
|
context 'get' do
|
254
240
|
it 'returns an HttpPaginatedResponse object' do
|
@@ -297,6 +283,76 @@ describe Ably::Realtime::Client, :event_machine do
|
|
297
283
|
end
|
298
284
|
end
|
299
285
|
end
|
286
|
+
|
287
|
+
|
288
|
+
context 'post', :webmock do
|
289
|
+
before do
|
290
|
+
stub_request(:delete, "#{endpoint}/push/deviceRegistrations/#{device_id}/resetUpdateToken").
|
291
|
+
to_return(status: 200, body: '{}', headers: { 'Content-Type' => 'application/json' })
|
292
|
+
end
|
293
|
+
|
294
|
+
it 'supports post' do
|
295
|
+
subject.request(:delete, "push/deviceRegistrations/#{device_id}/resetUpdateToken").callback do |response|
|
296
|
+
expect(response).to be_success
|
297
|
+
stop_reactor
|
298
|
+
end
|
299
|
+
end
|
300
|
+
end
|
301
|
+
|
302
|
+
context 'delete', :webmock do
|
303
|
+
before do
|
304
|
+
stub_request(:delete, "#{endpoint}/push/channelSubscriptions?deviceId=#{device_id}").
|
305
|
+
to_return(status: 200, body: '{}', headers: { 'Content-Type' => 'application/json' })
|
306
|
+
end
|
307
|
+
|
308
|
+
it 'supports delete' do
|
309
|
+
subject.request(:delete, "/push/channelSubscriptions", { deviceId: device_id}).callback do |response|
|
310
|
+
expect(response).to be_success
|
311
|
+
stop_reactor
|
312
|
+
end
|
313
|
+
end
|
314
|
+
end
|
315
|
+
|
316
|
+
context 'patch', :webmock do
|
317
|
+
let(:body_params) { { 'metadata' => { 'key' => 'value' } } }
|
318
|
+
|
319
|
+
before do
|
320
|
+
stub_request(:patch, "#{endpoint}/push/deviceRegistrations/#{device_id}")
|
321
|
+
.with(body: serialize_body(body_params, protocol))
|
322
|
+
.to_return(status: 200, body: '{}', headers: { 'Content-Type' => 'application/json' })
|
323
|
+
end
|
324
|
+
|
325
|
+
it 'supports patch' do
|
326
|
+
subject.request(:patch, "/push/deviceRegistrations/#{device_id}", {}, body_params).callback do |response|
|
327
|
+
expect(response).to be_success
|
328
|
+
stop_reactor
|
329
|
+
end
|
330
|
+
end
|
331
|
+
end
|
332
|
+
|
333
|
+
context 'put', :webmock do
|
334
|
+
let(:body_params) do
|
335
|
+
{
|
336
|
+
'id' => random_str,
|
337
|
+
'platform' => 'ios',
|
338
|
+
'formFactor' => 'phone',
|
339
|
+
'metadata' => { 'key' => 'value' }
|
340
|
+
}
|
341
|
+
end
|
342
|
+
|
343
|
+
before do
|
344
|
+
stub_request(:put, "#{endpoint}/push/deviceRegistrations/#{device_id}")
|
345
|
+
.with(body: serialize_body(body_params, protocol))
|
346
|
+
.to_return(status: 200, body: '{}', headers: { 'Content-Type' => 'application/json' })
|
347
|
+
end
|
348
|
+
|
349
|
+
it 'supports put' do
|
350
|
+
subject.request(:put, "/push/deviceRegistrations/#{device_id}", {}, body_params).callback do |response|
|
351
|
+
expect(response).to be_success
|
352
|
+
stop_reactor
|
353
|
+
end
|
354
|
+
end
|
355
|
+
end
|
300
356
|
end
|
301
357
|
|
302
358
|
context '#publish (#TBC)' do
|
@@ -156,10 +156,20 @@ describe Ably::Realtime::Connection, 'failures', :event_machine do
|
|
156
156
|
|
157
157
|
stub_request(:get, auth_url).
|
158
158
|
to_return do |request|
|
159
|
-
|
160
|
-
|
161
|
-
|
162
|
-
|
159
|
+
sleep Ably::Rest::Client::HTTP_DEFAULTS.fetch(:request_timeout)
|
160
|
+
{ status: [500, "Internal Server Error"] }
|
161
|
+
end.then.
|
162
|
+
to_return(:status => 201, :body => token_response.to_json, :headers => { 'Content-Type' => 'application/json' })
|
163
|
+
|
164
|
+
stub_request(:get, 'https://internet-up.ably-realtime.com/is-the-internet-up.txt')
|
165
|
+
.with(
|
166
|
+
headers: {
|
167
|
+
'Accept-Encoding' => 'gzip, compressed',
|
168
|
+
'Connection' => 'close',
|
169
|
+
'Host' => 'internet-up.ably-realtime.com',
|
170
|
+
'User-Agent' => 'EventMachine HttpClient'
|
171
|
+
}
|
172
|
+
).to_return(status: 200, body: 'yes\n', headers: { 'Content-Type' => 'text/plain' })
|
163
173
|
end
|
164
174
|
|
165
175
|
specify 'the connection moves to the disconnected state and tries again, returning again to the disconnected state (#RSA4c, #RSA4c1, #RSA4c2)' do
|
@@ -1423,14 +1433,19 @@ describe Ably::Realtime::Connection, 'failures', :event_machine do
|
|
1423
1433
|
let(:expected_host) { "#{environment}-#{Ably::Realtime::Client::DOMAIN}" }
|
1424
1434
|
let(:client_options) { timeout_options.merge(environment: environment) }
|
1425
1435
|
|
1426
|
-
|
1427
|
-
|
1428
|
-
|
1429
|
-
|
1430
|
-
|
1436
|
+
context ':fallback_hosts_use_default is unset' do
|
1437
|
+
let(:max_time_in_state_for_tests) { 8 }
|
1438
|
+
let(:expected_hosts) { Ably::CUSTOM_ENVIRONMENT_FALLBACKS_SUFFIXES.map { |suffix| "#{environment}#{suffix}" } + [expected_host] }
|
1439
|
+
let(:fallback_hosts_used) { Array.new }
|
1440
|
+
|
1441
|
+
it 'uses fallback hosts by default' do
|
1442
|
+
allow(connection).to receive(:create_transport) do |host|
|
1443
|
+
fallback_hosts_used << host
|
1444
|
+
raise EventMachine::ConnectionError
|
1445
|
+
end
|
1431
1446
|
|
1432
|
-
connection.once(:suspended) do
|
1433
1447
|
connection.once(:suspended) do
|
1448
|
+
expect(fallback_hosts_used.uniq).to match_array(expected_hosts)
|
1434
1449
|
stop_reactor
|
1435
1450
|
end
|
1436
1451
|
end
|
@@ -1508,7 +1523,7 @@ describe Ably::Realtime::Connection, 'failures', :event_machine do
|
|
1508
1523
|
end
|
1509
1524
|
|
1510
1525
|
context 'with production environment' do
|
1511
|
-
let(:custom_hosts) { %w(
|
1526
|
+
let(:custom_hosts) { %w(a.ably-realtime.com b.ably-realtime.com) }
|
1512
1527
|
before do
|
1513
1528
|
stub_const 'Ably::FALLBACK_HOSTS', custom_hosts
|
1514
1529
|
end
|
@@ -77,18 +77,6 @@ describe Ably::Realtime::Connection, :event_machine do
|
|
77
77
|
end
|
78
78
|
end
|
79
79
|
end
|
80
|
-
|
81
|
-
context 'with implicit authorisation' do
|
82
|
-
let(:client_options) { default_options.merge(client_id: 'force_token_auth') }
|
83
|
-
|
84
|
-
it 'uses the token created by the implicit authorisation' do
|
85
|
-
expect(client.rest_client.auth).to receive(:request_token).once.and_call_original
|
86
|
-
|
87
|
-
connection.once(:connected) do
|
88
|
-
stop_reactor
|
89
|
-
end
|
90
|
-
end
|
91
|
-
end
|
92
80
|
end
|
93
81
|
|
94
82
|
context 'that expire' do
|
@@ -134,7 +122,7 @@ describe Ably::Realtime::Connection, :event_machine do
|
|
134
122
|
end
|
135
123
|
end
|
136
124
|
|
137
|
-
context 'with immediately expired token' do
|
125
|
+
context 'with immediately expired token and no fallback hosts' do
|
138
126
|
let(:ttl) { 0.001 }
|
139
127
|
let(:auth_requests) { [] }
|
140
128
|
let(:token_callback) do
|
@@ -143,7 +131,7 @@ describe Ably::Realtime::Connection, :event_machine do
|
|
143
131
|
Ably::Rest::Client.new(default_options).auth.request_token(ttl: ttl).token
|
144
132
|
end
|
145
133
|
end
|
146
|
-
let(:client_options) { default_options.merge(auth_callback: token_callback) }
|
134
|
+
let(:client_options) { default_options.merge(auth_callback: token_callback, fallback_hosts: []) }
|
147
135
|
|
148
136
|
it 'renews the token on connect, and makes one immediate subsequent attempt to obtain a new token (#RSA4b)' do
|
149
137
|
started_at = Time.now.to_f
|
@@ -158,7 +146,7 @@ describe Ably::Realtime::Connection, :event_machine do
|
|
158
146
|
end
|
159
147
|
|
160
148
|
context 'when disconnected_retry_timeout is 0.5 seconds' do
|
161
|
-
let(:client_options) { default_options.merge(disconnected_retry_timeout: 0.5, auth_callback: token_callback) }
|
149
|
+
let(:client_options) { default_options.merge(disconnected_retry_timeout: 0.5, auth_callback: token_callback, fallback_hosts: []) }
|
162
150
|
|
163
151
|
it 'renews the token on connect, and continues to attempt renew based on the retry schedule' do
|
164
152
|
disconnect_count = 0
|
@@ -184,7 +172,7 @@ describe Ably::Realtime::Connection, :event_machine do
|
|
184
172
|
end
|
185
173
|
|
186
174
|
context 'using implicit token auth' do
|
187
|
-
let(:client_options) { default_options.merge(use_token_auth: true, default_token_params: { ttl: ttl }) }
|
175
|
+
let(:client_options) { default_options.merge(use_token_auth: true, default_token_params: { ttl: ttl }, fallback_hosts: []) }
|
188
176
|
|
189
177
|
before do
|
190
178
|
stub_const 'Ably::Models::TokenDetails::TOKEN_EXPIRY_BUFFER', -10 # ensure client lib thinks token is still valid
|
@@ -453,7 +441,9 @@ describe Ably::Realtime::Connection, :event_machine do
|
|
453
441
|
end
|
454
442
|
end
|
455
443
|
|
456
|
-
context '#connect' do
|
444
|
+
context '#connect with no fallbacks' do
|
445
|
+
let(:client_options) { default_options.merge(fallback_hosts: []) }
|
446
|
+
|
457
447
|
it 'returns a SafeDeferrable that catches exceptions in callbacks and logs them' do
|
458
448
|
expect(connection.connect).to be_a(Ably::Util::SafeDeferrable)
|
459
449
|
stop_reactor
|
@@ -1179,6 +1169,7 @@ describe Ably::Realtime::Connection, :event_machine do
|
|
1179
1169
|
host: 'this.host.does.not.exist.com'
|
1180
1170
|
)
|
1181
1171
|
)
|
1172
|
+
allow(client).to receive(:fallback_hosts).and_return([])
|
1182
1173
|
|
1183
1174
|
connection.transition_state_machine! :disconnected
|
1184
1175
|
end
|
@@ -1879,5 +1870,33 @@ describe Ably::Realtime::Connection, :event_machine do
|
|
1879
1870
|
end
|
1880
1871
|
end
|
1881
1872
|
end
|
1873
|
+
|
1874
|
+
context 'transport_params (#RTC1f)' do
|
1875
|
+
let(:client_options) { default_options.merge(transport_params: { 'extra_param' => 'extra_param' }) }
|
1876
|
+
|
1877
|
+
it 'pases transport_params to query' do
|
1878
|
+
expect(EventMachine).to receive(:connect) do |host, port, transport, object, url|
|
1879
|
+
uri = URI.parse(url)
|
1880
|
+
expect(CGI::parse(uri.query)['extra_param'][0]).to eq('extra_param')
|
1881
|
+
stop_reactor
|
1882
|
+
end
|
1883
|
+
|
1884
|
+
client
|
1885
|
+
end
|
1886
|
+
|
1887
|
+
context 'when changing default param' do
|
1888
|
+
let(:client_options) { default_options.merge(transport_params: { v: '1.0' }) }
|
1889
|
+
|
1890
|
+
it 'overrides default param (#RTC1f1)' do
|
1891
|
+
expect(EventMachine).to receive(:connect) do |host, port, transport, object, url|
|
1892
|
+
uri = URI.parse(url)
|
1893
|
+
expect(CGI::parse(uri.query)['v'][0]).to eq('1.0')
|
1894
|
+
stop_reactor
|
1895
|
+
end
|
1896
|
+
|
1897
|
+
client
|
1898
|
+
end
|
1899
|
+
end
|
1900
|
+
end
|
1882
1901
|
end
|
1883
1902
|
end
|