Why a Backstage software catalog fails without an ownership model
A Backstage software catalog fails when it lists services that nobody owns or keeps current. The portal looks complete on the first day, then drifts: components are renamed, teams are reorganized, repositories are archived, and the entries still point to people who have moved on. Developers learn quickly that the catalog cannot be trusted, and they stop opening it. The fix is not a better YAML template. It is a clear answer to the question of who maintains each entry, and that answer has to exist before any ingestion job runs.
The Software Catalog is one of the core built-in features of Backstage, alongside Software Templates and TechDocs. Its value depends on two things: how well the entity model reflects your real systems (components, systems, APIs, resources, and groups or users as owners), and how accurate the owner references are. A catalog with perfect schemas but wrong owners answers the question "who do I call about this service?" incorrectly, which is the question it exists to answer. The technical work of writing descriptors and configuring ingestion is comparatively straightforward. The hard part is organizational: someone has to accept responsibility for each entry and for changing it when the service changes.
Teams usually need this work when a portal project moves past the pilot stage, when a platform team is asked to show which services exist, or when incident response and compliance reviews start relying on catalog data. The difficulty is easy to underestimate. Duplicate entries appear when the same service is registered through a manual file and an automated provider. Stale owners accumulate when a team reorganizes but the owner field still names a retired group. Ownership gaps appear for shared libraries, legacy services and infrastructure that no single team claims. Each of these needs a rule, not a one-time cleanup.
Before designing the model, confirm three things with your engineering leadership: which teams are the accountable owner for each system, how group membership is sourced (for example, from your identity provider or a directory you maintain), and who approves changes to ownership when a service moves. Ask who reviews orphaned entries and how often. Write these answers down. They determine which entity kinds you model, which ingestion sources you trust, and how the catalog is reconciled over time.
Plan for ongoing effort after launch. Ownership data changes whenever teams change, so the catalog needs a named steward, a review routine, and a way to surface entries with no owner or an owner that no longer resolves. Treat these as operating tasks with an owner of their own, not as side effects of a project. Teams that skip this step usually rebuild the catalog within a year, and the cost of that rebuild is almost always higher than the cost of setting the ownership model correctly at the start.
Which catalog entities and ingestion points Backstage uses
The Backstage catalog is built from a small set of entity kinds, descriptor files kept with source code, and the processors and providers that bring entities in from other systems. Each choice affects who owns what, how fresh the data is, and how much maintenance the catalog needs. Confirm exact kind names and fields against the Backstage version your team runs before you write the model.
Component and system entities
Components describe deployable units such as services, websites and libraries, and systems group the components that work together for a business capability. Decide the granularity before anyone writes descriptors, because a system that is too broad hides ownership and a system that is too narrow multiplies entries. Agree on the naming rules, the lifecycle values each team will use, and which component types are in scope for the first rollout. Check the kind and type fields in the version you run.
API entities and their relationships
API entities record the interfaces that components provide or consume, along with their definitions and owners. Decide which APIs are catalogued in the first phase, such as public or cross-team interfaces, and which stay in their own repositories. Define how providesApis and consumesApis links are maintained when a service changes its contract. Confirm which API types and definition formats your version supports before you commit to a convention.
Resource entities for infrastructure
Resource entities represent infrastructure a component depends on, such as databases, queues and storage buckets. Decide which infrastructure is worth cataloguing, since every resource needs an owner and a maintenance path. Map each resource to the components that depend on it so incident responders can trace impact. Confirm the resource types and dependency fields your Backstage version supports, and agree who updates entries when infrastructure is retired.
Group and user entities
Group and user entities define the teams and people that own catalog items, and they are usually populated from the identity provider rather than typed by hand. Decide which identity source is authoritative, how group hierarchy maps to your org chart, and how ownership is recorded when a team is renamed or split. Confirm the group and user fields your version supports and the sync schedule for each provider. Stale ownership is the most common cause of unowned catalog entries.
catalog-info.yaml descriptor files
A catalog-info.yaml file kept beside source code lets the owning team describe a component in the same pull request that changes it. Decide where the file lives, who may edit it, and which fields are required by your review rules. Add a check in continuous integration that validates the descriptor schema before merge. Confirm the file name, discovery settings and required metadata for your version, since the expected layout changes between releases.
Processors, providers and the catalog database
Providers and processors read entities from repositories, cloud accounts and identity systems, then write them into the catalog database, which Backstage backs with PostgreSQL in production. Decide which sources are polled, how often, and which credentials the catalog uses to read them. Plan the database as a stateful service with backups and a restore test, because the catalog is only as current as its last successful ingestion run. Confirm the processors and provider settings your version ships before building custom ones.
Choosing catalog-info.yaml files or providers for each entity source
This table compares committing catalog-info.yaml descriptors in each repository, importing entities from a source of truth through providers, and a hybrid of the two. Read each row as a trade-off: the option's fit, what it costs to run, and who should be allowed to change each entity. Most teams end up hybrid, with repository files for components they own and providers for people, groups and inventories that already live elsewhere.
| Option | When it fits | Operational cost | Who may edit the entity |
|---|---|---|---|
| Descriptor files in each repository | Components whose owning team already maintains the repo and wants metadata reviewed in the same pull request as code | Each team keeps the file current, reviews changes and fixes drift; catalog updates follow the next ingestion cycle, so lag is usually small but not zero | Repository maintainers, enforced through CODEOWNERS and branch protection on catalog-info.yaml |
| Providers reading a source of truth | Users, groups, and inventories already kept in an identity provider, service registry or CMDB that must match the catalog | Depends on a connection to the external system and its API limits; sync lag is set by the schedule; mapping rules need upkeep when the source schema changes | Edits happen in the source system, so access control sits with that system's administrators, not with catalog users |
| Hybrid model | Most organizations: code-owned components in repositories, people and shared infrastructure through providers | Two ingestion paths to monitor; duplicate or conflicting entity names must be resolved by a stated rule; more review points | Split by entity kind and by location, documented in a single ownership matrix that names the approving team for each source |
| Descriptor files with a required owner field | Teams that need every component to resolve to a real owner before it is listed | Owner values must match real group or user references; validation in CI adds setup effort and blocks merges when references are wrong | Owning team edits, platform team sets the validation rules and reviews exceptions |
| Provider-only inventory for resources and systems | Infrastructure, databases or APIs described by a registry or cloud inventory rather than by hand | Mapping logic and credentials to the registry need ongoing care; stale records surface as orphaned entities that someone must triage | Registry or cloud owners edit records; catalog maintainers control only the mapping and filters |
| Manual catalog entries in the UI or ad hoc files | Short-term pilots or one-off entities during migration from a wiki | Changes bypass review and history is harder to audit; cleanup is usually needed before the portal is used broadly | Ideally restricted to the platform team; set this explicitly before onboarding teams |
| Ownership decision to record per entity kind | Before any ingestion path is built, for users, groups, components, APIs, systems and resources | Unclear ownership causes orphaned entities and disputed edits; writing the matrix early costs little compared with later cleanup | Name one accountable team per kind and one approver for changes to shared or cross-team entities |
How to build the Backstage software catalog in order
This sequence takes a Backstage catalog from an agreed entity model to full ingestion across the organization, with a check at each stage so ownership data is trustworthy before it reaches every team. Each step builds on the one before, so later sources do not introduce orphaned owners or duplicate entities.
Agree the entity model and naming rules
Platform architects and a small group of service owners decide which entity kinds the catalog will hold, such as Component, API, Resource, System, Domain, User and Group, and how each one maps to something your teams already run. Write down naming rules for entity names, namespaces and tags, and define which fields are mandatory, especially spec.owner and spec.system. Confirm the model against the Backstage catalog model documentation for the version you run. The step is done when the agreed model fits on one page and each owner team has signed off on how its services will be named.
Set catalog locations and ingestion sources in configuration
The platform team adds the catalog section to the app configuration file, listing the static locations and provider settings that Backstage will read at startup. Keep the first configuration small: one source for the users and groups provider, one for the repositories in the pilot, and nothing else. Store credentials for source systems in your secrets mechanism rather than in the configuration file. The check is that the backend starts without catalog errors and that the catalog health view shows each configured source as reachable, with no failed processors for the pilot locations.
Seed users and groups before components
Load users and groups first, either through the organizational data provider that matches your identity system or through a reviewed set of User and Group descriptor files. Components reference owners by name, so ownership cannot resolve until the people and teams exist in the catalog. Check that group membership matches your identity provider for a sample of teams, including nested groups and team leads. The step is complete when each pilot owner team appears as a Group entity with its expected members, and when a test component that names one of those groups shows the owner link resolving rather than pointing at an empty entity.
Add descriptor files to a pilot set of repositories
Choose a small pilot of repositories that cover different languages, deployment patterns and owner teams, then add a catalog-info.yaml descriptor to each one. Each file should declare the entity kind, metadata name, owner, system, lifecycle and the APIs or resources the component provides or consumes. Have the owning teams review their own file in a merge request so the descriptor reflects how they actually run the service. The check is that every pilot repository produces exactly one component entity, that its owner matches the team that maintains it, and that the entity page lists its linked API or resource.
Define required fields and owner references
Turn the rules from the first step into enforced checks. Add validation in a custom processor or in your descriptor linting so that missing owners, unknown systems, or invalid lifecycle values fail before merge rather than appearing later as broken pages. Confirm that every owner, system and dependency reference points to an existing entity in the same namespace. Ask the team that operates the catalog to run a report of references that do not resolve. The step is done when the pilot produces zero orphaned references and the validation rejects a deliberately malformed test descriptor in a non-production environment.
Turn on ingestion for the remaining repositories
Once the pilot is stable, extend discovery to the rest of the organization, usually with a provider that scans a repository host for catalog-info.yaml files on a schedule, and widen it in stages by team or business unit. Keep an owner for each batch who checks the new entities on their teams. Watch the orphan report and the processing error list after each batch, and pause the rollout if error counts rise. The step is complete when a full discovery run finishes without unexplained errors, every discovered repository with a descriptor has an owner that resolves to a group, and the teams accept the catalog as the place where their ownership is recorded.
How to model systems, APIs and resources without duplicate entries
The catalog stays useful only when each real service, API and resource has exactly one home in the model. Start by deciding what counts as a component. A practical test is whether one team deploys, versions and is paged for the thing as a unit. If it is, it is a component of type service, website or library. Group components that together serve one business capability into a system, and keep the system as a grouping object rather than a deployable. Illustrative example: a payments team that runs a checkout API, a refund worker and a shared ledger database might model three components under one system called payments-core, not one large component that hides the worker's separate on-call history. APIs and resources should not be modeled as free-floating copies of the service behind them. Declare the API as its own entity with a type, lifecycle and an owner, then link it from the providing component using the providesApis field, and from consuming components using consumesApis. Resources such as databases, queues and buckets follow the same pattern with dependsOn and providesResources or dependsOn references. Confirm in your own environment which relations your plugins read, because views such as the dependency graph and the API overview depend on these links being present on both sides.
Duplicates usually come from two sources: the same service declared in more than one catalog-info.yaml file, and the same service discovered by a provider while also being registered by hand. Pick one source of truth per entity. If a repository already has a catalog-info.yaml, avoid also creating a location entry for the same component in a central file, and check whether a discovery provider such as a cloud or Kubernetes integration would create a second entity with a different name. Agree on a naming rule before the first import. Use a stable, lowercase identifier per entity, unique within its namespace, and never derive the name from a hostname or a deployment slug that changes with each release. Run a periodic check for entities that share a repository URL or an annotation value, and treat any hit as a defect to resolve. Naming and tags make ownership searchable. Write a short naming standard that covers the entity name, the title, and a small set of tags such as the environment class, data sensitivity and compliance scope. Keep tags lowercase and drawn from a closed list, so that filters return what teams expect. Ownership is expressed through spec.owner, which should reference a group entity, such as group:default/payments-platform, rather than an individual person. Groups map to teams that survive staff changes, and the Software Catalog can resolve group membership from your identity provider when that ingestion is configured. Ask your identity team which groups are authoritative before you write owner values.
Owner references need maintenance. Each group should exist in the catalog, have a named lead and a documented escalation path, and be reviewed when teams are reorganized. An entity that points at a missing group will still load, which means problems appear quietly in ownership reports. Add a validation step to the pull request workflow that rejects unknown owner references and malformed names, and schedule a monthly review of entities with no owner, a lifecycle of experimental or deprecated, or no link to any system. These gaps show where a team has registered something, moved on and left the entry behind. Before a broad rollout, model a small pilot of one domain end to end, including two systems, several APIs and a shared database. Check that the graph shows each relation once, that search returns the entity by its expected name and tag, and that an owner change in the source file moves the entity to the new group after the next ingestion cycle. Document the naming standard, the tag list and the owner rules in the same repository as the catalog files so changes go through review. Teams that set these rules early spend less time later merging entries that describe the same service under different names.
What drives catalog effort and how to keep each driver down
This table lists the factors that move catalog effort and cost, with a practical way to reduce each one. Read each row as a lever: the reduction approach is usually the cheapest way to shorten the first phase. The main takeaway is that scope and field agreement decide most of the effort before any ingestion code is written.
| Driver | Why it changes effort | How to keep it down |
|---|---|---|
| Number of repositories and services | Each repository with a catalog-info.yaml or discovered component needs review, ownership confirmation and ongoing upkeep. | Limit the first phase to one pilot domain with a bounded set of services, then add domains in later waves. |
| Number of source systems to reconcile | Service data often lives in a wiki, a CMDB, a service registry and repositories, and the same component can appear with conflicting names or owners. | Pick one system of record per field, and document which source wins when records disagree before writing processors. |
| Quality of existing service records | Stale owners, missing system links and inconsistent names force manual correction before entities can be trusted. | Generate descriptors from existing records where fields map cleanly, and flag incomplete records for owner review instead of hand-fixing all of them. |
| Number of teams and groups | Every owner reference must match a group or user entity, so each team adds a confirmation step and a sign-in resolver dependency. | Agree the group naming convention early and ingest groups from the identity provider where possible, so owners resolve without manual entries. |
| Required metadata and compliance tagging | Each mandatory annotation or tag adds validation rules, reviewer questions and checks that must be kept current over time. | Agree a short list of required fields at the start, keep optional metadata optional, and add compliance tags only where a named control or report uses them. |
| Number of environments | Each environment needs its own catalog locations, credentials, integration tokens and verification, and drift between them creates support work. | Keep one shared descriptor format across environments, parameterize endpoints and tokens, and verify ingestion in a non-production environment first. |
| Ownership change frequency | Teams that reorganize often generate recurring updates to owner and system references, which becomes ongoing operational work. | Tie ownership to the identity provider's group membership and set a regular review of owners so changes flow through one path. |
| Custom processors and integrations | Each custom processor or non-standard provider needs its own design, testing and upgrade checks across Backstage releases. | Start with built-in providers and descriptor files, and confirm that any custom processor is needed before scoping it into the fixed quote. |
How sign-in identity and group data keep owners accurate
An owner field in the Backstage software catalog is only as good as the identity behind it. If the same engineer appears as one user when she signs in with GitHub and as a different user when she signs in with Okta, ownership views split, notifications go to the wrong place and team pages look incomplete. The Backstage authentication documentation advises configuring sign-in resolvers so that every authentication provider resolves to the same catalog identity. Before you write a single catalog-info.yaml file, decide which provider is the primary source of identity, which attribute (usually an email address or a provider-specific user ID) links the others, and what happens when a user signs in through a provider that has no match. Write those rules down, because they determine which owner references will resolve later.
Guest access is the shortcut that most teams are tempted to leave on during rollout. It lets anyone open the portal without an identity provider account, which means catalog actions, template runs and documentation edits can be attributed to nobody in particular. The Backstage authentication guidance advises against offering guest access in production. Treat its removal as a gating item for the portal launch rather than a cleanup task for later. Confirm with your security team which environments, if any, may keep a guest provider for testing, and make sure that setting does not leak into the production configuration file during deployment.
Sign-in alone does not populate owners. Owner references in catalog entities point to user and group entities, so those entities must exist in the catalog before a component can show a resolved owner. Backstage can ingest users and groups from your identity source through a catalog provider, typically in the same scheduled cycle as other entities. Plan the group model before ingestion starts: which groups represent teams that own software, how nested groups map to departments, and which group names are stable enough to appear in many catalog-info.yaml files. Renaming a team later means updating every owner reference or accepting broken links, so involve the people who maintain your identity directory in this design work.
Verify the chain end to end before you rely on it. Pick a sample of components, confirm that each owner reference resolves to a user or group entity, and check that a signed-in engineer sees the components owned by her team. Review the ingestion logs for users or groups that failed to load, and decide how orphaned owners will be reported. Build a recurring check that flags owner references without a matching entity, because team reorganizations and leavers will create drift every quarter. Ask whoever runs the portal to show you this report as part of the handover.
The detailed mechanics of sign-in setup are covered in the Backstage SSO and identity integration topic, including provider configuration for Okta, Microsoft, Google, GitHub and generic OIDC, resolver code and removal of guest access. This section is about the design consequences for ownership data. Use it to settle the identity rules and group model first, then take them into the SSO work so that configuration implements decisions you have already made rather than discovering them during rollout.
Access control on catalog data and ownership changes
In a Backstage catalog, a change to a descriptor file or an ingestion source can alter who owns a service and who is listed as a team member. The cards below cover the controls that decide who may make those changes, which sources may write entities, how group and user data is protected, and where read access needs narrowing.
Repository review rules for descriptors
Catalog-info.yaml files live in the same repositories as the code they describe, so a pull request can change an owner, a lifecycle or a system link without anyone on the platform team seeing it. Set branch protection and CODEOWNERS rules so changes to descriptor files need approval from the owning team or a platform reviewer. Confirm with your Git host how CODEOWNERS paths are enforced on default branches and whether the same rule applies to forks and bot accounts.
Restricting which sources write entities
Entities can arrive from static locations, from discovery of repositories and from provider plugins that read other systems. Each source that can create or overwrite an entity is a write path into the catalog, so list them and decide which may claim ownership of which kinds and namespaces. Confirm in your version how entity provider identity is recorded and whether one provider can replace entities that another provider created.
Protecting group and user data
Groups and users ingested from an identity provider drive ownership, so a tampered group membership can route ownership or access to the wrong people. Restrict who can edit group definitions in the source directory, and keep the sync credential scoped to read-only directory access. Review the sign-in resolver logic together with ingestion, since both decide which identity a person maps to in the catalog.
Limiting read access to sensitive metadata
Some entity annotations, such as links to incident channels, internal hostnames or customer-facing system names, may be sensitive even when the component itself is not. Catalog read access is not split by field by default, so decide which entities or annotations must be hidden from some groups before you populate the catalog widely. Confirm with your Backstage version which read restrictions are available through the permission framework and which need custom work.
Audit trail for ownership changes
When ownership changes, you need to know which commit, provider or user caused the change and when it took effect. Keep descriptor changes in Git history and retain logs from ingestion runs so an owner change can be traced to a merge. Ask your team to confirm how long ingestion logs are kept in your deployment and where they are exported.
Permission framework as a separate step
The Backstage permission framework can authorize catalog reads and writes at the API level, but it is a separate hardening topic and not a substitute for the repository and source controls above. Before relying on it, confirm for your Backstage version which catalog permissions are supported, how they interact with your auth provider, and whether your plugins enforce them. Plan it as its own workstream with its own test cases.
How to test that catalog entries and owners are correct
The catalog is correct when every entity it shows can be traced to a source that still exists, has an owner the platform can resolve, and fails visibly when something goes wrong. Test those properties directly rather than trusting that the catalog looks complete in the user interface. Start with an owner check: for every Component, System, API and Resource, the spec.owner field should reference a Group or User entity that the catalog actually holds. A reference to a team that was renamed or removed is an unresolved relation, and it is the most common way ownership quietly drifts. Run this as a scheduled query against the catalog database or the catalog API, and treat any entity without a resolvable owner as a failing result, not a warning.
Next, test for duplicates across sources. A repository that is discovered by a GitHub or GitLab provider and also declares its own catalog-info.yaml can produce two entities with the same metadata.name in the same namespace, or two entities that describe the same service under different names. Check for entities with identical repository URLs, identical annotations such as the source location, and identical names within a kind. Decide in advance which source wins when two providers overlap, and write that rule down, because the duplicate check will otherwise flag the same pair every run and teams will stop reading the report.
Removal is where many catalogs fail silently. Test what happens when a repository is deleted, archived or renamed. A provider should remove or orphan the entity on its next refresh, and the expected result should be written as a test case: delete a sample repository in a non-production organization, wait for the next scheduled ingestion cycle, and confirm the entity disappears or is marked as no longer discovered. Repeat the test with a renamed repository, because the catalog may create a new entity while leaving the old one behind. Negative tests should also include a deleted team referenced as owner, a catalog-info.yaml with a malformed owner reference, and a provider token that loses read access. Each should produce a visible error rather than a stale entry that looks healthy.
Ingestion errors only protect you if a platform owner sees them. Confirm that processor and provider errors appear in a place someone actually checks, such as the catalog error view in the portal, a dashboard fed from backend logs, or an alert routed to the platform team. Inject one deliberate error in a test environment and verify the alert reaches a named person within the time your operations process requires. Then sample ownership with the teams themselves: pick a small, documented set of entities across different groups, ask each owning team to confirm the description, lifecycle, owner and dependencies are current, and record any corrections as defects against the ingestion or the source file. Ask your implementation partner to show the exact queries, test repositories and alert rules they used, and confirm these tests are part of the acceptance criteria in the written scope.
What to monitor, document and review after the catalog goes live
A catalog is only useful while its entities parse, its owners are current and its data survives a restore. The cards below list the recurring tasks that keep it that way, with the team that should own each one.
Ingestion error and orphan monitoring
Watch the catalog's ingestion logs and the entity list for two failure modes: locations that stop producing entities, and entities whose source file was deleted or moved but whose record remains. Platform engineering should review ingestion errors on a set schedule and assign each one to the repository owner. Orphaned entities should be reported, confirmed with the owning team, then removed so that search results and ownership views stay accurate.
Scheduled ownership review
Ownership fields in catalog-info.yaml files and in the group and user entities ingested from your identity provider go stale when teams are reorganized, renamed or dissolved. Set a recurring review, owned by the platform team with input from HR or the directory administrators, that compares owner references against current team membership. Trigger an extra review whenever a reorganization is announced, because ownership drift is the most common reason a catalog loses the trust of its users.
Entity model and naming documentation
Keep a written record of the kinds, types, lifecycle values, tags and naming rules the catalog uses, including which fields are mandatory and which teams may create each kind. Platform engineering owns this document and updates it whenever a new entity type or annotation is approved. Without it, new repositories tend to invent their own values, and search, filtering and dependency graphs become inconsistent within a few quarters.
Catalog database backup
The catalog stores its state in the portal's PostgreSQL instance, where it has its own logical database. Include that database in the same backup schedule, retention policy and restore test that cover the rest of the portal, rather than treating catalog data as a cache that can be rebuilt. Confirm with the operations team how long a restore takes and whether a restored catalog is re-ingested from source so that deleted or changed entities are reconciled. Infrastructure or database operations owns this task.
Entity parsing checks after each upgrade
Each Backstage upgrade can change how entity definitions are validated, so run a parse check across all catalog-info.yaml files and ingested sources after moving packages to a new version. The upgrade helper's template changes show which packages and configuration files moved, but they do not replace a check against your own entities. Platform engineering owns the check, and the upgrade is not complete until the failing entities are fixed or listed with an owner and a date.
What do teams ask before building the catalog with a partner?
What does a Backstage software catalog build cost?
The cost depends mainly on the size of the estate and how much of it must be modeled. The Backstage project itself is Apache-2.0 software with no paid edition, so the spend is on people and operations, not on a Backstage license. Quotes usually separate the work into components: discovery of existing repositories and records, design of the entity model, writing or generating descriptor files, configuring ingestion through providers or locations, confirming ownership with named teams, and handover documentation. Recurring costs sit outside the build: hosting, the people who keep descriptors current as services change, and upgrades. Ask any partner to price each component against your inventory and to state which parts are one-time and which recur. A fixed-scope quote should name the systems in scope and the entity types included.
How long does it take to build a software catalog?
Duration depends on how many systems exist, how consistent their ownership records are, and how many teams must confirm what they own. Discovery is often the longest phase when records are scattered across wikis, spreadsheets and cloud tags, because someone must decide what counts as a component before any file is written. Agreeing entity types and naming conventions early keeps modeling short. Ingestion and validation take less time once descriptors exist, but each round of team review adds a wait. Ask for a phased schedule with review gates after discovery and after a pilot group is ingested. Be cautious about any timeline that does not list dependencies on team sign-off and identity access, because those are the usual sources of delay.
Can an internal team build a Backstage catalog without a partner?
Yes, a team with Backstage, CI and identity provider experience can build a catalog alone. The skills that matter most are modeling entities, writing descriptor files, operating ingestion from source control and configuring sign-in so ownership references resolve. The harder constraints are usually capacity and neutrality: platform engineers must also chase owners, resolve duplicate records and agree conventions across teams that may not prioritize the work. A partner tends to add value when the internal team lacks spare capacity, wants an outside review of its entity model, or needs a fixed-scope deliverable with written acceptance criteria. Before deciding, confirm who will maintain the catalog after handover, because stale ownership data reduces trust in the portal quickly.
What access and inputs does a catalog build need from our side?
The work needs three things: identity administration access, repository access and named owners. Identity access lets the team connect the sign-in provider and read users and groups so that ownership references resolve to real accounts. The Backstage authentication guidance recommends sign-in resolvers that map every provider to the same identity, which depends on this access. Repository access, typically read access to the repositories that will hold catalog-info.yaml files, lets engineers inspect services and open pull requests, while write access is usually limited to the teams that commit the files. Named owners means a person or group accountable for each system, confirmed in writing. Also ask for a non-production identity tenant, a change window for ingestion and a single approver for scope decisions.
Can catalog descriptor files be generated from existing records?
Often partly. Descriptor files can be generated from records that already hold a service name, owner, repository and lifecycle, such as a configuration database export, a service registry or a repository inventory. The output still needs review. Generation is usually a scripted mapping from source fields to Backstage kinds such as Component, System, API, Resource and Group, and it fails where records are incomplete or owners are free text. Commit generated files through a normal review so each owner sees what will appear in the portal before it does. Confirm the source export format, how often the source changes, and whether the generator will run once or on a schedule. Treat the first run as a draft that teams correct, and budget review time for it.
What happens to ownership data when a team reorganizes?
Ownership data stays wrong until someone updates it, so the catalog needs a defined path for moves, splits and mergers. When owner references live in descriptor files in source control, a reorganization becomes a set of changes to the owner field on affected entities, and the receiving team should review them. If groups are ingested from the identity provider, membership changes arrive on the next sync, but entities still point at a group name that may have been renamed or removed. Plan for scheduled ownership reviews, a rule for entities with no active owner, and a named owner for the catalog itself. Ask any partner how the design handles renamed groups, transferred services and abandoned components before the first ingestion.
How do we verify that catalog ingestion works correctly?
Verification checks four things: that every intended entity appears, that relationships and references resolve, that owners match identity groups, and that ingestion produces no unresolved errors. Teams usually run schema or lint checks on descriptor files in continuous integration so malformed files fail before they merge. After ingestion, compare the catalog against the agreed inventory, sample several entities per team and confirm that each owner recognizes what is listed. Review processor and ingestion logs for repeated errors, because a single bad file can block others in some configurations. Ask the partner for written acceptance criteria and a test plan that covers both the initial load and later changes to descriptors.
How DeployOpen scopes, builds and hands over catalog work
DeployOpen plans, implements, documents and supports self-hosted open-source platforms inside the client's own infrastructure, and Backstage catalog work follows the same path. We agree the catalog model, ingestion sources and ownership rules in writing first, then build and test them in your environment so your teams can run the catalog after handover.
How we scope
- Agree the entity types in scope, such as components, systems, APIs, resources and groups, and the fields each must carry.
- Decide which data comes from catalog-info.yaml files and which comes from providers, and record that split in the written scope.
- Confirm who owns each team, system and component record, and how ownership gaps will be reported and closed.
- Engagements are fixed-scope, so scope, deliverables and timelines are agreed in writing before any build work starts.
How we build
- Set up the catalog model and entity schema, then validate sample descriptors against it before wider rollout.
- Configure ingestion providers and processors for your source systems, with the credentials scoped to read-only access.
- Test that ingestion runs, entities update when source data changes, and orphaned or duplicate entities are flagged.
- Document the model, ingestion sources, ownership rules and the steps for adding a new service to the catalog.
How we hand over
- Deliver the catalog descriptor templates, provider configuration and a written ownership convention your teams can follow.
- Walk your platform engineers through troubleshooting ingestion failures, stale entities and ownership changes in a working session.
- Provide the test evidence and the list of open items, with each item assigned to an owner on your side.
- Confirm the handover checklist in writing so both teams know which parts of the catalog each party maintains.
How we support
- Ongoing support, upgrades and continuous testing are available as retainers after handover.
- Review catalog quality on a regular cadence, covering missing owners, stale components and broken ingestion sources.
- Check catalog ingestion and schema changes when Backstage releases are upgraded, since catalog behavior can shift between versions.
- Ask us to confirm the support scope, response expectations and review cadence in the written retainer before work begins.

