CtrlK
BlogDocsLog inGet started
Tessl Logo

tessl/npm-backstage--catalog-model

Types and validation framework for Backstage's software catalog model with support for all entity kinds, relationships, and validation policies

93

1.05x

Evaluation93%

1.05x

Agent success when using this tile

Overview
Eval results
Files

entity-references.mddocs/

Entity References

Utilities for parsing, formatting, and working with entity references that uniquely identify catalog entities. Entity references provide a standardized way to reference entities across the Backstage catalog using a kind-namespace-name triplet format.

Capabilities

Compound Entity Reference

The complete entity reference structure containing all components needed to uniquely identify an entity.

/**
 * All parts of a complete entity ref, forming a full kind-namespace-name triplet
 */
interface CompoundEntityRef {
  /** The entity kind (e.g., 'component', 'api', 'system') */
  kind: string;
  /** The namespace containing the entity */
  namespace: string;
  /** The name of the entity within the namespace */
  name: string;
}

Entity Reference Parsing

Parse entity reference strings into structured compound reference objects with support for defaults and context.

/**
 * Parse an entity reference string into a CompoundEntityRef object
 * @param ref - String reference or existing CompoundEntityRef
 * @param context - Optional parsing context with defaults
 * @returns Parsed compound entity reference
 */
function parseEntityRef(
  ref: string | CompoundEntityRef,
  context?: {
    /** Default kind to use if not specified in ref */
    defaultKind?: string;
    /** Default namespace to use if not specified in ref */
    defaultNamespace?: string;
  }
): CompoundEntityRef;

Usage Examples:

import { parseEntityRef } from "@backstage/catalog-model";

// Parse full reference
const ref1 = parseEntityRef("component:default/user-service");
// Result: { kind: "component", namespace: "default", name: "user-service" }

// Parse with default namespace
const ref2 = parseEntityRef("component:user-service", {
  defaultNamespace: "default"
});
// Result: { kind: "component", namespace: "default", name: "user-service" }

// Parse with default kind and namespace
const ref3 = parseEntityRef("user-service", {
  defaultKind: "component",
  defaultNamespace: "default"
});
// Result: { kind: "component", namespace: "default", name: "user-service" }

// Parse already structured reference (passthrough)
const ref4 = parseEntityRef({
  kind: "api",
  namespace: "payments",
  name: "billing-api"
});
// Result: { kind: "api", namespace: "payments", name: "billing-api" }

Entity Reference Stringification

Convert entity references and entities into canonical string representations.

/**
 * Convert an entity or entity reference into a canonical string representation
 * @param ref - Entity or CompoundEntityRef to stringify
 * @returns Canonical string representation of the entity reference
 */
function stringifyEntityRef(ref: Entity | CompoundEntityRef): string;

Usage Examples:

import { stringifyEntityRef, Entity } from "@backstage/catalog-model";

// Stringify compound reference
const ref = { kind: "component", namespace: "default", name: "user-service" };
const refString = stringifyEntityRef(ref);
// Result: "component:default/user-service"

// Stringify from entity
const entity: Entity = {
  apiVersion: "backstage.io/v1alpha1",
  kind: "Component",
  metadata: {
    name: "user-service",
    namespace: "default"
  }
};
const entityString = stringifyEntityRef(entity);
// Result: "component:default/user-service"

Compound Reference Extraction

Extract compound entity references directly from entity objects.

/**
 * Extract a CompoundEntityRef from an entity object
 * @param entity - Entity to extract reference from
 * @returns Compound entity reference with normalized kind and namespace
 */
function getCompoundEntityRef(entity: Entity): CompoundEntityRef;

Usage Examples:

import { getCompoundEntityRef, Entity, DEFAULT_NAMESPACE } from "@backstage/catalog-model";

const entity: Entity = {
  apiVersion: "backstage.io/v1alpha1",
  kind: "Component",
  metadata: {
    name: "user-service"
    // No namespace specified
  }
};

const ref = getCompoundEntityRef(entity);
// Result: { 
//   kind: "component", 
//   namespace: "default", 
//   name: "user-service" 
// }

Reference Format Specification

Entity references follow a standardized format that enables consistent identification across the Backstage ecosystem:

String Format

The canonical string format for entity references is:

[kind:][namespace/]name
  • kind: Optional entity kind (defaults to context-specific default)
  • namespace: Optional namespace (defaults to "default")
  • name: Required entity name

Examples of Valid References

// Complete references
"component:default/user-service"
"api:payments/billing-api" 
"system:platform/authentication-system"

// References with default namespace
"component:user-service"        // → component:default/user-service
"api:billing-api"              // → api:default/billing-api

// Name-only references (requires context defaults)
"user-service"                 // → component:default/user-service (with defaults)

Case Sensitivity

Entity references are case-insensitive for the kind component but preserve case for namespace and name:

import { parseEntityRef } from "@backstage/catalog-model";

// Kind is normalized to lowercase
const ref = parseEntityRef("COMPONENT:default/user-service");
// Result: { kind: "component", namespace: "default", name: "user-service" }

Common Usage Patterns

Working with Entity Collections

import { 
  Entity, 
  parseEntityRef, 
  stringifyEntityRef, 
  getCompoundEntityRef 
} from "@backstage/catalog-model";

function findEntityByReference(
  entities: Entity[], 
  targetRef: string
): Entity | undefined {
  const target = parseEntityRef(targetRef, { 
    defaultNamespace: "default" 
  });
  
  return entities.find(entity => {
    const entityRef = getCompoundEntityRef(entity);
    return entityRef.kind === target.kind &&
           entityRef.namespace === target.namespace &&
           entityRef.name === target.name;
  });
}

// Usage
const entities: Entity[] = [/* ... */];
const foundEntity = findEntityByReference(entities, "component:user-service");

Building Entity Relationship Maps

import { 
  Entity, 
  ComponentEntity, 
  isComponentEntity, 
  parseEntityRef 
} from "@backstage/catalog-model";

function buildDependencyGraph(entities: Entity[]): Map<string, string[]> {
  const dependencies = new Map<string, string[]>();
  
  entities.forEach(entity => {
    if (isComponentEntity(entity)) {
      const entityRef = stringifyEntityRef(entity);
      const deps = entity.spec.dependsOn || [];
      
      // Normalize dependency references
      const normalizedDeps = deps.map(dep => 
        stringifyEntityRef(parseEntityRef(dep, { 
          defaultNamespace: entity.metadata.namespace || "default" 
        }))
      );
      
      dependencies.set(entityRef, normalizedDeps);
    }
  });
  
  return dependencies;
}

Reference Validation

import { parseEntityRef } from "@backstage/catalog-model";

function isValidEntityReference(ref: string): boolean {
  try {
    parseEntityRef(ref);
    return true;
  } catch (error) {
    return false;
  }
}

// Usage
const validRefs = [
  "component:default/user-service",
  "api:billing-api",
  "system:platform/auth"
].filter(isValidEntityReference);

Install with Tessl CLI

npx tessl i tessl/npm-backstage--catalog-model

docs

core-entities.md

entity-kinds.md

entity-policies.md

entity-references.md

entity-relations.md

index.md

location-management.md

validation.md

tile.json