Building a Platform Engineering Service Catalog

Why Most Internal Developer Portals Fail

When engineering teams decide to move beyond traditional DevOps and build an Internal Developer Portal (IDP), they almost always start with the service catalog. The goal sounds straightforward: give developers a single pane of glass to spin up microservices, provision databases, and check deployment statuses without filing a Jira ticket for every little task.

Yet, six months in, the catalog is usually a ghost town. Developers go back to copying old Terraform modules, pasting outdated CI/CD YAML files, or pinging senior engineers on Slack. Why? Because the catalog was built as a documentation graveyard rather than an action-oriented workflow engine. It listed things that exist instead of letting developers create things cleanly and securely.

At techsolss, when we help engineering teams implement internal platforms—whether using Backstage, Port, or custom lightweight portals—we emphasize treating the service catalog as a product. It needs defined SLAs, clean schemas, and automated scaffolding underneath.

Core Components of a Production Service Catalog

A functional service catalog bridges the gap between raw infrastructure code (Terraform, Ansible, Kubernetes manifests) and developer intent. It typically breaks down into three core layers:

  1. The Metadata Registry: A central database (often backed by Git repositories via GitOps) tracking every software component, API, pipeline, and infrastructure resource owned by each team.
  2. The Software Templates (Scaffolder): The executable engine that takes user input from a form, renders templates, commits the code to a new Git repository, and triggers the initial pipeline.
  3. The Ownership & Governance Model: Clear mappings showing who owns what service, enforcing compliance guardrails (like required security scanning or tagging conventions) by default.

When designing your catalog, avoid forcing developers to manually update YAML files in a central repo every time they spin up a service. That friction kills adoption. Instead, automate registration through GitHub/GitLab webhooks or CI/CD registration steps.

Defining Your First Software Template (Backstage Example)

Let’s look at a concrete example. Below is a snippet of a Backstage software template (template.yaml) designed to scaffold a new Go microservice with pre-configured CI/CD pipelines, standard logging, and correct security guardrails already baked in.

apiVersion: scaffolder.backstage.io/v1beta3
        kind: Template
        metadata:
          name: go-microservice-template
          title: Go Microservice Scaffolder
          description: Create a production-ready Go microservice with CI/CD and monitoring
        spec:
          owner: platform-team
          type: service

          parameters:
            - title: Service Details
              required:
                - name
                - owner
              properties:
                name:
                  title: Service Name
                  type: string
                  description: Unique name of the microservice
                owner:
                  title: Owner Team
                  type: string
                  ui:field: OwnerPicker
                environment:
                  title: Target Environment
                  type: string
                  default: staging
                  enum:
                    - staging
                    - production

          steps:
            - id: fetch-template
              name: Fetching Skeleton Files
              action: fetch:template
              input:
                url: ./skeleton
                values:
                  name: ${{ parameters.name }}
                  owner: ${{ parameters.owner }}
                  environment: ${{ parameters.environment }}

            - id: publish
              name: Publishing to GitHub
              action: publish:github
              input:
                repoUrl: github.com?repo=${{ parameters.name }}&owner=my-org
                access: private

            - id: register
              name: Registering in Catalog
              action: catalog:register
              input:
                catalogInfoUrl: https://github.com/my-org/${{ parameters.name }}/blob/main/catalog-info.yaml
        

This template ensures that developers don't have to guess how to set up their initial repository structure. They fill out a simple UI form, and the platform handles repository creation, boilerplate code generation, and catalog registration in under 60 seconds.

Enforcing Day-2 Operations and Governance

A service catalog shouldn't just help you launch services; it must help you manage them throughout their lifecycle. Day-2 operations often get neglected, leading to orphaned infrastructure, unpatched runtimes, and ballooning cloud bills.

Your catalog should track operational maturity using scorecards. For instance, a service cannot graduate from staging to production unless its catalog entry meets specific criteria:

  • Observability: Datadog or Prometheus scraping endpoints are active.
  • Security: Recent container vulnerability scans show zero critical Common Vulnerabilities and Exposures (CVEs).
  • Cost Allocation: Proper cloud cost tags (cost-center, owner) are attached to all underlying infrastructure resources, tying directly into your cloud cost optimization workflows.

By exposing these scorecards directly in the developer portal, engineering managers get instant visibility into technical debt without having to run tedious manual audits.

Avoiding Common Pitfalls During Implementation

When teams start building their platform engineering service catalog, they frequently fall into a few operational traps:

  • Boiling the Ocean: Trying to model every single database, queue, and legacy monolith on day one. Start with one common pattern—like a standard REST API service—prove value, and expand.
  • Lack of Dedicated Ownership: Treating the catalog as a side project for whoever has free cycles. A platform is a product; it requires continuous maintenance, feedback loops with internal users, and dedicated iteration.
  • Ignoring Existing Workflows: If your developers are deeply embedded in GitHub Actions or GitLab CI, your catalog shouldn't force them into an entirely foreign interface for routine tasks. Integrate deeply with the tools they already use daily.

If you are comparing structural shifts in your delivery model, reviewing how platform engineering vs DevOps differ will help clarify team boundaries before you write code.

Summary

A well-designed service catalog transforms your engineering organization from a chaotic, ticket-driven operation into a streamlined, self-service machine. By focusing on actionable scaffolding, automated registration, and clear Day-2 governance, you reduce cognitive load and let developers focus on writing business logic rather than wrestling with infrastructure configurations. If you are planning your internal developer platform rollout, let's talk through your architecture.

Want help with this in your own stack?

We build and run this in production for clients — and we’ll tell you honestly what it will take in yours. Book a free 20-minute call.

Book a free 20-min call