public void UpdateAttemptState(ConnectionStateBase newState) { lock (_syncLock) switch (newState.State) { case ConnectionState.Connecting: Attempts.Add(new ConnectionAttempt(Now())); break; case ConnectionState.Failed: case ConnectionState.Closed: case ConnectionState.Connected: Reset(); break; case ConnectionState.Suspended: case ConnectionState.Disconnected: if (newState.Exception != null) { RecordAttemptFailure(newState.State, newState.Exception); } else { RecordAttemptFailure(newState.State, newState.Error); } break; } }
public void UpdateAttemptState(ConnectionStateBase newState, ILogger logger) { switch (newState.State) { case ConnectionState.Connecting: logger.Debug("Recording connection attempt."); Attempts.Add(new ConnectionAttempt(_now())); break; case ConnectionState.Failed: case ConnectionState.Closed: case ConnectionState.Connected: logger.Debug("Resetting Attempts collection."); Reset(); break; case ConnectionState.Suspended: case ConnectionState.Disconnected: logger.Debug($"Recording failed attempt for state {newState.State}."); if (newState.Exception != null) { RecordAttemptFailure(newState.State, newState.Exception); } else { RecordAttemptFailure(newState.State, newState.Error); } break; } }
public ConnectionStateChange UpdateState(ConnectionStateBase state, ILogger logger) { if (!state.IsUpdate && state.State == State) { return(null); } if (logger.IsDebug) { logger.Debug($"Updating state to `{state.State}`"); } var oldState = State; var newState = state.State; CurrentStateObject = state; ErrorReason = state.Error; var connectionEvent = oldState == newState ? ConnectionEvent.Update : newState.ToConnectionEvent(); return(new ConnectionStateChange(connectionEvent, oldState, newState, state.RetryIn, ErrorReason)); }
internal void UpdateState(ConnectionStateBase state) { if (state.State == State) { return; } if (Logger.IsDebug) { Logger.Debug($"Connection notifying subscribers for state change `{state.State}`"); } var oldState = ConnectionState.State; var newState = state.State; ConnectionState = state; ErrorReason = state.Error; var stateChange = new ConnectionStateChange(oldState, newState, state.RetryIn, ErrorReason); var internalHandlers = Volatile.Read(ref InternalStateChanged); //Make sure we get all the subscribers on all threads var externalHandlers = Volatile.Read(ref ConnectionStateChanged); //Make sure we get all the subscribers on all threads internalHandlers(this, stateChange); RealtimeClient.NotifyExternalClients(() => { try { externalHandlers(this, stateChange); } catch (Exception ex) { Logger.Error("Error notifying Connection state changed handlers", ex); } Emit(newState, stateChange); }); }
public Task SetState(ConnectionStateBase state, bool skipAttach) { State = state; LastSetState = state; return(TaskConstants.BooleanTrue); }
public Task SetState(ConnectionStateBase newState, bool skipAttach = false) { if (Logger.IsDebug) { Logger.Debug($"xx Changing state from {ConnectionState} => {newState.State}. SkipAttach = {skipAttach}."); } _inTransitionToState = newState; return(ExecuteOnManagerThread(async() => { try { lock (_stateSyncLock) { if (State.State == newState.State) { if (Logger.IsDebug) { Logger.Debug($"xx State is already {State.State}. Skipping SetState action."); } return; } //Abort any timers on the old state State.AbortTimer(); if (Logger.IsDebug) { Logger.Debug($"xx {newState.State}: BeforeTransition"); } newState.BeforeTransition(); AttemptsInfo.UpdateAttemptState(newState); Connection.UpdateState(newState); } if (skipAttach == false) { if (Logger.IsDebug) { Logger.Debug($"xx {newState.State}: Attaching state "); } await newState.OnAttachToContext(); } else if (Logger.IsDebug) { Logger.Debug($"xx {newState.State}: Skipping attaching."); } await ProcessQueuedMessages(); } catch (AblyException ex) { Logger.Error("Error attaching to context", ex); lock (_transportQueueLock) _queuedTransportMessages.Clear(); Connection.UpdateState(newState); newState.AbortTimer(); if (newState.State != Realtime.ConnectionState.Failed) { SetState(new ConnectionFailedState(this, ex.ErrorInfo)); } } finally { //Clear the state in transition only if the current state hasn't updated it if (_inTransitionToState == newState) { _inTransitionToState = null; } } })); }
public Task SetState(ConnectionStateBase newState, bool skipAttach = false) { if (Logger.IsDebug) { Logger.Debug( $"xx Changing state from {ConnectionState} => {newState.State}. SkipAttach = {skipAttach}."); } _inTransitionToState = newState; return(ExecuteOnManagerThread(async() => { try { lock (_stateSyncLock) { if (!newState.IsUpdate) { if (State.State == newState.State) { if (Logger.IsDebug) { Logger.Debug($"xx State is already {State.State}. Skipping SetState action."); } return; } AttemptsInfo.UpdateAttemptState(newState); State.AbortTimer(); } if (Logger.IsDebug) { Logger.Debug($"xx {newState.State}: BeforeTransition"); } newState.BeforeTransition(); if (Logger.IsDebug) { Logger.Debug($"xx {newState.State}: BeforeTransition end"); } Connection.UpdateState(newState); } if (skipAttach == false) { if (Logger.IsDebug) { Logger.Debug($"xx {newState.State}: Attaching state "); } await newState.OnAttachToContext(); } else if (Logger.IsDebug) { Logger.Debug($"xx {newState.State}: Skipping attaching."); } await ProcessQueuedMessages(); } catch (AblyException ex) { Logger.Error("Error attaching to context", ex); _queuedTransportMessages = new ConcurrentQueue <ProtocolMessage>(); Connection.UpdateState(newState); newState.AbortTimer(); // RSA4c2 & RSA4d if (newState.State == ConnectionState.Connecting && ex.ErrorInfo.Code == 80019 & !ex.ErrorInfo.IsForbiddenError) { await SetState(new ConnectionDisconnectedState(this, ex.ErrorInfo, Logger)); } else if (newState.State != ConnectionState.Failed) { await SetState(new ConnectionFailedState(this, ex.ErrorInfo, Logger)); } } finally { // Clear the state in transition only if the current state hasn't updated it if (_inTransitionToState == newState) { _inTransitionToState = null; } } })); }