Prometheus Exporter Implementation

The Prometheus exporter implementation in this project is designed to gather Balena metrics and expose them in the Prometheus exposition format. The following sections describe how this is achieved.

Balena API Interaction

The exporter uses the Balena API to retrieve fleet data, specifically focusing on the number of devices online within each fleet.

Retrieval of Fleet IDs:

  • The exporter first fetches a list of fleets that the user has access to using the Balena API endpoint: https://api.balena-cloud.com/v6/application?$filter=is_directly_accessible_by__user/any(dau:1 eq 1). This endpoint returns a list of applications (fleets) based on the user’s access permissions.
  • The Balena API token is used to authenticate requests, ensuring authorized access.

Gathering Fleet Metrics:

  • For each fleet ID retrieved, the exporter makes another request to the Balena API endpoint: https://api.balena-cloud.com/v6/application({fleet_id})?$expand=owns__device/$count($filter=is_online eq true).
  • This endpoint returns a count of online devices for the specified fleet, as well as the fleet name.

Prometheus Exposition Format

The exporter transforms the Balena metrics into the Prometheus exposition format using the prometheus_client library.

Metric Structure:

  • The exporter defines a single metric named balena_devices_online representing the number of online devices in a fleet.
  • The metric has one label, fleet_name, to differentiate device counts across different fleets.
  • The metric value is a float representing the count of online devices.

Example:

balena_devices_online{fleet_name="test_fleet"} 3.0
          

Exposing Metrics via HTTP

The exporter exposes the collected metrics via HTTP on port 8000, the default Prometheus port.

Implementation:

  • The exporter uses the prometheus_client library to register the Balena collector and start an HTTP server.
  • The start_http_server function from the prometheus_client library is used to initialize the server.
  • The Balena collector is registered with the REGISTRY from the prometheus_client library.

Environment Variables:

  • BALENA_TOKEN: Required environment variable, providing the Balena API token for authentication.
  • CRAWL_INTERVAL: Optional environment variable, specifying the interval (in seconds) at which the exporter should collect metrics. Defaults to 60 seconds.

Testing

The exporter includes unit tests to verify its functionality.

Test Suite:

  • The tests/test_exporter.py file contains unit tests that mock Balena API calls and verify the exporter’s data retrieval and transformation logic.
  • The tests use the unittest and mock libraries to simulate API responses and test the exporter’s behavior.

Examples:

  • test_collect: Tests the collect method, verifying the correct metric values and labels.
  • test_get_balena_fleets: Tests the get_balena_fleets method, asserting the correct list of fleet IDs is retrieved.
  • test_get_fleet_metrics: Tests the get_fleet_metrics method, verifying the accurate retrieval of fleet name and online device count.

Deployment

The exporter can be deployed as a Docker container.

Dockerfile:

  • The Dockerfile defines the build process, including dependencies, image base, and entry point.
  • It uses Python 3.10-alpine as the base image and installs required Python libraries.

Deployment Steps:

  1. Build the Docker image: docker build -t balena-exporter .
  2. Run the container: docker run -d --name balena-exporter -p 8000:8000 -e BALENA_TOKEN=<YOUR_BALENA_TOKEN> balena-exporter
  3. Access the metrics: curl http://localhost:8000/metrics

Note: Replace <YOUR_BALENA_TOKEN> with your actual Balena API token.


          ## Top-Level Directory Explanations
          
          <a class='local-link directory-link' data-ref="tests/" href="#tests/">tests/</a> - This directory contains all the unit and integration tests for the project. It includes the `__init__.py` file which makes it a package, and specific test files like `test_exporter.py`.