The other day, at DevOps Midwest, Heath Moylan told a story from RGA from their evolution toward DevOps.

In the beginning there was no continuous integration. Then developer teams started running Jenkins on their own, each their own instance, and it was useful. In time, the larger organization noticed that it was useful. Meanwhile, these Jenkins installations aged: they were out of date, with lax password security. Clearly this is not OK for Compliance etc.

So a central team stepped up and operated One True Jenkins. The developer teams were free to use different workers, but the central Jenkins install was managed. Cracks emerged: plug-in versions conflicted, the build-success light was never the right color, and there was no good time to restart for upgrades.

Most recently, the compromise solution is for the central team to run Jenkins in a container, in many containers. The teams get their own configuration. Yet these still need to be maintained.

Centralization/decentralization is a pernicious tradeoff in development. Do we value consistency or flexibility? To defeat this tradeoff, draw the lines in the right place.

With continuous integration, I want some consistency: authentication, security and compliance checks. And I want some flexibility: build tools, formatting, what to do on a branch or PR vs the default branch. I want some team-specific features: what format to use, what to automatically fix, when to ask about deployment. I want some organization-specific features: code and dependency checks from security, approval checks from audit, where to publish artifacts and more from the platform team. Then there are industry-wide needs: triggering, cloning, load balancing, messaging on a failed build, status updates in chat and on the web.

Atomist draws these lines differently.

Atomist service in our network does auth, events, UI. SDMs in your network do checks, audits (security team) and build, test, autoformat (dev teams)

The Atomist service integrates with chat, version control (for triggering), and its own web UI. It receives, correlates, and then publishes events to Software Delivery Machines (SDM) that you own. These include a framework that defines things everyone wants to do: set goals for build, test, deploy, post-deploy checks, etc. Bonus: it’s a graph, not a pipeline. Make these choices based the code in the repository, instead of per-repo configuration.

You can have one SDM for the whole organization, or one per team, whatever you need. Central teams can add goals (and block deploy) on every repository in the organization. Use standard functions contributed by the community, or make the specific to you -- it’s all code. You have that power.

We don’t have to choose one or the other. Have consistency where you want it, flexibility where you choose. Define your delivery in code: just enough testable, modular code in a modern language.