Backstage Primer & Modelling Guide — Developer Portal Catalogue with Linked.Archi¶
Engineering organizations that run Backstage end up with a rich software catalogue locked inside a single tool — hard to query alongside architecture models, hard to govern, and hard to reconcile with ArchiMate or C4. Representing the catalogue as semantic assets makes ownership, API dependencies, and system boundaries queryable across the whole architecture knowledge graph.
This guide introduces the Backstage software catalogue model as formalized in Linked.Archi, explains how its concepts map to semantic assets, and demonstrates practical modelling through a worked example.
Backstage Concepts¶
What is Backstage?¶
Backstage is an open-source developer portal platform originally created by Spotify. Its Software Catalog provides a centralized registry of all software components, systems, APIs, resources, and their ownership within an organization.
Backstage is: - Developer-centric — built for engineering teams to discover and understand services - Ownership-first — every entity has a clear owner (team/group) - API-aware — APIs are first-class citizens with provider/consumer relationships - Domain-driven — entities are grouped into business domains
"Backstage unifies all your infrastructure tooling, services, and documentation to create a streamlined development environment from end to end." — backstage.io
Catalogue Entity Types¶
graph TD
subgraph Software["Software Entities"]
Component["Component"]
System["System"]
API["API"]
Resource["Resource"]
end
subgraph Organisational["Organisational Entities"]
Domain["Domain"]
User["User"]
Group["Group"]
end
Component -->|"partOfSystem"| System
API -->|"partOfSystem"| System
Resource -->|"partOfSystem"| System
Component -->|"providesAPI"| API
Component -->|"consumesAPI"| API
Component -->|"dependsOn"| Component
Component -->|"usesResource"| Resource
Resource -->|"usesResource"| Resource
Component -->|"subcomponentOf"| Component
Component -->|"ownedBy"| Group
System -->|"belongsToDomain"| Domain
Domain -->|"subdomainOf"| Domain
User -->|"memberOf"| Group
Group -->|"childOf"| Group
style Software fill:#B3D9FF,stroke:#333,color:#000
style Organisational fill:#D4E6B5,stroke:#333,color:#000
| Entity | What it represents |
|---|---|
| Component | A deployable unit — service, library, website, or application |
| System | A set of components that provide business or technical value together |
| API | An interface owned and maintained in the ecosystem (OpenAPI, AsyncAPI, gRPC, GraphQL) |
| Resource | Infrastructure used by components — databases, buckets, queues, external services |
| Domain | A high-level business domain grouping systems and components |
| User | A human user in the ecosystem |
| Group | A team, department, or tribe that owns entities |
Relationships¶
The ontology declares 12 relation types, each in the three-declaration form (unqualified property, qualified class, qualified property — see the Relationship Modelling Guide):
| Relationship | From → To | Meaning |
|---|---|---|
| ownedBy | Any Element → Group or User | Entity is owned by a team or, in smaller organisations, a person |
| partOfSystem | Component, API, Resource → System | Entity belongs to a system |
| providesAPI | Component, System → API | Component or system exposes an API |
| consumesAPI | Component, System → API | Component or system depends on an API |
| dependsOn | Component, Resource → Component, Resource | General dependency — spec.dependsOn, deliberately broad |
| usesResource | Component, Resource → Resource | Resource-facing subproperty of dependsOn, kept for continuity |
| belongsToDomain | System → Domain | System belongs to a business domain |
| memberOf | User → Group | User belongs to a team |
| childOf | Group → Group | Group organisational hierarchy, stored child-to-parent |
| subcomponentOf | Component → Component | Component nesting, e.g. a scoring sub-service packaged separately |
| subdomainOf | Domain → Domain | Domain nesting, for organisations with a large domain landscape |
| techdocsDelegatedTo | Any Element → Any Element | Documentation ownership, from the backstage.io/techdocs-entity annotation |
Two long-standing relations are wider than they first look, because of how the descriptor format
declares the underlying spec field: spec.system is declared on Component, API and Resource,
so all three can sit in a system, and providesAPI/consumesAPI are declared on System as well as
Component — a System is defined as exposing one or several public APIs, so a System source is
ordinary Backstage rather than an edge case.
dependsOn is the general reading of spec.dependsOn and covers component-to-component dependencies
as well as resource dependencies; usesResource is retained as its resource-facing subproperty for
continuity with older data. A lift emitting fresh data should prefer dependsOn and let subproperty
entailment cover usesResource queries.
Value Vocabularies¶
Backstage's spec.type fields and lifecycle/visibility states are modelled as named individuals
(DD-23) — classes of individuals with no owl:oneOf, so an adopter can mint their own member in their
own namespace without forking a published axiom:
| Vocabulary | Property | Individuals (documented examples) | Closure |
|---|---|---|---|
bs:LifecycleState |
bs:lifecycleState |
bs:Experimental, bs:Production, bs:DeprecatedState |
Open (Warning if outside the set) |
bs:ApiVisibility |
bs:apiVisibility |
bs:Public, bs:Restricted, bs:Private |
Closed (Violation if outside the set — fixed by the system model) |
bs:ComponentType |
bs:componentType |
bs:ServiceType, bs:WebsiteType, bs:LibraryType |
Open |
bs:APIType |
bs:apiType |
bs:OpenAPI, bs:AsyncAPI, bs:GraphQL, bs:GRPC |
Open |
bs:ResourceType |
bs:resourceType |
bs:DatabaseResourceType, bs:S3BucketResourceType, bs:KubernetesClusterResourceType |
Open, illustrative only |
bs:GroupType |
bs:groupType |
bs:TeamGroupType, bs:BusinessUnitGroupType, bs:ProductAreaGroupType, bs:RootGroupType |
Open, illustrative only |
bs:SystemType |
bs:systemType |
bs:ProductSystemType, bs:ServiceSystemType, bs:FeatureSetSystemType |
Open, illustrative only |
bs:DomainType |
bs:domainType |
bs:ProductAreaDomainType, bs:ProductGroupDomainType, bs:BundleDomainType |
Open, illustrative only |
Each individual carries skos:notation with the exact YAML token (e.g. "openapi", "database") —
that is the value a lift matches against when converting catalog-info.yaml to RDF.
Lifecycle¶
bs:lifecycle(a plain string) is deprecated as of 0.3.0. Usebs:lifecycleState, which points at abs:LifecycleStateindividual —bs:Experimental,bs:Production, orbs:DeprecatedState— instead of a bare string. The old property still validates (with a migration Warning), but new models should usebs:lifecycleStatefrom the start:
Entity Identity¶
A Backstage entity is identified by its entity reference, kind:namespace/name. All four identity
fields are retained source data (DD-24) — read from catalog-info.yaml, not computed:
| Field | Property | Required by the shapes |
|---|---|---|
kind |
bs:kind (a plain string, title-case: "Component", "API") |
No — maxCount 1 only |
namespace |
bs:namespace (absent means "default") |
Recommended — Warning if absent |
name |
bs:name |
Yes — Violation if absent |
| the whole reference | bs:entityRef |
No — maxCount 1 only |
:payment-processor
a bs:Component ; # how THIS GRAPH classifies it
bs:kind "Component" ; # what the CATALOGUE said
bs:namespace "default" ;
bs:name "payment-processor" ;
bs:entityRef "component:default/payment-processor" ; # the reference, as the catalogue circulates it
skos:prefLabel "payment-processor"@en . # the human-readable label
bs:kind and rdf:type are both recorded, and may diverge¶
They answer different questions. bs:kind is what the descriptor said; rdf:type is how this graph
classifies the entity, which is a modelling decision open to revision later. A lift maps one to the
other, but an adopter may retype a lifted entity under a convention adopted afterwards, or carry
additional types from another notation in a merged graph — and neither makes the retained kind wrong.
Keeping only rdf:type would lose the descriptor's own statement the moment either happened. Keeping
only bs:kind would leave the entity invisible to every sh:targetClass and rdfs:subClassOf query in
the repository. So both are kept, and neither is derived from the other.
The mapping between them is published on the classes, not hardcoded in each lift — each of the seven
element classes carries skos:notation with its exact kind token:
So a lift resolves kind: Component → bs:Component by matching skos:notation, exactly as it
resolves type: openapi → bs:OpenAPI. These tokens are title-case, unlike every other
skos:notation in the ontology, which carries a lowercase spec.type or state token.
Divergence is reported by bssh:KindTypeAlignmentShape at sh:Info — deliberately not an error. A
mis-mapped lift and a deliberate retyping look identical in the data, so the shape makes both visible
for a reconciliation pass rather than pronouncing on which one you meant. Switch it off where retyping
is standing policy.
bs:entityRef is what the catalogue circulates¶
The entity reference is not a convenience we assemble — it is the form Backstage itself uses in the
relations array and in spec.owner, spec.system, spec.dependsOn and the techdocs-entity
annotation. Retaining it verbatim keeps resolution honest: the specification defines the
default-namespace rule and case-insensitive comparison, and a consumer that rebuilds the reference
reimplements those rules and may diverge from the catalogue. A reference the catalogue actually emitted
is evidence; a reconstruction is an assumption. It also makes resolving an incoming reference one triple
pattern instead of a three-way join with string concatenation.
bssh:EntityRefConsistencyShape checks it against bs:kind, bs:namespace and bs:name — the three
other retained fields from the same descriptor, so a mismatch means the lift mangled one of them, which
is a genuine Violation. It is not checked against rdf:type, because validating the reference
against a type the modeller is free to change would report every intentionally retyped entity as broken.
Both bs:kind and bs:entityRef are targeted with sh:targetSubjectsOf, so a natively authored model
that has no descriptor to retain simply omits them and is not reported as incomplete — as the
hand-written PayFlow example does.
Two things not to do¶
bs:name does not substitute for skos:prefLabel — emit both. And bs:title is presentation-only;
putting it in skos:prefLabel in place of the name makes two entities sharing a title indistinguishable
in every label-driven view.
Do not use bs:uid as a join key. The catalog assigns it on first ingestion and the specification warns
it changes when the identical file is unregistered and re-registered, so it identifies a registration
rather than the thing. The entity reference is what joins across sources.
Semantic Assets¶
Asset Set¶
modelingLanguages/backstage/
├── backstage-metamodel.ttl ← Entry point: arch:Metamodel
├── backstage-onto.ttl ← OWL ontology (7 elements, 12 relationships, 8 value vocabularies)
├── backstage-tax.ttl ← SKOS taxonomy
├── backstage-shapes.ttl ← SHACL validation
├── backstage-viewpoints.ttl ← 7 viewpoints
├── backstage-reference-data.ttl ← Cross-module correspondences (lifecycle ↔ arch-processes stages)
├── backstage-presentation-contexts.ttl ← Developer, Architect, Stakeholder themes
└── backstage-deliverable-templates.ttl ← Document templates
The value vocabularies themselves — lifecycle, API visibility, component/API/resource/group/system/domain
types — moved from backstage-reference-data.ttl into backstage-onto.ttl as of 0.3.0, as named
individuals (DD-23), the same pattern UML uses for uml:MessageSort. backstage-reference-data.ttl now
holds only what sits around those values — correspondences to other vocabularies (e.g.
bs:Production skos:closeMatch ap:Active, aligning Backstage lifecycle to the notation-agnostic
Architecture Processes extension) and any organisation-specific reference data an adopter adds. Two
IRIs for one value was the failure mode this reconciliation removed.
Concept-to-Asset Mapping¶
| Backstage Concept | Semantic Representation | File |
|---|---|---|
| Entity types (Component, System, etc.) | owl:Class rdfs:subClassOf arch:Element |
backstage-onto.ttl |
| Relationships (ownedBy, providesAPI, dependsOn, childOf, etc.) | Three-declaration pattern | backstage-onto.ttl |
| Lifecycle, visibility, component/API/resource/group/system/domain types | owl:NamedIndividual (DD-23, no owl:oneOf) |
backstage-onto.ttl |
| Cross-vocabulary correspondences (e.g. lifecycle ↔ arch-processes stages) | skos:closeMatch |
backstage-reference-data.ttl |
| Validation (identity, naming, relationship domain/range, vocabulary closure) | sh:NodeShape |
backstage-shapes.ttl |
| Viewpoints | arch:Viewpoint |
backstage-viewpoints.ttl |
Cross-Language Integration¶
Backstage entities map naturally to ArchiMate and C4:
| Backstage | ArchiMate 4.0 | C4 |
|---|---|---|
bs:Component |
am4:ApplicationComponent |
c4:Container or c4:Component |
bs:System |
(group of components) | c4:SoftwareSystem |
bs:API |
am4:ApplicationInterface |
— |
bs:Resource |
am4:Node / am4:Artifact |
c4:DeploymentNode |
bs:Group |
am4:Role |
— |
Worked Example: PayFlow (Fintech Platform)¶
Prerequisites¶
core/core-onto.ttl
modelingLanguages/backstage/backstage-onto.ttl
modelingLanguages/backstage/backstage-tax.ttl
modelingLanguages/backstage/backstage-shapes.ttl
modelingLanguages/backstage/backstage-viewpoints.ttl
modelingLanguages/backstage/backstage-reference-data.ttl
modelingLanguages/backstage/backstage-metamodel.ttl
About PayFlow¶
PayFlow is a fintech platform providing payment processing, merchant onboarding, and financial reporting as a service. The engineering organization is structured into domain-aligned squads using Backstage as their developer portal.
The complete, validatable example model is available at examples/payflow/payflow-model.ttl.
Model File Header¶
Start every Backstage model with this header, which binds it to the Backstage metamodel:
@prefix skos: <http://www.w3.org/2004/02/skos/core#> .
@prefix dcterms: <http://purl.org/dc/terms/> .
@prefix arch: <https://meta.linked.archi/core#> .
@prefix bs: <https://meta.linked.archi/backstage/onto#> .
@prefix : <https://meta.linked.archi/examples/payflow/> .
:PayFlowModel
a arch:Model ;
skos:prefLabel "PayFlow — Backstage Catalog Model"@en ;
arch:modelConformsToMetamodel <https://meta.linked.archi/backstage/metamodel#Backstage> ;
dcterms:created "2025-06-27"^^xsd:date ;
.
The model file also needs
@prefix xsd:for the date literal above; the full header is in the example file.
Element Patterns¶
Paste these patterns to declare each catalogue entity with its identity, type, and label, then rename
them to match your estate. Every entity carries bs:name (the catalog identity, required by
BackstageEntityIdentityShape) alongside skos:prefLabel (the human-readable label):
## Domains
:PaymentsDomain a bs:Domain ; bs:name "payments" ; skos:prefLabel "Payments"@en .
:MerchantDomain a bs:Domain ; bs:name "merchant-services" ; skos:prefLabel "Merchant Services"@en .
:PlatformDomain a bs:Domain ; bs:name "platform" ; skos:prefLabel "Platform"@en .
## Groups (teams) — spec.type is optional but recommended
:PaymentsSquad a bs:Group ; bs:name "payments-squad" ; bs:groupType bs:TeamGroupType ; skos:prefLabel "Payments Squad"@en .
:MerchantSquad a bs:Group ; bs:name "merchant-squad" ; bs:groupType bs:TeamGroupType ; skos:prefLabel "Merchant Squad"@en .
:PlatformTeam a bs:Group ; bs:name "platform-team" ; bs:groupType bs:TeamGroupType ; skos:prefLabel "Platform Team"@en .
:SRETeam a bs:Group ; bs:name "sre-team" ; bs:groupType bs:TeamGroupType ; skos:prefLabel "SRE Team"@en .
## Group hierarchy — spec.parent, stored child-to-parent
:SRETeam bs:childOf :PlatformTeam .
## Systems
:PaymentGateway a bs:System ; bs:name "payment-gateway" ; skos:prefLabel "Payment Gateway"@en .
:MerchantPortal a bs:System ; bs:name "merchant-portal" ; skos:prefLabel "Merchant Portal"@en .
:ObservabilityPlatform a bs:System ; bs:name "observability-platform" ; skos:prefLabel "Observability Platform"@en .
## Components — bs:lifecycleState points at a bs:LifecycleState individual, not a string
:PaymentProcessor a bs:Component ; bs:name "payment-processor" ; skos:prefLabel "payment-processor"@en ; bs:lifecycleState bs:Production .
:FraudService a bs:Component ; bs:name "fraud-service" ; skos:prefLabel "fraud-service"@en ; bs:lifecycleState bs:Production .
:PayoutService a bs:Component ; bs:name "payout-service" ; skos:prefLabel "payout-service"@en ; bs:lifecycleState bs:Production .
:MerchantOnboarding a bs:Component ; bs:name "merchant-onboarding" ; skos:prefLabel "merchant-onboarding"@en ; bs:lifecycleState bs:Production .
:ReportingService a bs:Component ; bs:name "reporting-service" ; skos:prefLabel "reporting-service"@en ; bs:lifecycleState bs:Experimental .
:WebhookDispatcher a bs:Component ; bs:name "webhook-dispatcher" ; skos:prefLabel "webhook-dispatcher"@en ; bs:lifecycleState bs:Production .
## Component nesting — spec.subcomponentOf, a component packaged and shipped separately from its parent
:FraudModelScorer a bs:Component ; bs:name "fraud-model-scorer" ; skos:prefLabel "fraud-model-scorer"@en ;
bs:lifecycleState bs:Experimental ; bs:subcomponentOf :FraudService .
## APIs — bs:apiType points at a bs:APIType individual
:PaymentsAPI a bs:API ; bs:name "payments-api" ; bs:apiType bs:OpenAPI ; skos:prefLabel "Payments API (OpenAPI)"@en .
:MerchantAPI a bs:API ; bs:name "merchant-api" ; bs:apiType bs:OpenAPI ; skos:prefLabel "Merchant API (OpenAPI)"@en .
:PaymentEventsAPI a bs:API ; bs:name "payment-events" ; bs:apiType bs:AsyncAPI ; skos:prefLabel "Payment Events (AsyncAPI)"@en .
:FraudScoringAPI a bs:API ; bs:name "fraud-scoring" ; bs:apiType bs:GRPC ; skos:prefLabel "Fraud Scoring API (gRPC)"@en .
## Resources — bs:resourceType is illustrative-only; mint your own individual where the
## documented examples (database, s3-bucket, kubernetes-cluster) don't fit
:PaymentsDB a bs:Resource ; bs:name "payments-db" ; bs:resourceType bs:DatabaseResourceType ; skos:prefLabel "payments-db (PostgreSQL)"@en .
:EventBus a bs:Resource ; bs:name "event-bus" ; bs:resourceType :MessageBrokerResourceType ; skos:prefLabel "event-bus (Kafka)"@en .
:MerchantDB a bs:Resource ; bs:name "merchant-db" ; bs:resourceType bs:DatabaseResourceType ; skos:prefLabel "merchant-db (PostgreSQL)"@en .
:RedisCache a bs:Resource ; bs:name "redis-cache" ; bs:resourceType :CacheResourceType ; skos:prefLabel "redis-cache"@en .
## Organisation-specific bs:ResourceType individuals — message-broker and cache have no
## documented example, so PayFlow mints them in its own namespace
:MessageBrokerResourceType a bs:ResourceType ; skos:prefLabel "Message Broker"@en ; skos:notation "message-broker" .
:CacheResourceType a bs:ResourceType ; skos:prefLabel "Cache"@en ; skos:notation "cache" .
Relationship Patterns¶
Wire the entities together with ownership, system membership, API dependencies, and general dependency:
## Ownership
:PaymentProcessor bs:ownedBy :PaymentsSquad .
:FraudService bs:ownedBy :PaymentsSquad .
:PayoutService bs:ownedBy :PaymentsSquad .
:MerchantOnboarding bs:ownedBy :MerchantSquad .
:ReportingService bs:ownedBy :MerchantSquad .
:WebhookDispatcher bs:ownedBy :PlatformTeam .
:PaymentGateway bs:ownedBy :PaymentsSquad .
:MerchantPortal bs:ownedBy :MerchantSquad .
## System membership
:PaymentProcessor bs:partOfSystem :PaymentGateway .
:FraudService bs:partOfSystem :PaymentGateway .
:PayoutService bs:partOfSystem :PaymentGateway .
:WebhookDispatcher bs:partOfSystem :PaymentGateway .
:MerchantOnboarding bs:partOfSystem :MerchantPortal .
:ReportingService bs:partOfSystem :MerchantPortal .
## API provision
:PaymentProcessor bs:providesAPI :PaymentsAPI .
:PaymentProcessor bs:providesAPI :PaymentEventsAPI .
:FraudService bs:providesAPI :FraudScoringAPI .
:MerchantOnboarding bs:providesAPI :MerchantAPI .
## API consumption
:PayoutService bs:consumesAPI :PaymentsAPI .
:MerchantOnboarding bs:consumesAPI :PaymentsAPI .
:WebhookDispatcher bs:consumesAPI :PaymentEventsAPI .
:PaymentProcessor bs:consumesAPI :FraudScoringAPI .
## General dependency — spec.dependsOn between two Components (the reading usesResource
## does not cover, since usesResource's target is always a Resource)
:ReportingService bs:dependsOn :PaymentProcessor .
## Resource usage — the resource-facing subproperty of dependsOn
:PaymentProcessor bs:usesResource :PaymentsDB .
:PaymentProcessor bs:usesResource :EventBus .
:PaymentProcessor bs:usesResource :RedisCache .
:FraudService bs:usesResource :RedisCache .
:MerchantOnboarding bs:usesResource :MerchantDB .
:WebhookDispatcher bs:usesResource :EventBus .
## Domain membership — spec.domain is declared on System only
:PaymentGateway bs:belongsToDomain :PaymentsDomain .
:MerchantPortal bs:belongsToDomain :MerchantDomain .
:ObservabilityPlatform bs:belongsToDomain :PlatformDomain .
Service Catalogue View¶
graph TD
subgraph PaymentsDomain["Payments Domain"]
subgraph PG["Payment Gateway (System)"]
PP["payment-processor<br/>Production"]
FS["fraud-service<br/>Production"]
PS["payout-service<br/>Production"]
WD["webhook-dispatcher<br/>Production"]
end
end
subgraph MerchantDomain["Merchant Services Domain"]
subgraph MP["Merchant Portal (System)"]
MO["merchant-onboarding<br/>Production"]
RS["reporting-service<br/>Experimental"]
end
end
PP -->|"provides"| PAPI["Payments API"]
PP -->|"provides"| PEAPI["Payment Events"]
FS -->|"provides"| FSAPI["Fraud Scoring API"]
MO -->|"provides"| MAPI["Merchant API"]
PS -->|"consumes"| PAPI
MO -->|"consumes"| PAPI
WD -->|"consumes"| PEAPI
PP -->|"consumes"| FSAPI
PP -->|"uses"| PDB["payments-db"]
PP -->|"uses"| EB["event-bus"]
MO -->|"uses"| MDB["merchant-db"]
style PaymentsDomain fill:#B3D9FF,stroke:#333,color:#000
style MerchantDomain fill:#D4E6B5,stroke:#333,color:#000
style PG fill:#E3F2FD,stroke:#333,color:#000
style MP fill:#E8F5E9,stroke:#333,color:#000
Validate the Catalogue with SHACL¶
Run this to check the model against the core and Backstage shapes. The ontology is passed alongside
the model as data, not only as a shapes document: the model's bs:resourceType/bs:groupType/etc.
values are individuals declared in backstage-onto.ttl (bs:DatabaseResourceType,
bs:TeamGroupType, ...), and the sh:class constraints on those properties need that typing
present in the validated graph, not only in the shapes graph:
.scripts/validate.sh --shacl \
"modelingLanguages/backstage/backstage-onto.ttl,examples/payflow/payflow-model.ttl" \
core/core-shapes.ttl \
modelingLanguages/backstage/backstage-shapes.ttl
PayFlow is the regression test for the 0.3.0 migration: every entity carries bs:name, every
lifecycle uses bs:lifecycleState, and every spec.type value is a proper vocabulary individual (two
of them, message-broker and cache, minted locally since Backstage's bs:ResourceType examples
don't cover them) — it validates with zero Violations. The only findings are four sh:Warnings on
bs:definition, one per API, since this EA-level model deliberately keeps the type (bs:apiType) and
skips the raw OpenAPI/AsyncAPI/gRPC document body — exactly the case ApiDefinitionShape's comment
anticipates.
Further Reading¶
- Modelling Languages Guide — how Backstage relates to ArchiMate, C4, and other languages
- Backstage as C4 Complement or Replacement — positioning guide
- Deployment Modelling: ArchiMate Technology vs C4/Backstage — deployment modelling comparison
- Build Your Own Modelling Tool — how tools consume these assets
- Validation Guide — SHACL validation pipeline
- Backstage Documentation — official Backstage catalog docs
- Backstage System Model — entity types and relationships
Comparison Articles¶
For detailed comparisons of Backstage with other modelling languages in Linked.Archi:
- Backstage as C4 Complement or Replacement — When to use Backstage alongside or instead of C4
- Deployment Modelling: ArchiMate Technology vs C4/Backstage — Deployment modelling across notations
- EA Frameworks Compared — Broader comparison across TOGAF, Zachman, EA on a Page, and others
Disclaimer: This is a community semantic representation of the Backstage software catalogue model for interoperability purposes. It is not produced by, endorsed by, or affiliated with Spotify or the Backstage project. "Backstage" is a trademark of Spotify AB.