Building Meaningful Audit Trail in your System

I have seen two primary approaches to building a audit trails for systems – entity level audits and property level audits.

Entity level audit maintains an audit log for every entity and makes an audit entry for ‘any’ operation done on these entities. Weather there is a change in one property of the entity or the entire entity changes as part of an operation that affects a bunch of other entities in the same transaction. At database level, this is often implemented using triggers that would copy the row being changed to an audit table along with some audit information.

Property level audit, on the other hand, goes to a different extreme and makes an audit entry every time any property on any entities changes. At database level this often translates into one big fat table which keeps track of any field in any table that has changed along with some general audit information.

Whiles these are two widely adopted implementation approaches for performing system audits, what both of these approaches fail to capture is the actual intent of the user. The granularity at which the system captures the audit data has an impedance mismatch with the business and it can get difficult to tell what actually was done to system to create this audit entry. Hence, these audit data would have a very limited business meaning and use.

Think about a modelling strategy where the actual operations that can be performed on the system are expressed explicitly. Wouldn’t it be a lot easier to just record these operations or the fact that these operations got performed on the system? This kind of audit data would have the granularity that would make sense to the business and creating a business meaningful audit reports out of such audit logs would be a lot easier. Isn’t it?

Advertisements

Implementing Repository in DDD – Part 1

Implementing Repository is fairly staright forward in DDD. There are generally two styles of implementation,
1. aggregate-dedicated repository and
2. generic repository.

An aggregate-dedicated repository will have a method per command or query; while, Generic repository will have a standard interface for every Aggregate. However, in both cases, the repository is suppose to operate at the aggregate-root level. This post will demostrate implementation of an aggregate-dedicated repository,

In your domain layer,
public class Order: IAggregateRoot
{
public Order(IOrderRepository repository)
{ ..}

public void Order(PlaceOrderCommand command)
{
..
repository.Add(this);
}
public Order Get(Guid id)
{
return repository.Single(id);
}

public IList<Order> GetOrdersByCustomer(Guid customerId)
{
return repository.Where(o=>o.CustomerId = customerId);
}
}

Application Layer,

public class OrderService
{
public void PlaceOrder(PlaceOrderCommand command)
{
this.Transaction();
var Order = new Order(new OrderRepository());
Order.PlaceOrder(command);
this.CompleteTransaction();
}
}

The Application Layer uses dependency injection to inject an instance of the repository that the aggregate uses. The aggregate-root then calls the repository internally to persists the data and retrieve data.

In this style of implementation, a dedicated repository designed for each aggregate-root. This means a little more coding up-front compared to generic repositories, as there is one repository per aggregate. Writing unit-tests might be a little more difficult. But over all, the simplicity and flexibility that this implementation brings is huge and depending on your taste, choice of tech-stacks and data-access needs it might be a very good fit for you. Definitely worth a consideration.

IOC Containers Demystified

When I first came across this big buzz called IOC Containers, I found it very close to a factory class in its purpose and philosophy. As I dig deeper and deeper into the concept, I find myself more and more convinced that an IOC Container is nothing more than a Fancy Factory.

Amid all the mumbo-jumbo around it, these IOC Containers actually quite simple at their hearts. IOC Containers are essentially a tool for Dependency Injection. The whole idea being able to invert the flow of program control in a manner that maximum amount loose coupling can be achieved. Hence the name IOC (Inversion Of Control) Container.

Sounds vague? Let us jump into some code in order to understand this. Allow me to use the example of my favorite ‘PizzaStore’ class.


Public class PizzaStore
{
    Public ChickenPizza Prepare()
    {
        ChickenPizza pizza = new ChickenPizza();
        return pizza.Prepare();
    }
}

In the light of Dependency Inversion Principle (DIP) , this is not the right way of doing it. For every new Pizza class that is created in the system there needs to be a new PizzaStore class. This is because the PizzaStore class depends upon the Pizza class. A desirable design goal (according to DIP) here would be that the Pizza and the PizzaStore class should be decoupled in a manner that same PizzaStore class should be able to work with different types of Pizza. In other words, the dependency between Pizza and PizzaStore should be so inverted that PizzaStore should not directly depend on Pizza class. As a matter of fact, according to DIP, it should depend on an abstraction (IPizza interface in this case).


Public class PizzaStore
{
    Public IPizza Prepare(IPizza  pizza)
    {
        return pizza.Prepare();
    }
}

The client program must take pass the right dependency (instance of pizza) to the IPizza. This tecnique of injecting the dependency from outside is called Dependency Injection.

If we separate out the piece of code that assumes the responsibility of inverting the flow of control of the system in comparison to procedural programming using the technique of Dependency Injection, we would call this piece of code an IOC Container.

An IOC container, at the very basic should be able to do two things
• Register a Dependency
• Resolve a Dependency

For the ease of understanding, let us start with the Resolve part. Take a look at the following code,


public class PizzaStore
{
    Public IPizza Prepare()
    {
        var pizza = Container.Resolve<IPizza>();
        return pizza.Prepare();
    }
}

Here the Container determines and returns the right instance of the Pizza. Hence, whenever an instance of the type Pizza is required by the PizzaStore class, it will request the Container to resolve and return the right instance for the Pizza. This means that it is the responsibility of the Container to instantiate a class. This also means that the Container needs to have the information about what instance should it return for a given type. This is when the Register part comes into picture. The Register method tells the Container what object should be returned for a given type.


ChikenPizza chkPizza = new ChikenPizza();
Container.Register<IPizza>(chkPizza);

Or sometimes,


Container.Register<IPizza>(ChikenPizza);

Most of the existing IOC containers allow an ability to Register through configuration also. A typically full-blown IOC Container also provide with other sophistications like managing the scope and lifetime of the instance. For example, would you like your object to be instantiated on per call basis, or per thread basis or should your instance be a singleton instance.

In a nutshell, all that an IOC Container essentially does is know what instance to be retuned for a given type and then return that instance through an abstraction (generally interface) using dependency Injection.