/// <summary> /// Logs an exception using the standard pattern for the LaunchDarkly SDKs. /// </summary> /// <remarks> /// The exception summary is logged at Error level. Then the stacktrace is logged at /// Debug level, using lazy evaluation to avoid computing it if Debug loggins is disabled. /// </remarks> /// <param name="logger">the logger instance</param> /// <param name="message">a descriptive prefix ("Unexpected error" if null or empty)</param> /// <param name="e">the exception</param> public static void LogException(Logger logger, string message, Exception e) { logger.Error("{0}: {1}", string.IsNullOrEmpty(message) ? "Unexpected error" : message, LogValues.ExceptionSummary(e)); logger.Debug(LogValues.ExceptionTrace(e)); }
private async Task UpdateTaskAsync() { try { var response = await _featureFlagRequestor.FeatureFlagsAsync(); if (response.statusCode == 200) { var flagsAsJsonString = response.jsonResponse; var allData = DataModelSerialization.DeserializeV1Schema(flagsAsJsonString); _updateSink.Init(_user, allData); if (_initialized.GetAndSet(true) == false) { _startTask.SetResult(true); _log.Info("Initialized LaunchDarkly Polling Processor."); } } } catch (UnsuccessfulResponseException ex) { var errorInfo = DataSourceStatus.ErrorInfo.FromHttpError(ex.StatusCode); if (HttpErrors.IsRecoverable(ex.StatusCode)) { _log.Warn(HttpErrors.ErrorMessage(ex.StatusCode, "polling request", "will retry")); _updateSink.UpdateStatus(DataSourceState.Interrupted, errorInfo); } else { _log.Error(HttpErrors.ErrorMessage(ex.StatusCode, "polling request", "")); _updateSink.UpdateStatus(DataSourceState.Shutdown, errorInfo); // if client is initializing, make it stop waiting _startTask.TrySetResult(false); ((IDisposable)this).Dispose(); } } catch (JsonReadException ex) { _log.Error("Polling request received malformed data: {0}", LogValues.ExceptionSummary(ex)); _updateSink.UpdateStatus(DataSourceState.Interrupted, new DataSourceStatus.ErrorInfo { Kind = DataSourceStatus.ErrorKind.InvalidData, Time = DateTime.Now }); } catch (Exception ex) { Exception realEx = (ex is AggregateException ae) ? ae.Flatten() : ex; _log.Warn("Polling for feature flag updates failed: {0}", LogValues.ExceptionSummary(realEx)); _log.Debug(LogValues.ExceptionTrace(realEx)); _updateSink.UpdateStatus(DataSourceState.Interrupted, DataSourceStatus.ErrorInfo.FromException(realEx)); } }
public void ExceptionTrace() { try { throw new Exception(); } catch (Exception e) { var s = LogValues.ExceptionTrace(e).ToString(); Assert.Contains("LogValuesTest.ExceptionTrace", s); } }
private void ReportStoreFailure(Exception e) { if (!_lastStoreUpdateFailed) { _log.Warn("Unexpected data store error when trying to store an update received from the data source: {0}", LogValues.ExceptionSummary(e)); _lastStoreUpdateFailed = true; } _log.Debug(LogValues.ExceptionTrace(e)); UpdateStatus(DataSourceState.Interrupted, new DataSourceStatus.ErrorInfo { Kind = DataSourceStatus.ErrorKind.StoreError, Message = e.Message, Time = DateTime.Now }); }
private void OnError(object sender, EventSource.ExceptionEventArgs e) { var ex = e.Exception; var recoverable = true; DataSourceStatus.ErrorInfo errorInfo; RecordStreamInit(true); if (ex is EventSourceServiceUnsuccessfulResponseException respEx) { int status = respEx.StatusCode; errorInfo = DataSourceStatus.ErrorInfo.FromHttpError(status); if (!HttpErrors.IsRecoverable(status)) { recoverable = false; _log.Error(HttpErrors.ErrorMessage(status, "streaming connection", "")); } else { _log.Warn(HttpErrors.ErrorMessage(status, "streaming connection", "will retry")); } } else { errorInfo = DataSourceStatus.ErrorInfo.FromException(ex); _log.Warn("Encountered EventSource error: {0}", LogValues.ExceptionSummary(ex)); _log.Debug(LogValues.ExceptionTrace(ex)); } _updateSink.UpdateStatus(recoverable ? DataSourceState.Interrupted : DataSourceState.Shutdown, errorInfo); if (!recoverable) { // Make _initTask complete to tell the client to stop waiting for initialization. We use // TrySetResult rather than SetResult here because it might have already been completed // (if for instance the stream started successfully, then restarted and got a 401). _initTask.TrySetResult(false); ((IDisposable)this).Dispose(); } }