The most important artifact any development team produces is raw, running, naked code. Everything else is secondary or tertiary. However, that is not to say that these other things are inconsequential. Rather, our models, our processes, our design patterns help one to build the right thing at the right time for the right stakeholders.
Yet, while code is king, one must realize that it is also a servant, for it in the end must serve some constituency, deliver some measurable value. Just as I loathe architecture astronauts—people who have no skin in the game, people who are so divorced from the reality of executables that they melt in the sight of a line of code—I also loathe code bigots who are so blinded by their own prowess and tools that they lose sight of why or for whom they are toiling. Design for design’s sake is meaningless; code for code’s sake may be fun but it is also meaningless.
Recognize also that there are very real tensions between doing the right thing in the short term and doing the right thing for the long term. Code centricity tends to draw you to the former; architectual centricity tends to draw you to the latter, and honestly, neither pole is correct, but rather it is the dance between the two for which a particular team with a specific culture working in a given domain must find balance.
This quote probably hits home for many developers. There needs to be a balance between using an architecture to improve the process of software development versus developing working code that does what the client expects.
Trade-offs are usually made in projects due to budget, time, or resource constraints, but the chosen tools and architecture (whether custom built or based on an existing pattern) should at least exhibit these features:
- The architecture should lend itself to scalability and maintainability. The final application will need to grow and other developers will need to take over programming duties. If your architecture is so rigid and convoluted that it can’t grow, it probably needs to be redesigned.
- The methodology and design patterns should not be overly complex. While a learning curve is acceptable, if it takes an inordinate amount of valuable project time to learn the ins-and-outs of the architecture, it may not be worth using, especially for smaller projects.
- The architecture must help solve the problem at hand. As Joel Splosky described in his diatribe against “Architecture Astronauts”, tools are just that — tools to help build a solution. People have a tendency to separate the business and technical problem from the underlying architecture, favoring what they know or what they view as the “acceptable” way to do things (“If all you have is a hammer, every problem looks like a nail”).
- The architecture should promote best practices and lead programmers into developing in a structured manner. In Code Complete, Steve McConnell describes the role of good architecture:
A well thought-out architecture provides the structure needed to maintain a system’s conceptual integrity from the top levels down to the bottom. It provides guidance to programmers — at a level of detail appropriate to the skills of the programmers and to the job at hand…
Good architecture makes construction easy. Bad architecture makes construction almost impossible.
Grady Booch summed up the balance between architecture and working code pretty well, and this is coming from a man that has been at forefront of object-oriented design. There are no hard and fast rules about which design to use in which situation, and this is why a good deal of thought needs to be given in the architectural phase of any project.