protected override bool ShouldRetryImpl(RetryState retryStateObj) { Contract.Assert(retryStateObj is RetryStateEx); RetryStateEx retryState = (RetryStateEx)retryStateObj; // Calculate the delay as exponential value based on the number of retries. retryState.Delay = RetryPolicyUtils.CalcExponentialRetryDelay( retryState.RetryCount, _intervalFactor, _minInterval, _maxInterval); // Add the delay to the total retry time retryState.TotalRetryTime = retryState.TotalRetryTime + retryState.Delay; // Calculate the maximum total retry time depending on how long ago was the task (this retry policy) started. // Longer running tasks are less eager to abort since, more work is has been done. TimeSpan totalRetryTimeLimit = checked (TimeSpan.FromMilliseconds( Math.Max( Math.Min( _stopwatch.ElapsedMilliseconds * _totalRetryTimeLimitRate, _maxTotalRetryTimeLimit.TotalMilliseconds), _minTotalRetryTimeLimit.TotalMilliseconds))); if (retryState.TotalRetryTime <= totalRetryTimeLimit) { return(true); } retryState.Delay = TimeSpan.Zero; return(false); }
/// <summary> /// Notifies the subscribers whenever an error is ignored on retry. /// </summary> /// <param name="retryState">The state of current retry attempt.</param> protected virtual void OnIgnoreErrorOccurred(RetryState retryState) { var ignoreErrorOccurred = IgnoreErrorOccurred; if (ignoreErrorOccurred != null) { ignoreErrorOccurred(retryState); } }
/// <summary> /// Notifies the subscribers whenever a retry condition is encountered. /// </summary> /// <param name="retryState">The state of current retry attempt.</param> protected virtual void OnRetryOccurred(RetryState retryState) { var retryOccurred = RetryOccurred; if (retryOccurred != null) { retryOccurred(retryState); } }
private static void DataConnectionFailureRetry(RetryState retryState) { Logger.Write(LogLevel.Normal, string.Format(CultureInfo.InvariantCulture, "Connection retry number {0}. Delaying {1} ms before retry. Exception: {2}", retryState.RetryCount, retryState.Delay.TotalMilliseconds.ToString(CultureInfo.InvariantCulture), retryState.LastError.ToString())); RetryPolicyUtils.RaiseAmbientRetryMessage(retryState, SqlSchemaModelErrorCodes.ServiceActions.ConnectionRetry); }
private static void CommandFailureIgnore(RetryState retryState, string commandKeyword) { Logger.Write(LogLevel.Normal, string.Format( CultureInfo.InvariantCulture, "{0} retry number {1}. Ignoring failure. Exception: {2}", commandKeyword, retryState.RetryCount, retryState.LastError.ToString())); RetryPolicyUtils.RaiseAmbientIgnoreMessage(retryState, SqlSchemaModelErrorCodes.ServiceActions.CommandRetry); }
public static void CommandFailureRetry(RetryState retryState, string commandKeyword) { Logger.Write(TraceEventType.Information, string.Format( CultureInfo.InvariantCulture, "{0} retry number {1}. Delaying {2} ms before retry. Exception: {3}", commandKeyword, retryState.RetryCount, retryState.Delay.TotalMilliseconds.ToString(CultureInfo.InvariantCulture), retryState.LastError.ToString())); RetryPolicyUtils.RaiseAmbientRetryMessage(retryState, SqlSchemaModelErrorCodes.ServiceActions.CommandRetry); }
/// <summary> /// Traces the Schema retry information before raising the retry message /// </summary> /// <param name="retryState"></param> /// <param name="errorCode"></param> /// <param name="azureSessionId"></param> internal static void RaiseSchemaAmbientRetryMessage(RetryState retryState, int errorCode, Guid azureSessionId) { Logger.Write(LogLevel.Warning, string.Format( "Retry occurred: session: {0}; attempt - {1}; delay - {2}; exception - \"{3}\"", azureSessionId, retryState.RetryCount, retryState.Delay, retryState.LastError )); RaiseAmbientRetryMessage(retryState, errorCode); }
protected override bool ShouldRetryImpl(RetryState retryState) { Contract.Assert(retryState != null); if (IsLessThanMaxRetryCount(retryState.RetryCount, _maxRetryCount)) { retryState.Delay = _intervalBetweenRetries; return(true); } retryState.Delay = TimeSpan.Zero; return(false); }
protected override bool ShouldRetryImpl(RetryState retryState) { Contract.Assert(retryState != null); if (IsLessThanMaxRetryCount(retryState.RetryCount, _maxRetryCount)) { retryState.Delay = RetryPolicyUtils.CalcExponentialRetryDelay(retryState.RetryCount, _intervalFactor, _minInterval, _maxInterval); return(true); } retryState.Delay = TimeSpan.Zero; return(false); }
protected override bool ShouldRetryImpl(RetryState retryState) { Contract.Assert(retryState != null); if (IsLessThanMaxRetryCount(retryState.RetryCount, _maxRetryCount)) { retryState.Delay = TimeSpan.FromMilliseconds(_initialInterval.TotalMilliseconds + (_increment.TotalMilliseconds * (retryState.RetryCount - 1))); return(true); } retryState.Delay = TimeSpan.Zero; return(false); }
public bool ShouldIgnoreError(RetryState retryState) { bool shouldIgnoreError = ErrorDetectionStrategy.ShouldIgnoreError(retryState.LastError); Logger.Write(LogLevel.Error, string.Format( CultureInfo.InvariantCulture, "Ignore Error requested: Retry count = {0}. Delay = {1}, SQL Error Number = {2}, Should Ignore Error = {3}", retryState.RetryCount, retryState.Delay, GetErrorNumber(retryState.LastError), shouldIgnoreError)); return(shouldIgnoreError); }
public static void RaiseAmbientIgnoreMessage(RetryState retryState, int errorCode) { Action <SqlServerRetryError> retryMsgHandler = AmbientSettings.ConnectionRetryMessageHandler; if (retryMsgHandler != null) { string msg = SqlServerRetryError.FormatIgnoreMessage( retryState.RetryCount, retryState.LastError); retryMsgHandler(new SqlServerRetryError( msg, retryState.LastError, retryState.RetryCount, errorCode, ErrorSeverity.Warning)); } }
public bool ShouldRetry(RetryState retryState) { bool canRetry = ErrorDetectionStrategy.CanRetry(retryState.LastError); bool shouldRetry = canRetry && ShouldRetryImpl(retryState); Logger.Write(LogLevel.Error, string.Format( CultureInfo.InvariantCulture, "Retry requested: Retry count = {0}. Delay = {1}, SQL Error Number = {2}, Can retry error = {3}, Will retry = {4}", retryState.RetryCount, retryState.Delay, GetErrorNumber(retryState.LastError), canRetry, shouldRetry)); // Perform an extra check in the delay interval. Should prevent from accidentally ending up with the value of -1 which will block a thread indefinitely. // In addition, any other negative numbers will cause an ArgumentOutOfRangeException fault which will be thrown by Thread.Sleep. if (retryState.Delay.TotalMilliseconds < 0) { retryState.Delay = TimeSpan.Zero; } return(shouldRetry); }
private void RetryConnectionCallback(RetryState retryState) { RetryPolicyUtils.RaiseSchemaAmbientRetryMessage(retryState, SqlSchemaModelErrorCodes.ServiceActions.ConnectionRetry, _azureSessionId); }
private static void ElementCommandFailureIgnore(RetryState retryState) { CommandFailureIgnore(retryState, "Element Command"); }
private static void CreateDatabaseCommandFailureIgnore(RetryState retryState) { CommandFailureIgnore(retryState, "Database Command"); }
private static void CommandFailureIgnore(RetryState retryState) { CommandFailureIgnore(retryState, "Command"); }
private static void CommandFailureRetry(RetryState retryState) { CommandFailureRetry(retryState, "Command"); }
public static void CreateDatabaseCommandFailureRetry(RetryState retryState) { CommandFailureRetry(retryState, "Database Command"); }
public static void ElementCommandFailureRetry(RetryState retryState) { CommandFailureRetry(retryState, "Element Command"); }
/// <summary> /// Repetitively executes the specified action while it satisfies the current retry policy. /// </summary> /// <typeparam name="R">The type of result expected from the executable action.</typeparam> /// <param name="func">A delegate representing the executable action which returns the result of type R.</param> /// <param name="token">Cancellation token to cancel action between retries.</param> /// <returns>The result from the action.</returns> public R ExecuteAction <R>(Func <RetryState, R> func, CancellationToken?token = null) { RetryState retryState = CreateRetryState(); if (token != null) { token.Value.ThrowIfCancellationRequested(); } while (true) { try { return(func(retryState)); } catch (RetryLimitExceededException limitExceededEx) { // The user code can throw a RetryLimitExceededException to force the exit from the retry loop. // The RetryLimitExceeded exception can have an inner exception attached to it. This is the exception // which we will have to throw up the stack so that callers can handle it. if (limitExceededEx.InnerException != null) { throw limitExceededEx.InnerException; } return(default(R)); } catch (Exception ex) { retryState.LastError = ex; if (retryState.RetryCount > 0 || this.ShouldIgnoreOnFirstTry) { // If we can ignore this error, then break out of the loop and consider this execution as passing // We return the default value for the type R if (ShouldIgnoreError(retryState)) { OnIgnoreErrorOccurred(retryState); return(default(R)); } } retryState.RetryCount++; if (!ShouldRetry(retryState)) { throw; } } OnRetryOccurred(retryState); if ((retryState.RetryCount > 1 || !FastFirstRetry) && !retryState.IsDelayDisabled) { Thread.Sleep(retryState.Delay); } // check for cancellation after delay. if (token != null) { token.Value.ThrowIfCancellationRequested(); } } }
internal static void CommandFailureRetry(RetryState retryState) { CommandFailureRetry(retryState, "Command"); }
protected abstract bool ShouldRetryImpl(RetryState retryState);