Skip to content

Commit 15427a0

Browse files
authored
Merge pull request #449 from splitio/sse-retries
Retry with backoff if get an HTTP error opening the SSE connection
2 parents ec3637a + 1447cfe commit 15427a0

6 files changed

Lines changed: 21 additions & 18 deletions

File tree

lib/splitclient-rb/engine/auth_api_client.rb

Lines changed: 9 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -59,11 +59,7 @@ def process_error(response)
5959

6060
def process_success(response, start)
6161
@config.logger.debug("Success connection to: #{@config.auth_service_url}") if @config.debug_enabled
62-
63-
bucket = BinarySearchLatencyTracker.get_bucket((Time.now - start) * 1000.0)
64-
@telemetry_runtime_producer.record_sync_latency(Telemetry::Domain::Constants::TOKEN_SYNC, bucket)
65-
timestamp = (Time.now.to_f * 1000.0).to_i
66-
@telemetry_runtime_producer.record_successful_sync(Telemetry::Domain::Constants::TOKEN_SYNC, timestamp)
62+
record_telemetry(start)
6763

6864
body_json = JSON.parse(response.body, symbolize_names: true)
6965
push_enabled = body_json[:pushEnabled]
@@ -77,7 +73,7 @@ def process_success(response, start)
7773
@telemetry_runtime_producer.record_token_refreshes
7874
end
7975

80-
{ push_enabled: push_enabled, token: token, channels: channels, exp: exp, retry: false }
76+
{ push_enabled: push_enabled, token: token, channels: channels, exp: exp, retry: true }
8177
end
8278

8379
def control_channels(channels_string)
@@ -88,6 +84,13 @@ def control_channels(channels_string)
8884

8985
channels_string.gsub(control_sec, "#{prefix}#{control_sec}")
9086
end
87+
88+
def record_telemetry(start)
89+
bucket = BinarySearchLatencyTracker.get_bucket((Time.now - start) * 1000.0)
90+
@telemetry_runtime_producer.record_sync_latency(Telemetry::Domain::Constants::TOKEN_SYNC, bucket)
91+
timestamp = (Time.now.to_f * 1000.0).to_i
92+
@telemetry_runtime_producer.record_successful_sync(Telemetry::Domain::Constants::TOKEN_SYNC, timestamp)
93+
end
9194
end
9295
end
9396
end

lib/splitclient-rb/engine/back_off.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22

33
module SplitIoClient
44
module Engine
5-
BACKOFF_MAX_ALLOWED = 1.8
5+
BACKOFF_MAX_ALLOWED = 1800
66
class BackOff
77
def initialize(back_off_base, attempt = 0, max_allowed = BACKOFF_MAX_ALLOWED)
88
@attempt = attempt

lib/splitclient-rb/engine/push_manager.rb

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,6 @@ def initialize(config, sse_handler, api_key, telemetry_runtime_producer)
1414

1515
def start_sse
1616
response = @auth_api_client.authenticate(@api_key)
17-
1817
@config.logger.debug("Auth service response push_enabled: #{response[:push_enabled]}") if @config.debug_enabled
1918

2019
if response[:push_enabled] && @sse_handler.start(response[:token], response[:channels])
@@ -26,7 +25,6 @@ def start_sse
2625
end
2726

2827
stop_sse
29-
3028
schedule_next_token_refresh(@back_off.interval) if response[:retry]
3129
false
3230
rescue StandardError => e
@@ -35,7 +33,8 @@ def start_sse
3533

3634
def stop_sse
3735
@sse_handler.stop
38-
SplitIoClient::Helpers::ThreadHelper.stop(:schedule_next_token_refresh, @config)
36+
rescue StandardError => e
37+
@config.logger.error(e.inspect)
3938
end
4039

4140
private

lib/splitclient-rb/engine/synchronizer.rb

Lines changed: 7 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,6 @@ class Synchronizer
66
include SplitIoClient::Cache::Fetchers
77
include SplitIoClient::Cache::Senders
88

9-
ON_DEMAND_FETCH_BACKOFF_BASE_SECONDS = 10
10-
ON_DEMAND_FETCH_BACKOFF_MAX_WAIT_SECONDS = 60
119
ON_DEMAND_FETCH_BACKOFF_MAX_RETRIES = 10
1210

1311
def initialize(
@@ -27,6 +25,9 @@ def initialize(
2725
@telemetry_synchronizer = params[:telemetry_synchronizer]
2826
@impressions_sender_adapter = params[:impressions_sender_adapter]
2927
@unique_keys_tracker = params[:unique_keys_tracker]
28+
29+
@splits_sync_backoff = Engine::BackOff.new(10, 0, 60)
30+
@segments_sync_backoff = Engine::BackOff.new(10, 0, 60)
3031
end
3132

3233
def sync_all(asynchronous = true)
@@ -140,7 +141,7 @@ def fetch_segment(name, target_change_number)
140141

141142
def attempt_segment_sync(name, target_cn, fetch_options, max_retries, retry_delay_seconds, with_backoff)
142143
remaining_attempts = max_retries
143-
backoff = Engine::BackOff.new(ON_DEMAND_FETCH_BACKOFF_BASE_SECONDS, 0, ON_DEMAND_FETCH_BACKOFF_MAX_WAIT_SECONDS) if with_backoff
144+
@segments_sync_backoff.reset
144145

145146
loop do
146147
remaining_attempts -= 1
@@ -150,14 +151,14 @@ def attempt_segment_sync(name, target_cn, fetch_options, max_retries, retry_dela
150151
return sync_result(true, remaining_attempts) if target_cn <= @segments_repository.get_change_number(name).to_i
151152
return sync_result(false, remaining_attempts) if remaining_attempts <= 0
152153

153-
delay = with_backoff ? backoff.interval : retry_delay_seconds
154+
delay = with_backoff ? @segments_sync_backoff.interval : retry_delay_seconds
154155
sleep(delay)
155156
end
156157
end
157158

158159
def attempt_splits_sync(target_cn, fetch_options, max_retries, retry_delay_seconds, with_backoff)
159160
remaining_attempts = max_retries
160-
backoff = Engine::BackOff.new(ON_DEMAND_FETCH_BACKOFF_BASE_SECONDS, 0, ON_DEMAND_FETCH_BACKOFF_MAX_WAIT_SECONDS) if with_backoff
161+
@splits_sync_backoff.reset
161162

162163
loop do
163164
remaining_attempts -= 1
@@ -167,7 +168,7 @@ def attempt_splits_sync(target_cn, fetch_options, max_retries, retry_delay_secon
167168
return sync_result(true, remaining_attempts, result[:segment_names]) if target_cn <= @splits_repository.get_change_number
168169
return sync_result(false, remaining_attempts, result[:segment_names]) if remaining_attempts <= 0
169170

170-
delay = with_backoff ? backoff.interval : retry_delay_seconds
171+
delay = with_backoff ? @splits_sync_backoff.interval : retry_delay_seconds
171172
sleep(delay)
172173
end
173174
end

spec/engine/auth_api_client_spec.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,7 @@
2222

2323
expect(response[:push_enabled]).to eq(true)
2424
expect(response[:channels]).to eq('xxxx_xxxx_segments%2Cxxxx_xxxx_splits%2C%5B%3Foccupancy%3Dmetrics.publishers%5Dcontrol_pri%2C%5B%3Foccupancy%3Dmetrics.publishers%5Dcontrol_sec')
25-
expect(response[:retry]).to eq(false)
25+
expect(response[:retry]).to eq(true)
2626
end
2727

2828
it 'auth server return 500' do

spec/engine/sync_manager_spec.rb

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -103,7 +103,7 @@
103103
sleep(2)
104104
expect(a_request(:get, 'https://sdk.split.io/api/splitChanges?since=-1')).to have_been_made.once
105105

106-
expect(config.threads.size).to eq(7)
106+
expect(config.threads.size).to eq(8)
107107
end
108108
end
109109

0 commit comments

Comments
 (0)