AOP (aspect oriented programming) and logging. Is it really functional?

10,500

Solution 1

A few approaches:

  • Put a common interface on types that you want to log. (ILoggable, for example). Implementing that interface will give your aspect the ability to log exactly what you want. The downside is that you have to implement/maintain ILoggable for every object that you might log.

  • Use reflection (which is what I did in this audit example on my blog. It uses an MVC ActionFilter, but the principle is the same). The trade-offs are spelled out in the blog post, but basically it's complexity of using reflection and performance concerns, depending on how much you are logging and how often.

  • Use serialization. Given an object, serialize it to Json or XML or whatever, and log that string. Depending on what you're doing with the logs, this could range from perfect to worthless, and depending on how the serialization works and how complex the objects are, this could be a performance issue too.

Solution 2

I work on a new kind of AOP Framework to respond on the missing features of existing AOP Framework. You can find my open source project here : NConcern .NET AOP Framework

One of the differences with others is to allow you to develop your advice with System.Linq.Expression to avoid boxing/unboxing, reflection and hash jump based on type. It is a little harder to develop using Expression for beginner but easy for an advanced developer.

Example a simple example of logging (into console) without rewrite your business, reflection and boxing.

a business : Calculator

public class Calculator
{
    public int Add(int a, int b)
    {
        return a + b;
    }
}

your logging Aspect implemented by linq expression to describe how Advice must work.

public class Logging : IAspect
{
    //this is not an advice, this method is called to produce advices
    public IEnumerable<IAdvice> Advise(MethodInfo method)
    {
        //generic presentation method
        var presentation = typeof(Presentation). GetMethod("Of");

        //example log on exception
        //instance, arguments and exception are Expressions
        yield return Advice.Linq.After.Throwing((instance, arguments, exception) =>
        {
            Expression.Call
            (
                typeof(Console).GetMethod("WriteLine",...),
                Expression.Call
                (
                    typeof(string).GetMethod("Concat", new Type[] { typeof(string[]) }),
                    Expression.NewArrayInit(typeof(string), arguments.Select(argument => argument.Type == typeof(string) ? argument : ...).ToArray())
                )
            )
        }
    }
}
Share:
10,500
Ignacio Soler Garcia
Author by

Ignacio Soler Garcia

I am now acting as a delivery manager focused on the three main pillars of software creation: People, Procedures and Code working mainly with Javascript teams (React / Redux / Node) building applications 100% in the cloud with CI/CD, etc. I am open to proposals, let's talk. Previously I used to be an experienced technical leader commanding .Net technologies, passionate about Agile methodologies and a people person.

Updated on June 05, 2022

Comments

  • Ignacio Soler Garcia
    Ignacio Soler Garcia almost 2 years

    we are trying to implement Logging in our application using AOP (and PostSharp by the way but this question relates to any AOP framework).

    The problem we are facing is that the information we get is like:

    Entering method XXX with parameters:

    • parameter content if it is a value type.
    • anything in the ToString() override if it is done.
    • classname if the ToString() is not overridden.

    This information is not very useful as normally what we get is the 3rd case. We are creating also LOTS of non useful information.

    If you have used AOP for logging in any product how did you manage this problem?

    Thanks in advance.

  • Ignacio Soler Garcia
    Ignacio Soler Garcia about 10 years
    Thanks. These are good points. At the end we discarded the usage of AOP logging as we didn't found a way to completely replace standard log and we think that makes no sense to have both log systems at one. Anway I'll consider the first two points in the future. Thanks!
  • Ignacio Soler Garcia
    Ignacio Soler Garcia over 7 years
    I see, anyway my complain was not related with perfomance but with the usefulness of the generated data.
  • Tony THONG
    Tony THONG over 7 years
    I see, you just have to implement a kind of external serialization (JSON for example) for the logging to avoid logging class name. the problem is more related to logging process than AOP.
  • Ignacio Soler Garcia
    Ignacio Soler Garcia over 7 years
    Agree, it is a mixed problem as AOP does not allow you to discriminate what are you logging.
  • Tony THONG
    Tony THONG over 7 years
    In my example, I use the specific Expression implementation to advise methods, in the advice creation context, you can use reflection to get informations about target method (custom attributes, parameters, declaring type, reflected type...) in order to provide a dedicated advice. You can select what you want to log (with generic way) if a meta developement effort is provided. You can do your log as good as hard coded.