A maintainable environment - anti corruption as a way of life
Recently I had a number of conversations about how to create a maintainable environment, not only for advanced developers, but an environment that enables beginners and intermediate developers to create good, maintainable, scalable solutions.
This problem is not a simple one, and there aren't really one off solutions. However, there is quite a lot that can be done, and I am very disturbed by the assumption that nothing can be done about it.
I noticed that a major part of the problem seems to be in the underlying assumption that in order to make it possible for beginners/intermediate developers to work with the application, you have to do one of two things. Embark on a long education period or dumb down the application to a level that beginners can deal with.
I am using the term "dumb down" on purpose. This approach goes for the easiest solution possible, those solutions tend to be very easy and supportive for trivial scenarios, but they get very complicate for any real world scenario. They also tend to be focused on RAD, with little regard to the overall maintainability of the solution. I am pretty sure that you have encounter such systems before, they are depressingly common.
The end result of choosing such an approach is an application whose complexity is not handled by the underlying platform, but rather at each individual case. This significantly complicate the applicatIon and working with in over time. As a quick example (which is sure to annoy a lot of people), I consider any application that has "new SqlConnection()" in it outside the infrastructure layer to be such a system.
The other alternative, however, is a lengthy training cycle, and slower productivity all around until you get to be proficient in the new approach. And, of course, some people will have really hard time adjusting.
Or so many people believe, at least. I strongly disagree with the previous statement.
The way I would choose for such a scenario (a team composed of developers of varying skills, being non trivial application) is to accept the fact that you cannot escape from the complexity and embrace that fact. Instead of trying to base the application on an overly simple foundation, I would base it on advance platform.
This advance platform would be able to scale to handle the complexity of the application, while concentrating that complexity into the infrastructure layer.
Some of the concepts involved in creating such an architecture are:
- Infrastructure Ignorance - If I have to deal with my infrastructure explicitly, then I need to have developers dealing with it on a regular basis. That doesn't mesh well with the idea of moving all the complexity to the infrastructure.
- Fizz Buzz concepts - the code that a developer should write should be simple and easy to follow.
- Follow good design principals - the code written should naturally lean toward single responsibility principal, separation of concerns, etc
- Easy to figure out - It should be simpler than the alternative for any non trivial scenario. Ideally, you can explain how to solve most scenarios using this approach in half an hour or less (ignoring the infrastructure part, which may be very complex).
- No training wheels - one of the things that drives me crazy is having two ways to do things. One for the average developer, the second for the architect. This usually comes out of putting training wheels on the first approach that make it hard to deal with in more advance scenarios. I see this as a sign of contempt for the rest of the members of the team. If you expect the rest of the team to work in a certain way, make damn sure that this is a way that this is a way that you can live with.
I think that I manage to get fairly close to this in my previous project, and it has proven to be a successful one. I talk about it a bit in this post.
I based that system on IoC, NHibernate and WCF. None of this concepts was exposed to the other developers. In fact, after setting this up, we were able to focus on the actual business issues far more often than on the technology involved.
By the way, I would fully expect that during the project, significant attempts would be made to get the other developers to understand. This technique is about getting a project started and the team productive very early, and doing this using a stable foundation.
Now, what is this anti corruption stuff in the title of this post? This is very simple, actually. It is here as more than the anti corruption than the anti corruption layers that Feathers is talking about in Working Effectively With Legacy Code. In this case, we start with the assumption that the infrastructure that we will use (even if we are the one building it) is suspect and should not be trusted, so we will do everything in our power to isolate our code from the infrastructure.
An important benefit of this approach is that we get the ability to modify the infrastructure independently of our application. This means that we can make significant changes very easily, because there is little to no dependencies between the two.
Comments
Hey Ayende, can you clarify something about this:
"I based that system on IoC, NHibernate and WCF. None of this concepts was exposed to the other developers."
If one of the other developers were to leave and go to another company, would they be able to implement IoC and NHibernate and WCF? If not, aren't those developers going to be a bit at a loss?
That is, if they are 'sped-up' within your environment by you 'hiding' the implementation details, won't they be a bit behind in another environment?
jdn
Jdn,
Would they be able to do this without me?
Yes. Maybe not using the approach (or the same tooling), but using the overall strategy.
Just before I left we had another similar project there, and the team lead decided that he wasn't going to deal with my infrastructure, so they took the overall idea and built a simpler version.
For the guys in my team, not at first, probably, but after a month or so of working wtih this? Yeah, they could do that.
I know that people off my team went on to other project using the same approach and tooling there as well.
As I said, if you just abstract it out and doesn't educate people, it is a big problem. The team should be able to understand what is going on. It is just not mandatory to deal with it all the time
So then the concepts were exposed to them?
Not say the first day (so they could hit the ground running with productive development), but as time went on?
I'm asking because of the obvious problem if they never learn it. Then they can't move on and be productive.
Thanks.
Oh, yeah.
In my case, I usually paired with them to get a particular piece of the infrastructure reworked on
We also built it from scratch a few times, to show how things where put together.
That was during the project, when they already had a feeling for how it works.
I wouldn't say that they all the members of the team could go and write a similar system without doing more research on it, but I tried to give them the required background and reasoning.
The few project that were spun off since then were using the similar approaches
Cool.
One of the things that I felt good about when managing/mentoring other developers was when they said "I feel like I've learned from you" and were able to go to other companies and be successful.
As I introduce more 'advanced' things like IoC and ORM, I wonder if it is better to give them a crash course at the start, or get them to start working and then get into the details. I feel an obligation to make any of them able to advance their careers without tying them into whatever quirks exist in my environment.
I mean, there are always job specific details, but I want to make sure that anytime I introduce 'advanced' things, that I don't hamper them.
If you know what I mean.
There are other issues, beyond technology. If you are a company´s developer aiming to apply alt.net, not a lead or manager, you may find some difficulty to introduce more "advanced" or "new" pratices.
Sometimes social skills are required to encourage people to try new approaches...
You know the benefits, but you need some tact to sell the idea.
I´m working with motivated people in my current project. These people are learning from me great things that I´m learning from some key books and blogs like this, but I´ve worked with developers that [conciously just want to do drag´n drop and fill events with some dataBind code and a manager that only cares only
system screens working].
There are a lot of people sharing this mindset. They just don´t care about internal quality, future maintenance, etc.
Their objective is to relesase it soon, the second release is "future" problem...
I agree with Bruno, it's pain to work with that 'it just works so WTF' guys, in past few years I realized that I never can win a war against the army of ignorants..
On the other side, there are a lot of people 'who cares' and that's great and motivate me to stay in this business.
I hear you loud and clear Bruno : I see this as well.
The cost of that is tremendous as well.
The hard part is creating an environment of developers that share these quality traits.
In my most successful teams, we had guys that spoke in terms of OO principles in an agile environment. It was a real eye opener for me.
I like the dynamism of software development, it produces a lot of creative work, but sometimes the lack of well documented standard pratices bring us to real political discussions, "religous wars" and things like that.
You can say DDD is the key, but our coleage (a "best-country-university" graduate),
eventually don´t know it and here comes the "social skills" to "encourage" people and "sell" the idea.
Acctually I don´t like to pratice theses "social skills". To address these issues the alt.net community could encourage some key pratices in a more explicity way.
I agree, there are a lot of motivated people, and I believe motivation is the key.
I work with senior developers and we have only one that is under two years of experience. On top of that many of us have worked together for over 15 years so we are well acquired with each others strengths and weaknesses. And we each have our own unique take on how things should be done.
What we do all agree on is that we need an infrastructure that isolates the business domain from the complexity so that we concentrate on the business problems. A couple of us work in the core infrastructure components but most of the rest of the team uses them. The core is fairly stable and works well enough that we don't have to spend a lot of time maintaining or enhancing it.
Recently I looked into moving to MS MVC. However, I'm pushing back on this because of the paradigm shift that it would take moving from the event driven web forms to the REST approach. There is no doubt that the members of the team could make the shift but I'm not sure about the time it would take.
The point I'm making is that I agree that you shouldn't 'dumb down' the infrastructure but sometimes you have choose to not make a change that adds to the complexity either in the infrastructure or the way to code the solution. However, I am still in discussion with another member and we may still decide to make the move. If not now maybe later in the year.
Interesting post but it made me think there's got to be a better way. Surely the great minds that make up the development community can create technology that is both architecturally sound (follows best practice etc) AND is understandable to even the most junior of developers without a "long education period". I expand a bit on this thought here, http://andrewtokeley.net/archive/2008/03/24/building-a-maintainable-environment.aspx
Comment preview