Attributes and Automation
My favorite thing when programming is building complex, yet elegant solutions.
Reflection is one of my favorite bits of tooling out there. Sure, it has its performance costs. But, so too does everything. I'm not trying to naively pretend that I think it evens out. Just that for many use cases, it can be negligible. Especially if applied to the right areas.
I started toying with the idea of converting my brothers application to .Net Core and getting it up and running in Docker. I may never ship it that way. But, it is a fun activity for me.
In the process, I wanted to transition away from FluentNHibernate and move to MappingByCode inside of Nhibernate itself. But, the process was tedious. Writing just one programmatic mapping file takes some amount of time. And is INCREDIBLY boring after the first five or six.
So what do I do? I switch to abstract base classes. Great! I removed mapping 1 field common to all of my classes.
What next? Custom Attributes! I devised a collection of attribute classes which describe the properties I need mapped. I then use reflection in my abstract mapping class to interrogate the types for these attributes and use the data contained within to perform the mapping.
Where is the value? Well, most of these mappings were straight forward. So, once the attributes were existed I could mass copy and paste into the model objects. It was quicker.
Also, aside from a base mapping class, all of the logic which defines the mapping now lives with the model objects. Making my code cleaner and easier to deal with.
Performance? Minimal impact. The maps which use the attributes are only read once when the Session is initially constructed. Normal operation of the application should be largely untouched.
Long term impact? Even better. If I want to switch to EF or something else, I only need to rewrite the auto mapping logic and not every single map file.
Pretty neat huh?
I'm also able to trim down my total volume of code by a lot, as well as my dependencies.
This kind of meta-programming can be quick useful. You're basically writing code to help you handle your code. So when done right, you wind up with a more portable and more robust solution.
Reflection is one of my favorite bits of tooling out there. Sure, it has its performance costs. But, so too does everything. I'm not trying to naively pretend that I think it evens out. Just that for many use cases, it can be negligible. Especially if applied to the right areas.
I started toying with the idea of converting my brothers application to .Net Core and getting it up and running in Docker. I may never ship it that way. But, it is a fun activity for me.
In the process, I wanted to transition away from FluentNHibernate and move to MappingByCode inside of Nhibernate itself. But, the process was tedious. Writing just one programmatic mapping file takes some amount of time. And is INCREDIBLY boring after the first five or six.
So what do I do? I switch to abstract base classes. Great! I removed mapping 1 field common to all of my classes.
What next? Custom Attributes! I devised a collection of attribute classes which describe the properties I need mapped. I then use reflection in my abstract mapping class to interrogate the types for these attributes and use the data contained within to perform the mapping.
Where is the value? Well, most of these mappings were straight forward. So, once the attributes were existed I could mass copy and paste into the model objects. It was quicker.
Also, aside from a base mapping class, all of the logic which defines the mapping now lives with the model objects. Making my code cleaner and easier to deal with.
Performance? Minimal impact. The maps which use the attributes are only read once when the Session is initially constructed. Normal operation of the application should be largely untouched.
Long term impact? Even better. If I want to switch to EF or something else, I only need to rewrite the auto mapping logic and not every single map file.
Pretty neat huh?
I'm also able to trim down my total volume of code by a lot, as well as my dependencies.
This kind of meta-programming can be quick useful. You're basically writing code to help you handle your code. So when done right, you wind up with a more portable and more robust solution.
Comments
Post a Comment