A while ago I was supporting a company that offered a digital platform to small and medium-sized business in a specific industry. Great people, interesting ideas — a very enjoyable experience.
This platform was composed of independent products which were connected only very loosely. Some of these products were also marketed to customers independently of this platform.
Greater flexibility, greater inconsistency, more duplication of effort
This approach provided great flexibility to the company and its partners, independence and perhaps even a friendly and good-natured competition of ideas and approaches. However, these products (or services) provided very different experiences to their users — in terms of visual design, but also in terms of interaction design, terminology, data structures etc..
This could be considered to be largely acceptable as users understood (at least to some degree) that different products were used by this platform, but a higher degree of consistency would likely have been appreciated by users. However, that company also experienced a higher degree of feature duplication than would have been acceptable in any of the initiatives I’ve worked before.
Trading consistency for team effectiveness and efficiency?
More cohesive platforms (products, services, applications, whatever), or platforms that are desired to be perceived as more cohesive by users, can be negatively impacted by much subtler inconsistencies than the ones I described above. Avoiding these inconsistencies while maintaining team effectiveness and team efficiency is what this discussion is all about.
There seems to be a broad consensus that many types of software are best built and developed by cross-functional, self-organizing teams with about five to nine members using lean and agile approaches. (There are types of software and problem domains that require different approaches or need to be supplemented by additional practices, for example in health and safety related domains. I don’t focus on these here.)
Much software requires more than a single team to build and run. At this point, a decision on how to shape these teams and which responsibilities they take on becomes necessary. This decisions will have a significant impact on how the teams work, on how they collaborate and communicate with each other, and on the results they produce.
Teams shaped by functional domain
The common approach seems to be to organize teams by feature or functional domain. In this case, the teams would cover the full technology stack from front-end via services and application down to databases, storage, integration and compute infrastructure. This is certainly better than organizing teams by software layer such as user interface, application logic, underlying domain logic, and the data access layer.
In an e-commerce context, one team might take responsibility for product browsing and selection while another team might be responsible for the checkout process. A third team might take responsibility for account maintenance.
This might look something like this:
This is not unreasonable when we look at a single web application — but it may not be without problems even in this limited case. Great care needs to be taken so ensure that the boundaries between these teams do not lead to observable boundaries between these features or functional domains. For example, we do not want the user interface to subtly change when moving from product selection to checkout. (Think Conway’s Law.)
Going further, how does this approach scale to different client apps and interfaces? What if we want to add an iOS app? An Android app? Plus a public API? And support for voice assistants?
Adding people with the necessary skills to the teams is likely to cause the teams to grow beyond a reasonable size (even if individual team members are skilled in multiple areas). And the problem of ensuring integrity in these client apps and interfaces multiplies with the number of apps and interfaces.
App teams and service teams
To me it seems beneficial to separate the responsibilities for the client apps and interfaces from the services (or components) providing functional capabilities (i.e. managing access to data, implementing calculations, or implementing a business interaction such as placing an order).
This might look like this:
This allows app teams to focus on their users, the context they live and work in, their needs and preferences. Ensuring experiential and structural integrity within a single app becomes easier. App teams can also develop deeper expertise in the app-specific technology stack (e.g. web front-end vs. native mobile front-end vs. API management infrastructure).
Similarly, teams taking responsibility for services (or components) in a functional area can develop deeper expertise in this functional domain (e.g. pricing, order fulfilment, or product configuration). These teams can also develop deeper expertise in their service-specific technology stack.
Broad and shallow vs. narrow and deep responsibilities
I view app teams as having broad yet shallow responsibilities while service teams have narrow yet deep responsibilities. This refers to the breadth of functional scope and the depth of the technology stack. (I do not imply that app developers are somehow less technically adept or that their work is less technically complex than that of service developers. But in order to display a price to a user I do not have to know how to determine that price. And in order to determine that price I do not have to know when and how to effectively display that price to a user.)
I envisage these broad app teams and the deep service teams like this:
This approach to organizing teams requires collaboration between the app and the service teams to design and evolve the service API. We replace informal collaboration between team members (e.g. those focused on the UI and those focused on service implementation) with formal cross-team collaboration on an interface. This collaboration on the interface also ‘pays’ for mitigating the risk of friction at the boundaries of different parts of each app.
In this context, I’m thinking more about data-centric services (probably with a fairly generic and perhaps somewhat coarse-grained interface) rather than fine-grained RPC-style functions dressed up as a not-quite-RESTful JSON-over-HTTP interface. This should lead to increased stability (i.e. reduced volatility) of the interface and simplified dependencies (i.e. coarse-grained rather than fine-grained dependencies).
This is not “separate teams per software layer” — I think
So, I’m not — at least I don’t think I am — naïvely advocating for removing the UI layer from the application component, and thus advocating for a minimal form of separate teams per software layer. Instead, I view the different client apps and public APIs as individual products. I think that these products need to be product-managed. Similarly, I view these underlying functional services as products. The sum of their interfaces form an API (potentially, an internal API) which I view as another product. These products need — and deserve — to be product-managed, too.
What’s wrong with this?
And now, considering that this approach does not seem to be widely discussed, the Gretchenfrage: What am I missing? Why doesn’t this make sense? What would be a better principle for organizing teams in such a setting? Why is the team-by-feature approach superior?
I typically work for medium-sized to large companies building B2C, B2B or B2E products. Building significant features or functional capabilities typically requires collaboration and alignment with multiple groups within in the company. Such capabilities often depend on additional systems beyond the team’s control. YMMV.
As a bonus, the diagrams in this post show clearly that there is a difference between a visual designer and a graphic designer. Ah, well…
In their book Disciplined Agile Delivery: A Practitioner’s Guide to Agile Software Delivery in the Enterprise, Scott W. Ambler and Mark Lines write about The Agile 3C Rhythm (chapter 1):
“Over the years we’ve noticed a distinct rhythm, or cadence, at different levels of the agile process. We call this the agile 3C rhythm for coordinate, collaborate, and conclude. This is similar conceptually to Deming’s Plan, Do, Check, Act (PDCA) cycle, were coordinate maps to plan, collaborate maps to do, and conclude maps to check and act.”
While I prefer the Plan – Do – Study – Adjust variant of Deming’s cycle, I definitely agree with the fundamental assessment. This rhythm also maps nicely to the Plan – Brief – Execute – Debrief cycle, i.e. the Flawless Execution Engine described by James D. Murphy in his book Courage to Execute: What Elite U.S. Military Units Can Teach Business About Leadership and Team Performance. Here, coordinate maps to plan and brief, collaborate to execute, and conclude (mostly) to debrief.
Ambler and Lines continue:
“The agile 3C rhythm occurs at three levels in the DAD framework:
1. Release. The three phases of the delivery lifecycle—Inception, Construction, Transition—map directly to coordinate, collaborate and conclude, respectively.”
From a client’s perspective, these three phases seem more relevant to me than the four-phases model proposed by the older Unified Process: the Elaboration phase proposed by UP seems much more relevant to the service provider (i.e. the software development organisation) than the solution’s customer.
“2. Iteration. DAD construction iterations begin with an iteration planning workshop (coordinate), doing the implementation work (collaborate), and then wrapping up the iteration with a demo and retrospective (conclude).”
There’s not much to add to this description. When releasing a working solution into production every iteration, the release and iteration cadence described here overlay each other.
“3. Day. A typical day begins with a short coordination meeting, is followed by the team collaborating to do their work, and concludes with a working build (hopefully) at the end of the day.”
We expect working builds many times a day, but a nightly build (or better, the last continuous build of the day) is a worthwhile thing to have.
Now this description of a fractal rhythm isn’t rocket science, but it resonates nicely with my own experiences: I have this pattern.
PS: Reading Disciplined Agile Delivery was worthwhile to me. It describes a framework that many organisations try to build at home. It focuses on generic terms, which might allow us all to collaborate a little better. I like the fact that it is open to different development methods, providing explicit lifecycles for Scrum and Lean/Kanban environments.
A few weeks ago I joined an up-and-running software development (and service operations) project together with a few other people. The team had already launched the first version of the product successfully. We had heard that huge effort had been put in to achieve this success and we had a hunch that the team would likely benefit from a renewed emphasis on certain lean & agile practices. We also had a hunch that the team wouldn’t benefit from us showing up and starting to lecture from the latest Scrum book or so.
I consider us extremely lucky to work in an environment in which we are free to choose our working practices (obviously within reason). I also consider us extremely lucky to work in a great team willing to own their work — and to put themselves on the line every day trying to improve our performance while at same time having to deliver against high expectations.
Listening to the team and the people around us, and establishing a shared understanding of our goals (including trade-off priorities; hat-tip to Alistair Cockburn) and the forces acting on us seems to be the essential foundation for our learning. After that, getting out of the way seems to be the best thing us management types can do. Every so often, we can provide some support and advice, or offer some re-assurance and confirmation. But mostly, it seems to be about getting out of the way and keeping the way clear of other obstacles as best as we can (we have way to go on that one).
Our work practices seem to become more lean & agile by the day, and I think our performance is improving. This post makes reality probably sound easier than it is, but I feel things are going so much better than whenever I’ve seen project teams being instructed to “be agile”.