Migrate to RunxBuild and earn up to $50 in hosting credit on your first deposit.

Calculate your savings
unxBuild

GitLab CI/CD Components: Reusable Pipeline Building Blocks That Actually Work

Sean

Platform Writer

Jul 08, 2026
6 min read

GitLab CI/CD components are reusable pipeline units introduced in GitLab 17.0 that work like publishable includes with inputs and defaults. The team that uses them extracts common job logic (build, test, deploy) into versioned components and shares them across projects. The team that does not uses copy-pasted YAML that drifts between projects - one project’s test job runs Node 18, another runs Node 20, and the team has subtle bugs from the inconsistency.

GitLab CI/CD Components: Reusable Pipeline Building Blocks That Actually Work

Table of contents

What components are and how they differ from includes

Components are reusable CI/CD configuration units published to the GitLab CI/CD Catalog. Unlike include: local or include: template (which are static imports), components have inputs (parameters), defaults, and a version. The team that uses components has parameterized, versioned building blocks.

The CI/CD Catalog is the public directory of components. Teams publish components to the catalog; other teams discover and use them. The team that publishes a component to the catalog has it discoverable across the organization.

Components vs Docker images: components configure jobs; Docker images provide the runtime. A component might say ‘run these steps with this image and these inputs’. The team that uses components for pipeline logic and Docker images for runtime has clean separation of concerns.

Creating a component

A component is a repository with a template.yml file at the root. The template defines the jobs, inputs, and defaults. The team that creates a component has one repository per component, with the template.yml as the entry point.

Example component: ‘run-pytest’ (run Python tests with configurable Python version and test path). The template uses inputs: python_version (default ‘3.11’), test_path (default ‘tests/’). The team that uses this component in their pipeline includes it with component: gitlab.example.com/myorg/[email protected] and overrides inputs as needed.

Versioning: Git tags. Tag a component repository with 1.0.0, 1.1.0, etc. Pipelines include a specific version (@1.0.0) or follow major (@~latest). The team that pins versions has reproducible pipelines; the team that follows latest has automatic updates but less control.

Using components in pipelines

Include a component: include: - component: gitlab.example.com/org/component-name@version. The component is included in the pipeline; its jobs run alongside the pipeline’s native jobs. The team that includes components adds them to the include block, just like local or template includes.

Pass inputs to a component: inputs: { python_version: '3.12', test_path: 'unit/' }. The component’s template uses these inputs to configure its jobs. The team that overrides inputs has different configurations for different pipelines.

Combine components: a typical pipeline might include lint, test, build, deploy components. Each component handles one stage of the pipeline. The team that uses component-per-stage has clear separation; the team that has all logic in one .gitlab-ci.yml has a monolithic file.

Component best practices

Keep components focused on one thing. A ‘run-pytest’ component handles Python tests, not lint or build. The team that has focused components composes them; the team that has multi-purpose components has parameters that overlap awkwardly.

Document inputs clearly. The team that uses components without documentation has to read template.yml to understand what inputs are available; the team that documents inputs has discoverable, usable components.

Test components in isolation. A component repo should have its own pipeline that tests the component logic. The team that tests components has confidence in their behavior; the team that does not has bugs in components that affect every project using them.

Version semver: major bump for breaking changes (input renames, behavior changes), minor for new features, patch for bug fixes. The team that follows semver has predictable upgrades; the team that uses ad-hoc versioning has surprise breaking changes.

When components shine vs when to skip

Use components when: the team has 5+ projects with similar pipeline stages, the team has dedicated platform engineers, the team needs to enforce standards (security scans, license checks). The team that builds components once and reuses across projects saves weeks of duplicated configuration.

Skip components when: the team has 1-2 projects, no dedicated platform team, pipelines that are radically different across projects. The team that has 1 project with a 50-line .gitlab-ci.yml does not need components; the overhead is not justified.

Components are not a replacement for shared runners or CI/CD infrastructure. The team that needs shared CI runners (GPU runners, large-memory runners) sets up GitLab Runner configuration, not components. Components are for pipeline logic, not infrastructure.

FAQ

What is the difference between a component and an include?

Includes are static YAML imports (local file, template, remote file). Components are reusable units with inputs, defaults, and versioning, published to the CI/CD Catalog. The team that uses components has parameterized, versioned building blocks; the team that uses includes has static imports.

Do components work with self-hosted GitLab?

Yes. Components work on GitLab.com and self-hosted GitLab 17.0+. The team that runs an older GitLab version does not have components - upgrade to 17.0+ to use them.

Can a component include another component?

Yes. Components can include other components, building hierarchical pipelines. The team that builds a ‘deploy’ component that includes a ‘docker-build’ component has composable pipelines. Be careful: deep hierarchies become hard to debug.

How do I discover existing components?

The CI/CD Catalog at gitlab.com/explore is the public directory. The team that has a self-hosted GitLab has an internal catalog of organization-specific components. The team that needs a component checks the catalog before building one.

What is the difference between a component and a CI/CD template?

Templates are static YAML files; components are parameterizable with inputs. The team that uses templates has copy-paste YAML that may diverge; the team that uses components has parameterized building blocks with version pinning.

Can components access project variables?

Yes. Components inherit the project’s CI/CD variables. The team that uses a component with project-specific credentials (deploy keys, registry tokens) works as expected. The team that hardcodes secrets in a component has security issues - use variables, not literals.

How this fits the rest of the stack

For a sense of what the full project costs before it commits, the RunxBuild hosting calculator shows the line items together. The API, the database, the storage, the worker, the bandwidth - each one is a separate number, and the team’s mental model for the platform is the sum of those numbers.

Useful related references:

#gitlab#ci-cd#components#pipelines