Open sandboxFocusImprove this doc

Advice Methods

An advice is a method of the aspect class that adds a behavior to a declaration of the target code. A custom attribute on the method, such as OnMethodEntryAdvice, determines the kind of the advice, that is, when the method is invoked. You can choose any name for the method.

The same advice methods are used by member-level aspects (see Developing Member-Level Aspects) and by type-level and assembly-level aspects (see Developing Type- and Assembly-Level Aspects). In a member-level aspect, the advices apply to the target of the aspect. In a type-level or assembly-level aspect, a pointcut selects the members to which an advice applies (see Selecting Members with Pointcuts).

Writing an advice method

An advice method follows these rules:

  • It is public and returns void, except a LocationValidationAdvice, which returns an Exception, and an OnMethodInvokeAsyncAdvice, which returns a Task.
  • It can be static or an instance method. In an InstanceLevelAspect, an advice that applies to static members must be static (error LA0107).
  • It has the custom attribute of one advice kind, from the table below.
  • Each of its parameters receives a value of the target, such as an argument, the return value or a variable shared with the other advices. A binding attribute on the parameter, such as [Argument( 0 )] or [DeclarationName], selects the value. See Advice Parameters.
  • It can be generic. The type arguments are then inferred for each target from the bound values.

The following advice writes the name of the target method and the value of its first argument to the console. The name is a constant, so this advice allocates no memory, except to box the argument when it is of a value type.

[OnMethodEntryAdvice]
public void OnEntry( [DeclarationName( IncludeTypeName = true )] string methodName, [Argument( 0 )] object argument )
{
    Console.WriteLine( "Entering {0}({1})", methodName, argument );
}

Advice kinds

The following table lists the kinds of advices that transform existing declarations. Most advices have a counterpart in a simple aspect. For instance, OnMethodEntryAdvice corresponds to OnEntry(MethodExecutionArgs). The documentation of the simple aspect describes the behavior of the advice in more detail.

The advices of one row form a family. The advices of a family that apply to the same declarations are grouped and woven as one transformation (see Grouping advices). The last column says whether the advice accepts bound parameters.

Advice type Targets Description Bound parameters
OnMethodEntryAdvice
OnMethodSuccessAdvice
OnMethodExceptionAdvice
OnMethodExitAdvice
OnMethodYieldAdvice
OnMethodResumeAdvice
Methods These advices are equivalent to the advices of the aspect OnMethodBoundaryAspect. The target method is wrapped by a try / catch / finally construct. The yield and resume advices run around the await operators of async methods and the yield return statements of iterators. Yes
OnMethodInvokeAdvice Methods This advice is equivalent to the aspect MethodInterceptionAspect. The body of the target method is replaced by a call to the advice, which can invoke the original implementation. Yes
OnLocationGetValueAdvice
OnLocationSetValueAdvice
Fields, properties These advices are equivalent to the advices of the aspect LocationInterceptionAspect. Fields are changed into properties, and calls to the accessors are replaced by calls to the proper advice. Yes
OnInstanceConstructedAdvice Types This advice runs once an instance of the target type is constructed, whichever constructor ran. Yes
LocationValidationAdvice Fields, properties, parameters This advice is equivalent to the ValidateValue(T, string, LocationKind, LocationValidationContext) method of the ILocationValidationAspect<T> aspect interface. It validates values assigned to their targets and returns an exception, which PostSharp throws, in case of error. No
OnEventAddHandlerAdvice
OnEventRemoveHandlerAdvice
OnEventInvokeHandlerAdvice
Events These advices are equivalent to the advices of the aspect EventInterceptionAspect. Calls to add and remove semantics are replaced by calls to advices. When the event is fired, the OnEventInvokeHandler is invoked for each handler, instead of the handler itself. No

Other advices introduce or import members instead of transforming existing ones. See Introducing Interfaces, Methods, Properties and Events into Existing Classes and Accessing Members of the Target Class.

Advice properties

The advice attributes have properties that control how the advice is woven and how it is shown in Visual Studio:

SemanticallyAdvisedMethodKinds and UnsupportedTargetAction apply to the whole group, so PostSharp reads them from the master advice only. When PostSharp infers the group, the advice that sets one of these properties, or Description, becomes the master advice. When several advices set them, PostSharp reports the error LA0231. An advice that sets the Master property cannot set them (error LA0135).

[OnMethodEntryAdvice( Description = "Measures the duration of the method",
                      SemanticallyAdvisedMethodKinds = SemanticallyAdvisedMethodKinds.None )]
public void OnEntry( [State( StateScope.MethodInvocation )] out Stopwatch stopwatch )
{
    stopwatch = Stopwatch.StartNew();
}

Legacy AdviceArgs signature

Instead of bound parameters, an advice method can have the parameter of the corresponding method of the simple aspect: MethodExecutionArgs for the method boundary advices, MethodInterceptionArgs for OnMethodInvokeAdvice, LocationInterceptionArgs for the location interception advices, and so on. This object is allocated on the heap on each call, and it gives access to the values of the target as object.

This signature is an obsolete practice, supported for compatibility with existing aspects. Prefer bound parameters. To convert an existing aspect, see Modernizing Your Custom Aspects.

The event interception advices do not accept bound parameters, so they must use this signature. LocationValidationAdvice has its own signature, the one of the ValidateValue(T, string, LocationKind, LocationValidationContext) method. In the method boundary, method interception and location interception advices, the AdviceArgs parameter can also be the first parameter, followed by bound parameters.

The following advice of an EventLevelAspect intercepts the add accessor of the target event:

[OnEventAddHandlerAdvice]
public void OnAddHandler( EventInterceptionArgs args )
{
    // Details skipped.

    args.ProceedAddHandler();
}

See Also

Reference

PostSharp.Aspects.Advices
Advice
AdviceParameterAttribute

Other Resources

Developing Member-Level Aspects
Advice Parameters
Selecting Members with Pointcuts
Modernizing Your Custom Aspects
Ordering Advices
Developing Simple Aspects