Issue No. 05 - September/October (1999 vol. 16)
In 1961 or 1962, Fred Brooks approached Jerry Weinberg at the IBM Systems Research Institute in New York and asked him whether he thought the term architect was suitable for software systems people. At the time, Weinberg had already been incorporating ideas from architecture in his courses on system development. Brooks was concerned about the fidelity of the analogy, but it seemed to hold in their ensuing discussions as they fleshed it out. From then on, the term became a fixture of the discourse on software design.
This was an important chapter in software engineering—a latent field grasping for the kind of formal foundations found in more established technical fields. The engineering disciplines had math and physics to stand on, and math stood on a millennium of logic and formalism. The software field found several adopted parent disciplines with which to form reciprocal relationships, starting with the most fundamental and increasingly moving into higher technology realms. The first was mathematics, building on the foundation of Kleene's, Turing's, and other mathematicians' and cyberneticists' work. Their visions fueled much of the programming work in the 1950s. Architecture joined the discourse in the early 1960s. And, in 1968, Peter Naur provocatively evoked the term software engineering. Maybe it was meant as a joke, but the term stuck. Unfortunately, this term opened the door for hardware engineering techniques in software, bringing the drawbacks that Louis Perrochon and Walter Mann elaborate on in "Inferred Designs."
Architecture found its home in software development as the grand, celebrated station of software abstraction. Because of this, the metaphor lost something from its original meaning. The building architect Ludwig Mies van der Rohe personally selected the doorknobs for the houses he designed because he knew—as in the phrase usually attributed to him—that "God is in the details." Software architecture distanced itself further and further from this detail, evolving beyond domain expertise to an abstract and idealized practice that became increasingly distant from the mores and structures of particular domains. Software architecture increased its focus on formalism and rigor (architecture description languages, design notation, and methodology) and became almost synonymous with abstraction—an antithesis to Mies van der Rohe's details. Architecture was elevated not only to an artifact in its own right, apart from the artifacts delivered to the customer, but also to a major step in waterfall processes. Software is not alone in this regard; the building architect Christopher Alexander (in his article "The Origins of Pattern Theory: The Future of the Theory, and the Generation of a Living World") laments analogous changes in his field over the past century. Software architecture seems to have lost its roots, a victim of a young industry's "formal envy."
Finding Our Center
What is the purpose of architecture? In the building profession, we find the Vitruvian triad: beauty, utility, and durability. Clearly, beauty was never a manifest goal of many schools of software architecture, although it was occasionally a happy accident resulting from a particularly gifted or fortunate development team. Utility at least has been given lip service in software, but firm principles of utility seem to elude software architecture. The architectural community does focus on durability—what we call maintenance—but usually by focusing on the artifact called architecture that is separate from the deliverable code—where the rubber of technology hits the road of markets. And, in spite of software designers' best attempts, architectures aren't robust. Phrases such as "software brittleness" have entered the discourse. Brooks, who popularized the concept of software architect, recommended rebuilding a system from scratch every few years to recover from entropy. 2
Objects started attracting attention in the early 1980s. Their early attraction had little to do with architecture, but more with the OO platforms that introduced windows and mice. The industry sang the praise of objects because of their ability to capture real-world structure. Yet, this was nothing new; Fortran programmers had long been able to capture the principal abstractions important to mathematicians and physicists. Although the object paradigm provided new tools to capture abstractions outside mathematics, it was even more valuable for its anthropomorphic focus. In the exploding enterprise of software development, specialization became increasingly important: to write software for a particular video game genre, for a particular kind of industrial robot, or for a particular family of financial instruments requires intimate knowledge of the business discipline. Programmers relate to the specific resources and devices they work with each day, and objects became a way to capture and nurture the software that reflects that understanding.
The object experience highlights what had been important all along: architecture is not so much about the software, but about the people who write the software. The core principles of architecture, such as coupling and cohesion, aren't about the code. The code doesn't "care" about how cohesive or decoupled it is; if anything, tightly coupled software lacks some of the performance snags found in more modular systems. But people do care about their coupling to other team members. The structure of the organization that builds the software is homomorphic to the structure of the software; it's not always clear which is cause and which is effect, so we'd better get both right. Of course, this is Conway's law, usually attributed to his 1968 Datamation article, 3 based on his notion that any compiler written by N teams of people would be an N-pass compiler.
One of the main purposes of architectural partitioning has been to recognize design's anthropomorphic nature: people work best when they can nurture something, contribute it to a whole, and be proud of that specific contribution while being part of something bigger than themselves. This played out in the OO world through techniques such as CRC cards, 4 a role-playing design technique built on the social structure of the development team rather than the insight of a central architect or the rigorous principles of a design method. CRC cards are about the allocation of responsibility (a human, not technological, concern) and are built on the knowledge or (even better) the instinct that lets the team leverage basic, intuitive principles of good design.
This perspective would come to its fruition, at least conceptually, in the next major wave of software architectural practice: patterns. An articulated goal of the early pattern advocates was to restore dignity to everyday programmers and to recognize them as the source of valuable architectural contributions. 8 The pattern community still strives to build a body of literature that captures these perspectives. But more than that, the pattern community recognizes a broader and perhaps more powerful dynamic: that architecture, like any system discipline, is about relationships between system parts and, according to Conway, between people. This perspective addressed a common shortfall of the earlier object work, which could be traced back to modular architectures. We can't build systems by focusing on isolated parts or on the coarse partitioning usually associated with architecture. It comes back to Mies van der Rohe's doorknobs.
A FULL CIRCLE, PIECE BY PIECE
Another important phenomenon—though neither novel nor unique to objects or patterns—is the growing internationalization of software. The world has shrunk appreciably in the past two decades, and more and more software development crosses geographic locations and cultures, exacerbating the issues of both partitioning and human relationships. We've forgotten, too, that the greater legacy of building architecture is steeped in culture.
Although we look to "movements" like objects and patterns as the source of these revelations about systems and people, they are just barometers of the industry's struggle with ever-increasing complexity. Architecture is not only about partitioning but also about abstraction; the two are hopelessly related. It seems natural that one of the industry's greatest needs, to tackle complexity with abstraction, would surface as the central feature in the major architecture advances of the era where this complexity started becoming oppressive.
There are other signs, outside these popular currents of thought, that also give voice to this renewed focus on systems and relationships. Management and process have attracted increasing interest, as evidenced by the explosion in process standards and the growing number of software management books. More importantly, a quiet revolution happened in software shops worldwide. It didn't always have a name, but it was equated with "empowered teams" or "Borland Software Craftsmanship" 1 or something else. These efforts were a move away from formalism and rigor, away from centralized architecture to the piecemeal growth of software systems under a participatory process. More likely, the industry came to a realization that these phenomena are the reality beneath the historic illusions of formalism and master planning. Richard Gabriel notes that
Software development is always through piecemeal growth and rarely through thorough design. Such planned development can lead both to technical problems because the future of a piece of software cannot be known and also to social problems because completely planned development alienates those developers who are not also the planners.5
David Parnas also adds his support to this perspective:
Many of the details only become known to us as we progress in the implementation...Even if we knew all of the relevant facts before we started, experience shows that human beings are unable to comprehend fully the plethora of details that must be taken into account in order to design and build a correct system...Even if we could master all of the detail needed, all but the most trivial projects are subject to change for external reasons.6
This perspective is directly relevant to Christopher Alexander's architectural concerns: "In order for the building to be alive, its construction details must be unique and fitted to their individual circumstances as carefully as the larger parts...The details of a building cannot be made alive when they are made from modular parts." 7
This means selecting the doorknob separately from the door, making sure software is crafted to fit the system. The essence of architecture is to answer the question, "How do the pieces fit?" The development team in Steven Stolper's article, "Designs that Fly," addresses this by "meeting in the middle" of the scale of abstraction and granularity—not by assembling premanufactured parts nor by following a master plan.
Although Parnas advises us to "fake it" 6 because there are so many large uncertainties on the way to correctness, there is another way: piecemeal growth. This means build a little, look at where you are, and build a little more; then, things fit. Gabriel insists that most software is done this way, and I agree. The project described in Perrochon and Mann turns the world around, basing designs on implementations instead of vice versa. Why? Things change so quickly—in the external requirements, in the constraints that come from progressive revelation, and in the uncertainties and changes in implementation technology—that requirements documents have ephemeral truth. If a project were to fake it, the faking would have to be so good that at the end everything looked as consistent as if it were the result of an ideal process that produced a single set of artifacts. It is not only that we understand requirements piecemeal, as Parnas admits, but that the very process is necessarily piecemeal, as Gabriel observes. Why fake it when you can embrace and capitalize on the uncertainty? It's important to honor the human constraints; they'll most often win out over the technological ones.
While we usually think of an architecture as a sort of collection of contracts that formalize interactions between people, the reality of everyday development is much closer to the vulgar end of the spectrum. Software development is primarily a social activity, and the ability to properly negotiate or even understand interfaces comes down to issues of personal communication preference (e-mail versus telephone), culture, and trust. Much of it rests on informal communications at the water cooler and in the hallways and stairwells. Communication problems are greatly amplified in multisite development projects, and architectural processes must heed these concerns. In "Architectures, Coordination, and Distance: Conway's Law and Beyond," James Herbsleb and Rebecca Grinter discuss the results from their studies of such projects and offer suggestions—both for the architecture of the system and the conduct of the organization—to avoid the recurring problems they observed.
That's the inside story, the story about getting our act together inside our discipline. But our horizons must be broader than that. Software is woven into the infrastructure of everyday life. All we do as programmers—and all programmers are software architects to some degree—somehow changes the life of every man, woman, and child on earth. The power of this influence is staggering. As software architects, we are as much architects of a new world as the architects of Rome, China's Forbidden City, or Jaipur were. Christopher Alexander has always understood the power of architecture in supporting the life of culture, but even he feels that the building architecture profession presents obstacles too large for it ever to be a vehicle for broad human comfort and dignity. However, he keenly appreciates our influential position, and he offers us a sobering challenge.
Today, we quietly stand at an architectural threshold. Perhaps, the next paradigm shift will find that people don't work best alone, and the time-honored sacrosanct principles of coupling and cohesion will be the next casualties of reality. Or, perhaps, the next paradigm shift will leave the technological bases largely untouched and rise to Alexander's challenge to build systems that are "morally profound." The articles in this special issue are intended to provoke thought and dialogue on the full range of architectural discourse and to offer hope in the search for that elusive quality called great design.
James O. Coplien is a Distinguished Member of the Software Production Research Department in Bell Laboratories. He has a BS in electrical and computer engineering and an MS in computer science from the University of Wisconsin at Madison. Coplien is the author of Multi-Paradigm Design for C++ (Addison Wesley Longman, 1998) and Advanced C++ (Addison Wesley Longman, 1992).Coplien's research interests include software architecture, particularly multiparadigm design, object-oriented design, and architectural patterns; ethnographic studies of software development organizations; and the theory of patterns, including temporal patterns and pattern symmetry. He writes a patterns column for the C++ Report, is a Member Emeritus of the Hillside Group (a small consortium of industry leaders providing industry-wide leadership and support in the pattern discipline), and was program chair of ACM OOPSLA 1996.