Components

Components allow you to isolate and categorize coverage data from your project with virtual filters.

Components allow you to isolate and categorize coverage data from your project with virtual filters. It is similar to Flags, but there is no direct relationship between Components and the reports you upload.

The most important differentiator between Components and Flags is that Components do not have to be supplied at upload time, they are fully defined in the codecov.yml. Components are particularly useful to create custom statuses and get coverage information from parts of your code that are not easily broken up into different uploads, or span multiple flag groups.

Currently you can get component information in the PR comment and also have component-based statuses. See examples below. The yaml configuration that generated the example statuses are discussed later in this guide.

714

Example of component information in the PR comment

906

Example of component statuses in a PR

๐Ÿ“˜

Wondering how it looks in a live repo? Check it out here: https://github.com/codecov/example-components

Getting Started with Components

To use components you just need to define your filters and optional statuses in your codecov.yaml.
To have a more concrete example, and better understand the differences of components and flags, let's consider an example with the following repo structure (you can check out the example repo in github)

|-- core/
|  	|
|   |-- tests/
|   |-- __init__.py
|   |-- main.py
|
|-- emotions/
|   |
|   |-- tests/
|   |-- __init__.py
|   |-- ascii.py
|   |-- emoji.py
|
|-- fruits/
    |
    |-- tests/
    |-- __init__.py
    |-- ascii.py
    |-- emoji.py

Let's assume we only have 1 flag - unit - that makes a single upload with all the coverage information that we have from all the tests in the repo.

Given that fact, we can't have statuses based on the emotions or the fruits modules. To make that using flags we would have to break up our uploads into 3 separate flags, namely unit (to keep the data we had before), emotions, and fruits. That would also require that we upload the coverage info for each flag separately, for a total of 3 uploads. Depending on the structure of the project and its tests, supplying these coverage reports separately may be very difficult to do.

We can achieve the same effect using components by defining path filters we're interested in in our codecov.yaml.

Actually we can go a step further and filter paths that are not under a folder (and therefore would not be able to be defined using just flags), but can be related somehow. For example in the definition below we have ascii and emoji components that group all ascii.py and emoji.py files respectively.

# ... previous config options...

comment:
  layout: "header, diff, flags, components"  # show component info in the PR comment
  
component_management:
  default_rules:  # default rules that will be inherited by all components
    statuses:
      - type: project # in this case every component that doens't have a status defined will have a project type one
        target: auto
        branches:
          - "!main"
  individual_components:
    - component_id: module_emotions  # this is an identifier that should not be changed
      name: emotions  # this is a display name, and can be changed freely
      paths:
        - emotions/**
    - component_id: module_fruits
      name: fruits
      paths:
        - fruits/**
    - component_id: module_core
      name: core
      paths:
        - core/**
      statuses:           # the core component has its own statuses
        - type: project
          target: auto
        - type: patch
    - component_id: ascii
      paths:
        - .*/ascii.py
    - component_id: emoji
      paths:
        - .*/emoji.py

Component Options

Below are the configuration options commented for components. Very similar to flag management configuration.

component_management:
  default_rules:	# Dict. rules inherited by all components that don't define a tag for themselves.
    paths: # List. Path filters.
      - "specific_file.txt
      - "^some.*regex$"
      - "glob/*"
    flag_regexes: # List. Flags to be included in the component.
      - "fruit.*"
    statuses: # List. Status definitions.
    # These statuses are the same as for flag_management
    # Except they don't accept 'flags'
  individual_components:  # List. These are the actual components.
    - component_id: component_1  # String. Required.
      name: display_name_1	# String. Optional.
    # Individual components also accept paths, flag_regexes and statuses
    - component_id: other_component
    #...

Filtering With Components

You can now filter your files by component on any file tree or file list in the Codecov app. You can select multiple components and search for them within the dropdown conveniently located next to the flag filter at the top of a file list.

This gives you a way to see the most up to date coverage of a component in the UI as well as drill down to where you might be lacking coverage within this component.

Manage Your Components

  • When deleting components from your YAML, the removed components will not appear on your pull request. However, if you or someone else uses the removed component's name again, the historical data will return to your coverage over time metrics.
  • Each component has a unique ID, so if you change the name of your component, it will create a new component with new data. If you accidentally change the component name, you can simply change the name back to retrieve the previous data.

Should I Use Flags or Components?

If you have a new project, the correct answer is likely Components. If you already have a robust Flags-based setup in your project and it is working for you/your team, you should likely stick with Flags.

As of this writing, Flags do have more support in the Codecov UI than Components, but that is expected to change in the future as we build more Component support into the Codecov UI. However, if you require per-flag coverage trend information and UI support immediately, then it is recommend to use Flags for the time being.

๐Ÿ“˜

Flags and Paths Rules

If both flag_regexes and paths are defined for a component, that filter is AND-style. That means that for a file to be considered part of the component it needs to have coverage from one of the flags AND be in one of the paths defined.