A Service Ownership Model Fails When It Is Confidently Wrong
Stale ownership data misroutes incidents and can trigger destructive automation. What GitHub learned, the low water mark it added and what to measure.

Quick Answer
Ownership lookups have three outcomes, no answer, a stale answer and a confidently wrong answer, and the last is the most expensive because people and automation act on it. GitHub found its repository automation was safe against a Service Catalog outage but not against stale or corrupted data, so it added a low water mark that aborts any run planning too many destructive actions. Measure redirects and answer provenance, not catalog coverage.
A service ownership model is the set of records and rules that answer who is responsible for a service, a repository or a piece of infrastructure. We think most organisations measure it the wrong way, by how many records are filled in, when the costly failure is a record that is filled in and wrong.
GitHub's account of giving every internal repository a durable owner is a useful case, because it describes the failure nobody planned for. The catalog never went down. The risk was that it would keep answering, confidently, with bad data.
This post covers why ownership lookups matter in incidents, the three outcomes of a lookup, why ownership data decays, what GitHub learned, how a low water mark generalises, what to measure instead of coverage and when coverage really is the right first goal.
The First Task in an Incident Is a Lookup
When a high-severity alert fires, the first thing a responder does is rarely deep investigation. It is a lookup. The dashboard names the unhealthy service, and the next question is who owns it and how to reach them.
If that lookup fails, coordination stalls before investigation starts. We have seen teams lose more time finding the right people than finding the cause, especially for shared or older services. The same routing question sits behind many support escalations to engineering.
The industry has mostly treated this as an empty-field problem, on the assumption that reaching full coverage in a service catalog solves coordination. Coverage is necessary, but it measures the wrong failure.
Ownership Lookups Have Three Outcomes, Not Two
A lookup is usually described as found or not found. We find it more useful to separate three outcomes, because they cost very different amounts.
1. No Answer
The record is empty. This is an honest failure, and the responder knows immediately to escalate through a general rotation or their own network. It costs minutes.
2. A Stale Answer
The record describes how things were months ago. The responder may notice the decay when the listed channel is archived or the listed person has moved teams, and then has to start again.
3. A Confidently Wrong Answer
The record names a specific team that looks exactly like a correct answer. The responder pages that team, which cannot help, and the most expensive minutes of the incident go to recovering from the lookup. Automation acting on the same record does the wrong thing at machine speed.
The third outcome is worse than the first, yet most ownership dashboards reward moving from no answer to any answer without checking if the answer is right.
Why Ownership Data Rots Faster Than Anyone Budgets For
Ownership is not static. Reorganisations move boundaries, people leave services nobody else understands, and shared infrastructure often has no natural owner at all, so the real expert is rarely the owner of record.
Catalog tools enforce that a value exists, not that it is right. In Backstage, for example, the catalog descriptor format marks spec.owner as required for components and APIs, and describes the owner as a singular entity, commonly a team. A required field guarantees a name. It cannot guarantee the name is current.
Modelling choices add their own decay. GitHub found that its service-to-repository relationship meant a repository could only find an owner if it mapped to a service, so repositories without one had no reliable owner. We would expect most organisations to have a similar blind spot somewhere in their model.
What GitHub Learned Giving Every Repository a Durable Owner
GitHub's security team described the work in how GitHub gave every repository a durable owner. The trigger was a secret scanning remediation effort, where rotating a secret without knowing the repository owner was risky and remediation work had nowhere clear to go.
The starting point was large. GitHub had over 14,000 repositories in its primary internal organisation, and as of early 2025 over 11,000 were non-archived, most with no clear owner. Repositories attached to production services had robust ownership, while repositories with no associated service did not.
Over about a month and a half, the team validated ownership for every active repository, archived about 8,000 that were no longer used and made ownership mandatory at repository creation. It finished with approximately 3,000 active repositories and 11,000 archived, and later tightened the enforcement loop for new repositories from 30 days to one hour.
Two incidents shaped the design, and we think they are the most transferable part of the write-up.
- Archiving a repository without an owner broke a Datadog monitoring workflow that opened issues in that repository, and the owning team was paged.
- The team realised it was robust against a Service Catalog outage but had not considered that the catalog "might return stale data or corrupted data," which could have led it to mass-archive repositories with valid owners.
The fix for the second was a low water mark. Before acting, each run tallied how many archives and issues it was about to create, and if the number exceeded a conservative threshold it bailed out entirely and triggered a Datadog monitor. If the catalog was unreachable, the job skipped that validation rather than treating every repository as unowned.
A Low Water Mark Belongs on Every Destructive Lookup
The principle generalises well beyond repository archiving. Any automation that acts on ownership data it did not produce should check the volume of what it is about to do before doing it.
- An auto-assignment rule that is about to route an incident to a team never paged for that service before.
- An access review job that is about to revoke permissions for a large share of a team at once.
- A cleanup job that is about to delete a large share of catalog entries in a single pass.
- A cost attribution job that suddenly moves a large share of spend to one owner.
In each case the safe behaviour is to stop and ask a human, not to execute a confidently wrong command at scale. GitHub's own advice is to assume data sources will occasionally be wrong and to design for that from the start, which we would adopt as a rule for every destructive automation.
Measure the Lookup, Not the Service Ownership Model's Coverage
Coverage percentage cannot tell a stale answer from a correct one. We would measure the lookup itself, using four signals most teams can recover from data they already have.
- Lookup latency, the time from the first alert to a name a responder can act on, recoverable from incident chat timestamps.
- Redirect rate, how often the first team paged was not the team that resolved the incident, which directly measures confidently wrong answers.
- Answer provenance, when the owner was last confirmed by a real event such as a deploy, a merged change or an acknowledged page, rather than a manual edit.
- Silent dependents, the automations that read each ownership record and would misbehave if it changed.
The fourth is the hardest to find, as GitHub learned from the Datadog workflow. Ownership data feeds more systems than most teams list. GitHub's own CODEOWNERS documentation notes that code owners are automatically requested for review when someone opens a pull request that modifies code they own, which is one more automation reading the same records.
Some of the context responders need does not live in an ownership field at all. Recent changes, dependencies and behaviour come from the system itself, which is why we favour agents that read code, logs and deploy history directly over relying only on catalog metadata. Our post on on-call onboarding and time to first page covers the human side of the same lookup.
When Catalog Coverage Is the Right First Goal
We do not dismiss coverage. When most records are empty, as GitHub's were for repositories without services, filling them is the right first step, and GitHub's project started exactly there.
The point is the order of goals. Coverage first, then accuracy, then guardrails on automation that consumes the data. Teams that stop at coverage end up with a catalog that looks complete and fails in the third way, which is the hardest to notice. Our guide to incident severity under uncertainty makes a similar argument about decisions made on incomplete information.
Treat Ownership Data as Production Data
A service ownership model fails most dangerously when it answers confidently and wrongly, not when it goes down. Keeping it right is ongoing operational work that rarely has a ticket or an owner of its own.
We would add a low water mark to every automation that acts on ownership data, track redirect rate and provenance instead of coverage alone, and list the silent dependents before the next cleanup run. When an incident does start, Operate runs dedicated AI agents that investigate root causes with cited evidence and propose fixes for engineers to review.
Frequently Asked Questions
It is the set of records and rules that say which team is responsible for each service, repository or piece of infrastructure, and how to reach them. We judge one by how often its answers are right during incidents, not by how many records are filled in.
A service owner is accountable for a service's reliability, changes and incidents, and is the first escalation point when it misbehaves. We expect the owner of record to be the team that can act on the service, not just the team that created it.
Service ownership is the practice of assigning each production service to a team that builds, runs and answers for it. We think it only works when the ownership record stays current, because a stale owner sends responders to people who cannot help.
A service catalog is an inventory of services with metadata such as owner, dependencies and documentation links. We treat it as production data, because incident routing, access reviews and cleanup automation often read it without anyone listing those dependencies.
Require an owner at creation, confirm ownership through real events such as deploys and acknowledged pages, and review records after reorganisations. We also measure how often the first team paged was the wrong one, since that shows inaccuracy directly.
About the author
Operate Team
The team behind Operate
Operate Team builds Operate, enterprise AI agents for production operations. Operate answers production questions from Slack and Microsoft Teams, investigates alerts, and reviews performance, security and cost. It finds the root cause with evidence and proposes a fix for an engineer to review, with controlled access to your systems.


