Microsoft Policy Injection Application Block allows developer to intercept calls to methods, wrap that calls to proxy object and return proxy back to calling class. Later when some methods of the class are called, calls are made to proxy object, and inside the proxy, calls can be made to wrapped class. In that case developer has full control over the proxy. He can log any input/output parameters, he can measure how much time it took to execute method and developer can even replace input/output parameters to something else. In my case, I am interesting only in logging calls to the methods of wrapped class and logging for input/output results.
As usual ,the world is not perfect and some limitation is applied to this approach. You can proxy your class only if it has interface.
I created a simple interface and class
The interface just supposed to return me a list of products from database or form external WCF service. To make it simple I created objects with new operator when implemented the MyRepository class
How to install Policy application block
Next step is add reference to Policy Injection block. The best way to do it is use Nuget: Run "Package manager console" from main menu - View->Other Windows->Package Manager Console and type Install-Package EnterpriseLibrary.PolicyInjection the last version of EnterpriseLibrary will be installed, including EnterpriseLibrary.Common and Unity To wrap our class in Proxy we have to call
Where T is our interface and instance is instance of our class Then we have to mark class which we will wrap with special attribute Tag and parameter for the attribute should be name of the policy rule (it will be more easy to understand on the below sample
Parameter name "Logging" is the name of the rule in our app.config
When it is done we have to implement our interceptor class, which is the most interesting part because we have to write code there :) Our interceptor has to implement ICallHandler which has one property Order and method Invoke In addition your class should contain attribute
and it should contain parameterized constructor
public LoggingInterceptor(NameValueCollection nameValueCollection)
That is it, now you can execute your application and you will see the following: As you can see we have automatic logging just before method call and immediately after call.
Logging input and output parameters using our Interceptor
One thing is still missing: we don't log all input and output parameters of the method. Let's add one more method to our interface
Product GetProduct(int id);
which will return production by id in this case we want to log our input and output parameters In order to do it we have to
- Before call to method get all input parameters and print input parameters
- Make a call to the method
- After the call print output parameter
I did a small modification to the code: so now it shows calls to method in green and I modified ToString method of the Product class to print all information about the product.