Skip to content

A demonstration reactive custom Polly policy, to log faults and results the policy is configured to handle.

License

Notifications You must be signed in to change notification settings

Polly-Contrib/Polly.Contrib.LoggingPolicy

Repository files navigation

Polly.Contrib.LoggingPolicy

This repo contains a custom Polly policy to log exceptions or handled results, then rethrow.

For more background on Polly see the main Polly repo.

Usage

Asynchronous executions

Define an Action<ILogger, Context, DelegateResult<TResult>> logAction to log exceptions or results. The Context input parameter allows filtering based on Polly's in-built execution metadata or context you pass in to the execution.

Action<ILogger, Context, DelegateResult<HttpResponseMessage>> logAction = (logger, context, outcome) => 
{
    logger.LogError("The call resulted in outcome: {happened}", outcome.Exception?.Message ?? outcome.Result.StatusCode.ToString());
}

Define a Func<Context, ILogger> loggerProvider to select an ILogger based on Context. This can use the extension method Context.GetLogger() defined on Polly.Context, if execution dispatch uses the Context.WithLogger(ILogger) overload, as demonstrated in the ConsoleApp example.

Configure the policy:

var loggingPolicy = Policy<HttpResponseMessage>
    .Handle<HttpRequestException>()
    .OrResult((int)response.StatusCode >= 500 || response.StatusCode == HttpStatusCode.RequestTimeout)
    .AsyncLog(ctx => ctx.GetLogger(), logAction);

The policy would typically be combined with other policies in a PolicyWrap - see below.

Synchronous executions

Define a logAction and loggerProvider as above.

Configure the policy, for example:

var loggingPolicy = Policy
    .Handle<Exception>()
    .Log(ctx => ctx.GetLogger(), logAction);

Using LoggingPolicy in PolicyWrap

The LoggingPolicy can be used in any position in a PolicyWrap.

It will log the faults it is configured to handle, based on faults bubbled outwards from the next-inner level.

  • A LoggingPolicy used outermost (configured first) in a PolicyWrap will log any eventual failure, after all policies of the PolicyWrap have exited.
  • A LoggingPolicy used innermost (configured last) in a PolicyWrap will log any failure from the underlying delegate executed through the PolicyWrap. For instance, if the PolicyWrap includes retries, a logging policy configured inside (after, in HttpClientFactory sequence) the retry policy, will log any exception/fault thrown by each try.

The sole purpose of the policy is to log. After logging, it bubbles faults further outwards to be handled by any policies further out or bubbled back to the caller.

Blog post example

The policy is an example for the blog Custom policies Part III: Authoring a reactive custom policy.

The policy in this repo differs in small ways from the blog post, as this repo offers LoggingPolicy in all four combinations:

  • LoggingPolicy (synchronous non-generic)
  • LoggingPolicy<TResult> (synchronous generic)
  • AsyncLoggingPolicy (asynchronous non-generic)
  • AsyncLoggingPolicy<TResult> (asynchronous generic)

Interested in developing your own custom policies?

See our blog series:

And see the templates for developing custom policies: Polly.Contrib.CustomPolicyTemplates.

About

A demonstration reactive custom Polly policy, to log faults and results the policy is configured to handle.

Resources

License

Code of conduct

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published