It annoys me when people make arguments that the UI should have absolutely no connection whatsoever to the business processes of a system. To me, this is a far too crippling restraint. Is your UI also not supposed to know that a given process is going to update your orders, to look for a new one? Should you then implement some sort of back-and-forth chaining of events that ensure your UI is up-to-date, but have it take 10 minutes to get through the chain of commands, rather than happen instantly because it knows that adding an order will...add an order?
This kind of active UI - one that knows something of the business processes - is not the death of maintainability. WPF has made it somewhat easier to manage by implementing binding so effectively, but that also has its own problems. I would rather have my business commands handle the UI updates directly, but this can be quite a mess; better is to just have the UI, when it gets some signal from the user (or from anywhere) do the update itself, before or after sending the command to the business processes. You might send to the business processes before updating the UI, and have the command catch a response from the business process telling you if you should update the UI (maybe there's some problem that the UI cannot and should not be able to validate); conversely, it's also reasonable to just update the UI and send to an async business process if you know for a fact that the updating is valid, say because of all validation that has already taken place.
What you definitely should not do, however, is have your UI implement all of your business processes. This is not only not maintainable, it's simply downright pug-fugly.
Wednesday, December 7, 2011
Tuesday, November 15, 2011
Writing stable code
Lately, I've been a tad obsessed with only writing stable code. Oh, sure, it'll be unstable until I realize how to fix
it, but I wanted to write a little bit about how I stabilize the code I'm writing, cause there are a few tricks that are convenient. The following represent refactoring techniques that can increase encapsulation, and decrease the number of times you have to change a given piece of code. Use wisely.
I hope that these are useful to you in some way, even if the above seem very simple to the vast majority of you.
it, but I wanted to write a little bit about how I stabilize the code I'm writing, cause there are a few tricks that are convenient. The following represent refactoring techniques that can increase encapsulation, and decrease the number of times you have to change a given piece of code. Use wisely.
- Argument lists --> Class
This first refactoring involves taking a long argument list for a function and wrapping the list in a class. A long argument list implies (to me) that there is some entire concept stored in that list, and that it would be better represented by some class with an appropriate name. Furthermore, if this is a public function that may be consumed by a customer, it would be very wise to do this so that if they have overwritten the function, when you change the class representing the argument list, they will not likely have a terrible break in their implementations of that class or interface. - Generic lists --> Class
The second refactoring takes long strings of generics and turns them into a single generic. For example:
Func<Father, Mother, IEnumerable<Children>, IEnumerable<KeyValuePair<Food, Money>>, Cost> PurchaseFoodStuffs;
Could be rewritten as:
Func<Family, GroceryStore, Cost> PurchaseFoodStuffs;
This Func takes a family to the grocery store and returns the cost of the food purchased. From the previous iteration, you would have no idea that that's what it's trying to do, however. You can imagine if you had to buy food for special occasions and what not that the argument list would get longer and longer and longer, but with the second one, if you're (say) adding an aunt and uncle that needs to be accounted for, you just add that to your Family class and you're almost done. There may need to be some more tinkering, but at least you don't have to go change a long generics list to match it all over the place. This also has the advantage that if you publish the above Func to a customer, you can change the underlying classes more easily than the argument list, and expect fewer breaks in customer code, similar to the first refactoring. - Func/Action --> Class
Are you noticing a trend? I prefer not to use Func/Action in my code unless it's particularly useful or necessary. I've found over time that using a naked Func or Action does not seem to really indicate the intent of a given piece of code very well. This is just my experience with code in the real world, but may not represent others' experiences. I just find that whenever I have a Func or Action that is even moderately complicated, I would have preferred to pass much of the data into a constructor and acted upon that data however I wanted, and passed around a class that can have functionality be overwritten, rather than a naked Func or Action which will likely require that you add a new condition in an if-statement. A good trick is to encapsulate the functionality into an actual class, and then make a derivative of that class that accepts a Func/Action into its constructor. This will give you the ability to rely purely on the class interface, while still being able to write simple code within a Func/Action, and you will not be coding yourself into a corner if the class functionality needs to change in the future, but the Func/Action code does not (necessarily) have to.
A good example of this in the real world is simply the ICommand interface and DelegateCommand<T> class in the WPF Commanding stack: It does a little bit of work for you, but allows you to either completely write a new implementation by implementing ICommand, or pass a delegate into the constructor and let the DelegateCommand do the majority of the heavy lifting.
I hope that these are useful to you in some way, even if the above seem very simple to the vast majority of you.
Tuesday, August 16, 2011
Koans of Programming: Interface are for me, not for you
"Do not define interfaces to tell the consumer of your system how to use your objects. Define interfaces to tell the consumer of your system how your system will use their objects."
This little gem of wisdom came to me one day some time ago, and remains true today. When you are defining an interface, remember that they are for *you* to use inside your framework, and should be clean, stable, and simple. They should not have to be implemented by someone using your framework, unless those people need to actually override the functionality provided by said interface. When there is no discernible reason for having an interface because implementing it does not change any functionality, then you are more likely trying to tell your user how they should use your classes, which is much better done with a class - in that way, you can put some kind of restraints on how things are used, and you can still, if needed, provide points of extensibility.
This little gem of wisdom came to me one day some time ago, and remains true today. When you are defining an interface, remember that they are for *you* to use inside your framework, and should be clean, stable, and simple. They should not have to be implemented by someone using your framework, unless those people need to actually override the functionality provided by said interface. When there is no discernible reason for having an interface because implementing it does not change any functionality, then you are more likely trying to tell your user how they should use your classes, which is much better done with a class - in that way, you can put some kind of restraints on how things are used, and you can still, if needed, provide points of extensibility.
Tuesday, May 31, 2011
Virtual properties - they're just dumb
Have you ever seen code of the form:
// Make it virtual so that implementers can provide their own version for them to use
public virtual IManager Manager { get; set; }
?
Code like this just angers me. For one, why didn't they pass it into the constructor? This is much clearer. For two, why does a *base* class need to define what classes the derived classes need to use in order to accomplish their tasks? This is ludicrous. That particular property isn't even used in the base class anywhere - and that's the main problem with it.
When you put something like this on your base classes, it's implying to the deriver that there's some reason that the base class needs it, so the deriver should provide their own implementation that doesn't break the invariants that the IManager interface is bound to. However, since it's not actually used in the base class (notice the comment? It very clearly states that the implementers will be required to use the class, not the base class), the base class shouldn't even have a reference to the IManager type.
The codebase that I was looking at was a real joke, and the original implementers had no idea what OOP means. Without any real depth of knowledge, OOP can quickly turn into POOP.
// Make it virtual so that implementers can provide their own version for them to use
public virtual IManager Manager { get; set; }
?
Code like this just angers me. For one, why didn't they pass it into the constructor? This is much clearer. For two, why does a *base* class need to define what classes the derived classes need to use in order to accomplish their tasks? This is ludicrous. That particular property isn't even used in the base class anywhere - and that's the main problem with it.
When you put something like this on your base classes, it's implying to the deriver that there's some reason that the base class needs it, so the deriver should provide their own implementation that doesn't break the invariants that the IManager interface is bound to. However, since it's not actually used in the base class (notice the comment? It very clearly states that the implementers will be required to use the class, not the base class), the base class shouldn't even have a reference to the IManager type.
The codebase that I was looking at was a real joke, and the original implementers had no idea what OOP means. Without any real depth of knowledge, OOP can quickly turn into POOP.
Thursday, May 26, 2011
Implementation hiding - it's important
I've decided to do away with the annoying naming scheme.
For this post, I'd like to talk about something that's very near and dear to me - implementation hiding. This is the concept in object-oriented design that allows a class' implementation to change without affecting the public interface of that class. It also allows things like schemas to change without requiring massive changes all throughout an application - if you hide the information and implementations of things, then no one can rely on those data and end up getting screwed when the schema has to change. This is important.
It's so important that the majority of the object-oriented design principles are focused purely on it. Most design patterns also encapsulate some form or another of implementation hiding in such a way that it makes it easier to change the code if needed, as well as at the level that's needed. Being able to change code efficiently and quickly - it's important.
An area that I really like to use implementation hiding is around legacy code. Let's say you have a COM library that you call into in order to generate some bitmaps of graphs for a scientific application. But let's also say you want to be able to make your class testable - to test it, you really don't want to pull in the COM library, initialize it, and so on; that's not just a lot of work, that's dangerous in a unit-testing scenario. So, instead of having just a class that calls directly into the COM library, have an interface that that class can implement that represents all of your code. In this way, a unit-test can create a mock of the interface and you can focus on test-driving it much more easily. Later on, when you're doing integration testing, you can test the class that calls the COM library directly, but this should always be done very carefully, and perhaps only on a CI server, in order to save developer time and effort (integration testing can take quite a long time; hence, I prefer to run it on a server instead). This is important.
Another way in which implementation hiding can be effective is on a codebase that uses a lot of static functions and such. It is often the case that as a developer, you'll get put onto a project that someone from a long time ago started coding and were only vaguely aware, if at all, of the principles we have these days, and because of that, they make it a very ugly solution. Your job is to clean it up where you can, and introduce new features. In order to integrate new features, though, a lot of stuff may have to change, and hiding these changes beneath an interface is an incredibly important way of cleaning up the codebase and making it safer for other developers to delve into.
Consider for example a codebase in which static classes and functions are the primary way the original developer worked. I think we've pretty much all seen this. None of it is testable at all, though. Sure, you can make calls to static classes in your unit tests, but that is possibly worse than not unit testing at all, because if the static class has to change, it now breaks both in the consuming system code and in the tests. Better would be to put an interface around it to wrap calls to the static classes, and replacing the calls to these in the consuming system code with calls to the interface. It sounds unimportant, but believe me, slowly removing static classes from your codebase over time is going to help you in the long-run, and not just with unit testing. It's very important.
Insulate change. Hide implementations. Winning.
For this post, I'd like to talk about something that's very near and dear to me - implementation hiding. This is the concept in object-oriented design that allows a class' implementation to change without affecting the public interface of that class. It also allows things like schemas to change without requiring massive changes all throughout an application - if you hide the information and implementations of things, then no one can rely on those data and end up getting screwed when the schema has to change. This is important.
It's so important that the majority of the object-oriented design principles are focused purely on it. Most design patterns also encapsulate some form or another of implementation hiding in such a way that it makes it easier to change the code if needed, as well as at the level that's needed. Being able to change code efficiently and quickly - it's important.
An area that I really like to use implementation hiding is around legacy code. Let's say you have a COM library that you call into in order to generate some bitmaps of graphs for a scientific application. But let's also say you want to be able to make your class testable - to test it, you really don't want to pull in the COM library, initialize it, and so on; that's not just a lot of work, that's dangerous in a unit-testing scenario. So, instead of having just a class that calls directly into the COM library, have an interface that that class can implement that represents all of your code. In this way, a unit-test can create a mock of the interface and you can focus on test-driving it much more easily. Later on, when you're doing integration testing, you can test the class that calls the COM library directly, but this should always be done very carefully, and perhaps only on a CI server, in order to save developer time and effort (integration testing can take quite a long time; hence, I prefer to run it on a server instead). This is important.
Another way in which implementation hiding can be effective is on a codebase that uses a lot of static functions and such. It is often the case that as a developer, you'll get put onto a project that someone from a long time ago started coding and were only vaguely aware, if at all, of the principles we have these days, and because of that, they make it a very ugly solution. Your job is to clean it up where you can, and introduce new features. In order to integrate new features, though, a lot of stuff may have to change, and hiding these changes beneath an interface is an incredibly important way of cleaning up the codebase and making it safer for other developers to delve into.
Consider for example a codebase in which static classes and functions are the primary way the original developer worked. I think we've pretty much all seen this. None of it is testable at all, though. Sure, you can make calls to static classes in your unit tests, but that is possibly worse than not unit testing at all, because if the static class has to change, it now breaks both in the consuming system code and in the tests. Better would be to put an interface around it to wrap calls to the static classes, and replacing the calls to these in the consuming system code with calls to the interface. It sounds unimportant, but believe me, slowly removing static classes from your codebase over time is going to help you in the long-run, and not just with unit testing. It's very important.
Insulate change. Hide implementations. Winning.
Friday, March 4, 2011
Stardate 2011.63.1: Design stenches - Rigidity
A lot of people are aware of what others call design smells. I hate using the term smell, so I use the term stenches, but they amount to the same thing: Something that reeks up the place somethin' fierce. I'm going to be writing a series of posts with my experiences on projects that feature plenty of malodorous designs, and show how I would have improved them and why they are better. I hope to keep these relatively short, as I tend to go too long, but if you have questions, I can answer them in follow-up posts.
From Agile Principles, Patterns, and Practices by Robert C. Martin, rigidity of design is defined as:
"Rigidity is the tendency for software to be difficult to change, even in simple ways. A design is rigid if a single change causes a cascade of subsequent changes in dependent modules. The more modules that must be changed, the more rigid the design."
From my personal experience, this happens most often when people are more worried about data than they are about functionality. For example, for a simple property bag, if you make an interface for it and make more than one implementation, what happens when you change the interface because it turns out it didn't have all the data you needed, or the datatype on one of the properties needed to change? Did you have control over all the implementors, and did you just publish an unnecessary breaking change? For this reason, I do not support having many properties on an interface - 2-3 tops, preferably none.
In any case, when you change the interface, it completely screws the app. *Every* place that uses that interface now may have to change, depending on the type of change. Does this mean we shouldn't use interfaces? No! We should only use them when they are appropriate, and ensure that they encapsulate a responsibility, rather than represent a piece of data.
To fix this, I would only put the appropriate functionality for a given class on the interface. More importantly, I try to ensure that the interface is truly stable. Without stability, interfaces are actually less useful than standard classes.
From Agile Principles, Patterns, and Practices by Robert C. Martin, rigidity of design is defined as:
"Rigidity is the tendency for software to be difficult to change, even in simple ways. A design is rigid if a single change causes a cascade of subsequent changes in dependent modules. The more modules that must be changed, the more rigid the design."
From my personal experience, this happens most often when people are more worried about data than they are about functionality. For example, for a simple property bag, if you make an interface for it and make more than one implementation, what happens when you change the interface because it turns out it didn't have all the data you needed, or the datatype on one of the properties needed to change? Did you have control over all the implementors, and did you just publish an unnecessary breaking change? For this reason, I do not support having many properties on an interface - 2-3 tops, preferably none.
In any case, when you change the interface, it completely screws the app. *Every* place that uses that interface now may have to change, depending on the type of change. Does this mean we shouldn't use interfaces? No! We should only use them when they are appropriate, and ensure that they encapsulate a responsibility, rather than represent a piece of data.
To fix this, I would only put the appropriate functionality for a given class on the interface. More importantly, I try to ensure that the interface is truly stable. Without stability, interfaces are actually less useful than standard classes.
Wednesday, February 2, 2011
Stardate 2011.31.1: Why Me(ssage Brokers)?
Boarding the Enterprise (architecture)
Enterprise-level application development is often much different from non-enterprise application development. It requires a lot more discipline, and a lot better understanding of the design of the application by all of the people on the project. The reasons why are fairly simple: If the architecture supports modularization, a strong probability, and at the lowest level the developers have glued dependencies between all of the modules through the use of static classes or through plain and simple data sharing, then what was the point of having modules in the first place? Modules are intended to have separate, clearly delineated boundaries between each area of the application, so if there are dependencies between each and every module, then there's something disturbingly wrong.
How does one typically fix this? There are three ways, usually: A message broker, an enterprise service bus, or a simple service locator/inversion of control container, depending on the requirements of the system. I'd like to discuss all three here today, but I don't know enough about service buses to write anything intelligible about them. On the other hand, I've used service locators and message brokers out the yin-yang, so I'll write about those. For more info on service buses, I highly recommend Udi Dahan's blog, wherein he talks about them most of the time. :)
An IoC container/service locator is a simple construct that allows you to grab a reference to an interface without having to know how it was instantiated, nor what the concrete implementation of that interface is. This allows a very clean, simple architecture, although I tend to use an IoC container rather than a service locator simply for the all-powerful constructor injection, which requires an explicit declaration of dependency on the interface in question.
A message broker is most often used to communicate between processes or programs. They typically support a Publish/Subscribe model, where a programmer can send messages to a host of programs easily by publishing a single message on the broker. This can also be used for inter-module communication, however, and cleanly supports future integration with other applications.
How are these two similar, and what is the motivation for using them in the first place?
A clean architecture may have explicit dependencies between each module, but it does so in the form of interfaces. These interfaces can be stored in an intermediate project so that everyone has access to them. While this leads to a high afferent coupling, the coupling is to an interface, so it's less likely to break something if the implementing class has to change how it satisfies the interface. When you rely directly on the implementing class (instead of the interface), you get into trouble when that implementation class has to change substantially, mainly because the code that used it may need to change as well. If it was dependent only upon the interface, i.e. the core functionality that the class provides, it's less likely that the interface will have to change, because the implementation class can change much more easily to meet the needs of the interface, so you save in two ways.
A service locator or IoC tool can be used to mitigate the complexity of the construction of an object, as well as the inherent coupling to the concrete implementation class. Whereas before you might have had:
IUsageTrackingService tracker = new SqlUsageService(connectionString, other_bs);
Now, you would have the rather simpler:
IUsageTrackingService tracker = ServiceLocator.Resolve<IUsageTrackingService>();
Instead of having whatever class needs access to the usage tracking service newing it up itself, it is pulled in through a static service locator here and the using-class doesn't need to know the connection string or anything else about the usage tracker in order to get a reference to one. You can see how useful this is if you ever need to unit-test the usage tracker: Do you want to have it crush a database, or simply output the usage into a string which can be inspected way more easily? And unit-testing the class that uses the usage tracker? FUHGEDABODIT! (Pass an interface reference into the constructor of the using-class, and just mock it.)
A message broker works in a strangely similar fashion. What the service locator/IoC tool did through inherent reliance on the interface (in this case IUsageTrackingService), a message broker goes one step further and says, "I don't even know who is going to be getting this, but here's some indication that something is happening! AAAAAAGGHHHHH!" Here's how I think of a message broker: When you need something to happen (let's say we're still on usage tracking) but there's absolutely no reason whatsoever for a class to care who or what is responding to its clicking of an advertisement in the application, then a message broker can very, very cleanly implement that. In this case, you just have the class fire off a message such as:
broker.Publish(new AdvertisementClicked(module: Modules.Comedy, user: user.ID, advertisement: ad.ID); // Only using named arguments for clarity
Now, anyone who might want to catch that event can simply be subscribed to it upon instantiation of the message broker, and that leads to much, much cleaner code. Consider also that if the message broker were to just push the message into a queue, this could be processed completely outside of the main application somewhere and you'd take no performance hit whatsoever.
The key here is that the message broker removed dependency even upon the interface itself, so now the interface that you've created can change, if required, without the using-class having to change its code to handle it. It can be argued that in this case, you may not even need the interface at all, but I'll leave it as-is for now.
Downsides
There are several downsides to each of these methods. I'll discuss those now briefly because they are pretty self-explanatory, in my opinion.
ServiceLocator/IoC container - With a static ServiceLocator, you get the added lack of bonus of relying on a static singleton, which isn't great for testability. At the same time, the IoC container can hinder testing as well. With the ServiceLocator pattern, you tend to run into problems when someone wants to use a class, but doesn't realize it has some dependency upon some interface - since the interface dependency isn't explicitly defined in the constructor of the class, it's not nearly as easy for the user to know that they have to register that dependency before using said class. With an IoC container, this is less of a problem because they typically have constructor injection, which allows the class to explicitly define the interface in its constructor. Both of these methods have somewhat of a complex learning curve due to the fact that you never technically know which implementation is being used, unless you're in the place where that implementation is being registered as the interface. You may very well *not* have access to that; for instance, if you were working in a module and the registering of the implementations all happens in the bootstrapper, and the bootstrapper is part of a totally different project, then you may not have access to it. At the same time, it lends itself to very simple programming, where you just get the reference and call functions on it - dirt simple.
With a message broker, the learning curve is much, much steeper. In addition to not knowing which particular class that you care about is processing the message, there could be tons of classes other classes processing the message as well, which can interfere. If you don't have access to all of them, then it could be one of those other classes that has a problem with the message. For this reason, it is a standard of mine that, when a class is processing a message, I log it. That way, when it fails, it is at least logged and I can go back and see exactly where it failed, if not specifically what failed.
The message broker also requires some knowledge of threading typically, as well as weak references. When you have an event that is being published, it could happen on the main thread or on a background thread. This can vastly change the programming model, and is a bit harder for most developers to wrap their heads around. Similarly, the pub/sub model that is usually used is somehow difficult for some developers to understand and compute. Some programmers also seem to struggle with weak references.
Both of these methods are more complicated, but save you time and money in the long run - it's a matter of how much extra complexity you're willing to take on up-front, in exchange for safety and clean code down the line.
Conclusion
I hope this post was useful to you in some way, and helped you to understand the very basics of how to use a message broker in an enterprise application. It's very high-level, but if you have low-level questions, feel free to post them in the comments and I'll see what I can do to answer them in future posts!
Enterprise-level application development is often much different from non-enterprise application development. It requires a lot more discipline, and a lot better understanding of the design of the application by all of the people on the project. The reasons why are fairly simple: If the architecture supports modularization, a strong probability, and at the lowest level the developers have glued dependencies between all of the modules through the use of static classes or through plain and simple data sharing, then what was the point of having modules in the first place? Modules are intended to have separate, clearly delineated boundaries between each area of the application, so if there are dependencies between each and every module, then there's something disturbingly wrong.
How does one typically fix this? There are three ways, usually: A message broker, an enterprise service bus, or a simple service locator/inversion of control container, depending on the requirements of the system. I'd like to discuss all three here today, but I don't know enough about service buses to write anything intelligible about them. On the other hand, I've used service locators and message brokers out the yin-yang, so I'll write about those. For more info on service buses, I highly recommend Udi Dahan's blog, wherein he talks about them most of the time. :)
An IoC container/service locator is a simple construct that allows you to grab a reference to an interface without having to know how it was instantiated, nor what the concrete implementation of that interface is. This allows a very clean, simple architecture, although I tend to use an IoC container rather than a service locator simply for the all-powerful constructor injection, which requires an explicit declaration of dependency on the interface in question.
A message broker is most often used to communicate between processes or programs. They typically support a Publish/Subscribe model, where a programmer can send messages to a host of programs easily by publishing a single message on the broker. This can also be used for inter-module communication, however, and cleanly supports future integration with other applications.
How are these two similar, and what is the motivation for using them in the first place?
A clean architecture may have explicit dependencies between each module, but it does so in the form of interfaces. These interfaces can be stored in an intermediate project so that everyone has access to them. While this leads to a high afferent coupling, the coupling is to an interface, so it's less likely to break something if the implementing class has to change how it satisfies the interface. When you rely directly on the implementing class (instead of the interface), you get into trouble when that implementation class has to change substantially, mainly because the code that used it may need to change as well. If it was dependent only upon the interface, i.e. the core functionality that the class provides, it's less likely that the interface will have to change, because the implementation class can change much more easily to meet the needs of the interface, so you save in two ways.
A service locator or IoC tool can be used to mitigate the complexity of the construction of an object, as well as the inherent coupling to the concrete implementation class. Whereas before you might have had:
IUsageTrackingService tracker = new SqlUsageService(connectionString, other_bs);
Now, you would have the rather simpler:
IUsageTrackingService tracker = ServiceLocator.Resolve<IUsageTrackingService>();
Instead of having whatever class needs access to the usage tracking service newing it up itself, it is pulled in through a static service locator here and the using-class doesn't need to know the connection string or anything else about the usage tracker in order to get a reference to one. You can see how useful this is if you ever need to unit-test the usage tracker: Do you want to have it crush a database, or simply output the usage into a string which can be inspected way more easily? And unit-testing the class that uses the usage tracker? FUHGEDABODIT! (Pass an interface reference into the constructor of the using-class, and just mock it.)
A message broker works in a strangely similar fashion. What the service locator/IoC tool did through inherent reliance on the interface (in this case IUsageTrackingService), a message broker goes one step further and says, "I don't even know who is going to be getting this, but here's some indication that something is happening! AAAAAAGGHHHHH!" Here's how I think of a message broker: When you need something to happen (let's say we're still on usage tracking) but there's absolutely no reason whatsoever for a class to care who or what is responding to its clicking of an advertisement in the application, then a message broker can very, very cleanly implement that. In this case, you just have the class fire off a message such as:
broker.Publish(new AdvertisementClicked(module: Modules.Comedy, user: user.ID, advertisement: ad.ID); // Only using named arguments for clarity
Now, anyone who might want to catch that event can simply be subscribed to it upon instantiation of the message broker, and that leads to much, much cleaner code. Consider also that if the message broker were to just push the message into a queue, this could be processed completely outside of the main application somewhere and you'd take no performance hit whatsoever.
The key here is that the message broker removed dependency even upon the interface itself, so now the interface that you've created can change, if required, without the using-class having to change its code to handle it. It can be argued that in this case, you may not even need the interface at all, but I'll leave it as-is for now.
Downsides
There are several downsides to each of these methods. I'll discuss those now briefly because they are pretty self-explanatory, in my opinion.
ServiceLocator/IoC container - With a static ServiceLocator, you get the added lack of bonus of relying on a static singleton, which isn't great for testability. At the same time, the IoC container can hinder testing as well. With the ServiceLocator pattern, you tend to run into problems when someone wants to use a class, but doesn't realize it has some dependency upon some interface - since the interface dependency isn't explicitly defined in the constructor of the class, it's not nearly as easy for the user to know that they have to register that dependency before using said class. With an IoC container, this is less of a problem because they typically have constructor injection, which allows the class to explicitly define the interface in its constructor. Both of these methods have somewhat of a complex learning curve due to the fact that you never technically know which implementation is being used, unless you're in the place where that implementation is being registered as the interface. You may very well *not* have access to that; for instance, if you were working in a module and the registering of the implementations all happens in the bootstrapper, and the bootstrapper is part of a totally different project, then you may not have access to it. At the same time, it lends itself to very simple programming, where you just get the reference and call functions on it - dirt simple.
With a message broker, the learning curve is much, much steeper. In addition to not knowing which particular class that you care about is processing the message, there could be tons of classes other classes processing the message as well, which can interfere. If you don't have access to all of them, then it could be one of those other classes that has a problem with the message. For this reason, it is a standard of mine that, when a class is processing a message, I log it. That way, when it fails, it is at least logged and I can go back and see exactly where it failed, if not specifically what failed.
The message broker also requires some knowledge of threading typically, as well as weak references. When you have an event that is being published, it could happen on the main thread or on a background thread. This can vastly change the programming model, and is a bit harder for most developers to wrap their heads around. Similarly, the pub/sub model that is usually used is somehow difficult for some developers to understand and compute. Some programmers also seem to struggle with weak references.
Both of these methods are more complicated, but save you time and money in the long run - it's a matter of how much extra complexity you're willing to take on up-front, in exchange for safety and clean code down the line.
Conclusion
I hope this post was useful to you in some way, and helped you to understand the very basics of how to use a message broker in an enterprise application. It's very high-level, but if you have low-level questions, feel free to post them in the comments and I'll see what I can do to answer them in future posts!
Wednesday, January 19, 2011
Stardate 2011.19.1: Domain Events - Powerful, Stupidly Named
Today, I thought I'd point out something that is terrifically obvious: Domain events may be the strongest concept to come to domain-driven programming since the ubiquitous language. I almost always have an object of type DomainEvents these days because they're just so useful. They become a kind of repository for the different things that can happen in the domain that really have no other place - see Udi Dahan's website for more information about the concept of domain events.
Also, this is probably the worst name for a type in the history of mankind, and might be a mistake to have the object at all. The reason for this is that, like my rant against Commons projects, it often becomes a kind of repository for trash that just needs to be maintained over time. There are sometimes Action<T>s in it, which is a mistake, but also it is often a static class that just has the different possible domain events in it that can be raised statically. This makes it difficult to test, but there's also something more obvious: There's virtually no ubiquitous language which contains the concept of an explicit DomainEvents object in it.
This is pretty obvious, however, and does not take away at all from the usefulness of the concept. Often, we require a place in the domain where we can just do different things that aren't necessarily part of the normal flow of execution of the business domain. For example, when filing a legislative bill, there are a crapton of things that can happen before the bill even gets into the first committee. However, there's no explicit, "Here's what's going to happen every time!" You can't necessarily model it effectively as a function that follows another function, e.g. if you have a SendToCommittee function, you can't necessarily prefix it with all of the functions that may happen before it goes to committee - there are just too many possibilities!
So how do you handle it? The best way (in my opinion) is basically with an event. There are many different ways to implement events in most programming languages. Since I'm a .NET developer exclusively, I'm going to talk about developing domain events in .NET, and C# in particular. I have no fuss with VB development, nor VB developers, but I'm just not familiar enough with it to be able to talk about it intelligently.
The standard DDD way of handling domain events in .NET uses the weak-eventing pattern. This is a pattern where you have a list of WeakReferences to actions. These actions get executed if they're valid references, or are skipped if they are not. That then becomes your domain event. It has to be a list of WeakReferences due to technical issues with subscribing causing a hard reference to stick around when it probably shouldn't - perhaps because the objects that have hooked up to the event would otherwise have gone out of scope.
My next post will have more useful content. I just wanted to point out that having an explicit type called DomainEvents is probably not the right way to go. In the next post, I'll discuss how I typically handle it, and why I think it's stronger and better OO design.
So how do you handle it? The best way (in my opinion) is basically with an event. There are many different ways to implement events in most programming languages. Since I'm a .NET developer exclusively, I'm going to talk about developing domain events in .NET, and C# in particular. I have no fuss with VB development, nor VB developers, but I'm just not familiar enough with it to be able to talk about it intelligently.
The standard DDD way of handling domain events in .NET uses the weak-eventing pattern. This is a pattern where you have a list of WeakReferences to actions. These actions get executed if they're valid references, or are skipped if they are not. That then becomes your domain event. It has to be a list of WeakReferences due to technical issues with subscribing causing a hard reference to stick around when it probably shouldn't - perhaps because the objects that have hooked up to the event would otherwise have gone out of scope.
My next post will have more useful content. I just wanted to point out that having an explicit type called DomainEvents is probably not the right way to go. In the next post, I'll discuss how I typically handle it, and why I think it's stronger and better OO design.
Friday, January 14, 2011
Stardate 2011.14.1: Friday's Book
I like to read. Heck, I love reading. Reading is also incredibly important. As such, I'd like to start a kind of Friday book club, where I review a book I've read or am reading and make recommendations based on it.
The first book is what should be largely considered to be the Bible of Software Design. It is Agile Principles, Patterns, and Practices, by Uncle Bob Martin. The link to the book links to the C# version of the book, but I actually found the C++ book to be a bit better.
The work produced by Robert Martin in this book is quite prolific. It is built upon a solid foundation of scientific thinking about programming and I really appreciate that aspect of it. It is reminiscent of the good old days of C++ programming with Scott Meyers and Herb Sutter. Here are some
Highlights:
Solid SOLID discussion: This book was the first one to completely and clearly define all of the SOLID principles, to my knowledge. These include all of the principles that I've talked about before. They are incredibly useful and can almost be used to create a quantifiable design metric that tells you the quality of a given system. There are a lot of resources on the web about the SOLID principles, including Robert Martin's own blog, so I'll leave it up to you to research them.
Surprising project design discussion: When I first read the book, I hadn't really encountered much in terms of setting up physical project solutions. This book goes into great detail about the various principles that can be used to set up the projects in your solutions and it works incredibly well for the book, despite more of a focus on patterns and principles for the real code and not just the structure of the projects.
Practical pattern discussion: Whenever I see that someone has written a blog post or a new book on patterns, I die a little on the inside. 99% of these efforts are garbage, and half of the remaining percent are written without including any real code or practical examples. On the other hand, Robert Martin's books never lack for code and it's code that makes sense. It's not always enterprise-level code, but it can easily be analyzed and taken and used on enterprise-level code.
Lowlights:
BYOBB? That's a typo: While I like the book in general, my near-OCD for proper spelling, grammar, and punctuation makes most of Robert Martin's books somewhat difficult to read. I'm not sure who the editor for them is, but most of the time, a problem text can be figured out with a little thought. At the same time, they're not really significantly worse than other programming books.
Diagram it!: There's a huge, huge focus on diagrams and things like this. I find this to be incredibly tedious. It may be quite, let's say, youthful of me, but I find diagrams to be quite distracting. They summarize the information somewhat well, but following them can lead to a significant disconnect with the actual code and I find this to be dangerous. At the same time, diagrams themselves often don't completely or accurately reflect the evolution of the code over time, so it's another piece of waste that ends up being generated, and very few people will ever look at it, preferring rather to just dive right into the code.
The first book is what should be largely considered to be the Bible of Software Design. It is Agile Principles, Patterns, and Practices, by Uncle Bob Martin. The link to the book links to the C# version of the book, but I actually found the C++ book to be a bit better.
The work produced by Robert Martin in this book is quite prolific. It is built upon a solid foundation of scientific thinking about programming and I really appreciate that aspect of it. It is reminiscent of the good old days of C++ programming with Scott Meyers and Herb Sutter. Here are some
Highlights:
Solid SOLID discussion: This book was the first one to completely and clearly define all of the SOLID principles, to my knowledge. These include all of the principles that I've talked about before. They are incredibly useful and can almost be used to create a quantifiable design metric that tells you the quality of a given system. There are a lot of resources on the web about the SOLID principles, including Robert Martin's own blog, so I'll leave it up to you to research them.
Surprising project design discussion: When I first read the book, I hadn't really encountered much in terms of setting up physical project solutions. This book goes into great detail about the various principles that can be used to set up the projects in your solutions and it works incredibly well for the book, despite more of a focus on patterns and principles for the real code and not just the structure of the projects.
Practical pattern discussion: Whenever I see that someone has written a blog post or a new book on patterns, I die a little on the inside. 99% of these efforts are garbage, and half of the remaining percent are written without including any real code or practical examples. On the other hand, Robert Martin's books never lack for code and it's code that makes sense. It's not always enterprise-level code, but it can easily be analyzed and taken and used on enterprise-level code.
Lowlights:
BYOBB? That's a typo: While I like the book in general, my near-OCD for proper spelling, grammar, and punctuation makes most of Robert Martin's books somewhat difficult to read. I'm not sure who the editor for them is, but most of the time, a problem text can be figured out with a little thought. At the same time, they're not really significantly worse than other programming books.
Diagram it!: There's a huge, huge focus on diagrams and things like this. I find this to be incredibly tedious. It may be quite, let's say, youthful of me, but I find diagrams to be quite distracting. They summarize the information somewhat well, but following them can lead to a significant disconnect with the actual code and I find this to be dangerous. At the same time, diagrams themselves often don't completely or accurately reflect the evolution of the code over time, so it's another piece of waste that ends up being generated, and very few people will ever look at it, preferring rather to just dive right into the code.
Thursday, January 13, 2011
Stardate 2011.13.1: Interfeces - Property-only Interfaces
When it comes to abstraction, I always try to be very careful. The abstraction should not dictate the types that the implementing classes should contain. This is very dangerous, and is one of the reasons that inheritance can be very dangerous. Even having a base class for a piece of data that is common to all derivatives of the base is not that wise in most instances - it is more likely that the derivative is going to either need to manage that piece of data in some way, and if it doesn't, then why have it in the base class and not in its own class that isn't in the inheritance hierarchy?
Sometimes, properties on the interfaces are somewhat useful. For instance, Ayende once mentioned to me that something like SupportsRollbacks, a boolean, is perfectly valid on an interface defining an object that can have data rolled back. However, having property-only interfaces should be a design stench in any system. I have found two ways to this same conclusion, so I think it's justified.
The first path is that, if you have an interface that is only properties, then it doesn't really manage its own data: Some other class must obviously be managing the changing of the values and so forth. When looked at this way, it's obvious that encapsulation is pantsed.
The second way is much more general in that interfaces are intended to represent some functional unit, or some specific responsibility in terms of functions. While properties in .NET are technically functions in that, when you get or set them, you have a point that you can insert code, in terms of the public-facing interface, you can't tell if it's a property or just a public variable. Of course, Visual Studio allows you to know if it is or not, but I'm talking from a purely practical standpoint here. How many times did your teacher back in CS tell you not to use public variables?
Anyway, since properties give no indication as to any functionality that they actually contain, since they often represent nouns in the system and not verbs, having interfaces that are only properties is like having a base class with only public variables.
It gets worse if the properties are custom types. What if the custom type is abstract in some way? Then you're in a real pickle (especially since those abstract types are probably just pure properties!). These are all things that I've seen on projects, and it really points out just how bad this type of system is to work with, and especially to maintain.
Subscribe to:
Posts (Atom)
