Skip to content

feat(monitor): Standardized OpenTelemetry and Dynamic Cluster Node Labeling - #2512

Closed
aniket866 wants to merge 3 commits into
Project-HAMi:masterfrom
aniket866:fix/standardized-opentelemetry-dynamic-node-labeling
Closed

feat(monitor): Standardized OpenTelemetry and Dynamic Cluster Node Labeling#2512
aniket866 wants to merge 3 commits into
Project-HAMi:masterfrom
aniket866:fix/standardized-opentelemetry-dynamic-node-labeling

Conversation

@aniket866

@aniket866 aniket866 commented Aug 9, 2026

Copy link
Copy Markdown
Contributor
Field Details
Description Prometheus metrics emitted by vGPUmonitor rely on local metric names (hami_host_gpu_memory_used_bytes) and lack standard Kubernetes node identification labels (node_name, cluster_id).
Location cmd/vGPUmonitor/metrics.go (in metric descriptor definitions)
Bug / Feature Feature
Reason Aggregating metrics across multi-cluster Prometheus deployments requires manual Prometheus relabeling configs because node identity is not attached to individual container metrics.
Proposed Changes Add --node-name and --cluster-id parameters to auto-inject node_name and cluster_id metric labels across all exported Prometheus descriptors.

Before vs. After Architecture

flowchart LR
    subgraph Before["Before: Unlabeled Metrics without Cluster Node Identity"]
        direction TB
        B1["Metric Generation in vGPUmonitor"]
        B2["Labels: namespace, pod, container, vdevice"]
        B3["Exported without Node or Cluster Identity"]
        B4["Central Prometheus Scrapes Hundreds of Nodes"]
        B5["Requires Heavy Relabeling Configurations"]
        B6["Incompatible with OpenTelemetry Standards"]

        B1 --> B2
        B2 --> B3
        B3 --> B4
        B4 --> B5
        B5 --> B6
    end

    Before ==>|Standardized Node & Cluster Metadata Injection| After

    subgraph After["After: OpenTelemetry Compliant Standard Metrics"]
        direction TB
        A1["Metric Generation in vGPUmonitor"]
        A2["Labels: node_name, cluster_id, namespace..."]
        A3["Exported with Standardized Infrastructure Labels"]
        A4["Central Prometheus Receives Fully Labeled Series"]
        A5["Zero Relabeling Overhead & Instant Dashboards"]
        A6["Fully OpenTelemetry Compliant"]

        A1 --> A2
        A2 --> A3
        A3 --> A4
        A4 --> A5
        A5 --> A6
    end

    classDef danger fill:#fee2e2,stroke:#ef4444,stroke-width:2px,color:#991b1b;
    classDef success fill:#dcfce7,stroke:#22c55e,stroke-width:2px,color:#166534;
    classDef neutral fill:#f3f4f6,stroke:#4b5563,stroke-width:1.5px,color:#1f2937;

    class B3,B5,B6 danger;
    class A2,A3,A5,A6 success;
    class B1,B2,B4,A1,A4 neutral;
Loading

Workflow & Component Diagram

graph TD
    A["vGPUmonitor Initialization"] --> B["Read Node Name from Env (util.NodeNameEnvName)"]
    B --> C["Read Cluster ID from CLI Flag (--cluster-id)"]
    C --> D["Construct Base Label Map: node_name, cluster_id"]
    D --> E["Create Wrapped Prometheus Registerer: prometheus.WrapRegistererWith()"]
    E --> F["Register ClusterManagerCollector with Base Labels"]
    F --> G["Prometheus Scrape Triggered"]
    G --> H["Collector Emits Gauge Metrics"]
    H --> I["Base Labels Auto-Appended to All Metric Families"]
    I --> J["Serve Standardized Metric Stream over HTTP"]
Loading

Closes #2510

Summary by CodeRabbit

  • New Features

    • Added configurable node name and cluster ID settings for metrics collection.
    • Metrics now include optional node and cluster labels alongside the zone label.
    • Node identification automatically falls back to the runtime environment when not explicitly configured.
    • Improved compatibility with Kubernetes client integrations for container and pod monitoring.
  • Documentation

    • Added a v2.9.0 changelog entry covering standardized metrics and dynamic cluster-node labeling.

…beling

Signed-off-by: aniket866 <iamaniketkumarmaner@gmail.com>
Signed-off-by: aniket866 <iamaniketkumarmaner@gmail.com>
@hami-robot
hami-robot Bot requested a review from chaunceyjiang August 9, 2026 13:34
@hami-robot
hami-robot Bot requested a review from DSFans2014 August 9, 2026 13:34
@hami-robot

hami-robot Bot commented Aug 9, 2026

Copy link
Copy Markdown
Contributor

[APPROVALNOTIFIER] This PR is NOT APPROVED

This pull-request has been approved by: aniket866
Once this PR has been reviewed and has the lgtm label, please assign dsfans2014 for approval. For more information see the Kubernetes Code Review Process.

The full list of commands accepted by this bot can be found here.

Details Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@github-actions github-actions Bot added the kind/feature new function label Aug 9, 2026
@hami-robot hami-robot Bot added the size/M label Aug 9, 2026
@coderabbitai

coderabbitai Bot commented Aug 9, 2026

Copy link
Copy Markdown

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 7474ee06-f70b-4c99-9e2d-5c741c68712d

📥 Commits

Reviewing files that changed from the base of the PR and between 0226b09 and f9ad876.

📒 Files selected for processing (2)
  • cmd/vGPUmonitor/metrics_test.go
  • pkg/monitor/nvidia/cudevshr.go
🚧 Files skipped from review as they are similar to previous changes (2)
  • pkg/monitor/nvidia/cudevshr.go
  • cmd/vGPUmonitor/metrics_test.go

📝 Walkthrough

Walkthrough

vGPUmonitor now accepts node and cluster identifiers through CLI flags. ClusterManager stores these values, resolves a missing node name from the environment, and registers metrics with optional node_name and cluster_id labels. ContainerLister supports injected Kubernetes interfaces.

Changes

vGPUmonitor metric identity and client initialization

Layer / File(s) Summary
Client injection and manager initialization
pkg/monitor/nvidia/cudevshr.go, cmd/vGPUmonitor/metrics.go, cmd/vGPUmonitor/metrics_test.go
ContainerLister accepts kubernetes.Interface through a new constructor. NewClusterManager stores the supplied identifiers and starts the pod informer only when a usable clientset exists. The test verifies the stored identifiers.
CLI configuration flow
cmd/vGPUmonitor/main.go
The CLI defines --node-name and --cluster-id and passes both values to NewClusterManager.
Metric collection and label registration
cmd/vGPUmonitor/metrics.go, CHANGELOG.md
Pod and MIG collection uses the stored node name with an environment fallback. Metric registration includes zone and optional node_name and cluster_id labels. The changelog records the v2.9.0 feature.

Estimated code review effort: 3 (Moderate) | ~20 minutes

Sequence Diagram(s)

sequenceDiagram
  participant CLI as vGPUmonitor CLI
  participant Manager as ClusterManager
  participant Prometheus as Prometheus
  CLI->>Manager: provide nodeName and clusterID
  Manager->>Manager: resolve nodeName from environment when empty
  Manager->>Prometheus: register metrics with optional identity labels
  Prometheus-->>Manager: scrape collector metrics
Loading

Possibly related issues

  • Issue 2152 — Both changes add native node_name labeling in cmd/vGPUmonitor/metrics.go; this PR also adds cluster_id and CLI configuration.

Possibly related PRs

Suggested reviewers: mesutoezdil, chaunceyjiang, dsfans2014

Poem

A rabbit adds two flags with care,
Node and cluster labels travel there.
Metrics hop beside the zone,
Client interfaces now are known.
The informer starts when clients are shown.

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly describes standardized metrics and dynamic cluster-node labeling, which match the primary changes.
Linked Issues check ✅ Passed The changes add node and cluster configuration, propagate both identifiers, and apply the labels to exported metrics as required by issue [#2510].
Out of Scope Changes check ✅ Passed The clientset interface and constructor changes support injected Kubernetes clients and metric initialization, so they are related to the stated objectives.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@coderabbitai
coderabbitai Bot requested a review from mesutoezdil August 9, 2026 13:35

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

🧹 Nitpick comments (1)
cmd/vGPUmonitor/metrics_test.go (1)

71-82: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Assert the Prometheus label contract.

The test checks only NodeName and ClusterID fields. It does not inspect the registry, so it passes if WrapRegistererWith omits either label. Gather a metric fixture and assert node_name="node-1" and cluster_id="cluster-1". Add coverage for node-name resolution from util.NodeNameEnvName.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@cmd/vGPUmonitor/metrics_test.go` around lines 71 - 82, Strengthen
TestNewClusterManagerNodeAndClusterIDLabels by gathering a registered metric
from reg and asserting its labels include node_name="node-1" and
cluster_id="cluster-1", rather than checking only struct fields. Add a test case
that verifies node-name resolution when util.NodeNameEnvName is configured.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@cmd/vGPUmonitor/main.go`:
- Line 149: Update the vGPU monitor registration flow around NewClusterManager
and versionmetrics.NewBuildInfoCollector so the build-info collector is
registered through the same prometheus.WrapRegistererWith identity labels
containing node_name and cluster_id. Ensure hami_build_info is emitted with
those labels alongside ClusterManagerCollector metrics, rather than remaining
registered on the raw registry.

In `@cmd/vGPUmonitor/metrics_test.go`:
- Around line 72-74: Update TestNewClusterManagerNodeAndClusterIDLabels to avoid
passing an uninitialized &nvidia.ContainerLister{} into NewClusterManager;
construct the ContainerLister with an initialized fake clientset before creating
the manager, or use a setup that does not start the informer while preserving
the test’s label-registration assertions.

In `@cmd/vGPUmonitor/metrics.go`:
- Around line 509-512: Resolve the effective node name once in the shared
collection flow, preferring ClusterManager.NodeName and falling back to
util.NodeNameEnvName, then pass or reuse it in both
collectPodAndContainerMigInfo and collectPodAndContainerInfo. Remove the direct
NODE_NAME lookup from collectPodAndContainerInfo so --node-name consistently
controls regular and MIG container metric collection.

---

Nitpick comments:
In `@cmd/vGPUmonitor/metrics_test.go`:
- Around line 71-82: Strengthen TestNewClusterManagerNodeAndClusterIDLabels by
gathering a registered metric from reg and asserting its labels include
node_name="node-1" and cluster_id="cluster-1", rather than checking only struct
fields. Add a test case that verifies node-name resolution when
util.NodeNameEnvName is configured.
🪄 Autofix

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: d395269a-367a-457f-b57e-6dd072499436

📥 Commits

Reviewing files that changed from the base of the PR and between 3616313 and 8a377b8.

📒 Files selected for processing (4)
  • CHANGELOG.md
  • cmd/vGPUmonitor/main.go
  • cmd/vGPUmonitor/metrics.go
  • cmd/vGPUmonitor/metrics_test.go

Comment thread cmd/vGPUmonitor/main.go
Comment thread cmd/vGPUmonitor/metrics_test.go Outdated
Comment thread cmd/vGPUmonitor/metrics.go

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
cmd/vGPUmonitor/metrics.go (1)

575-588: 🗄️ Data Integrity & Integration | 🟠 Major | ⚡ Quick win

Pass the effective node name into the container lister.

start() calls nvidia.NewContainerLister() before NewClusterManager(...), and NewContainerLister() only reads NODE_NAME; it does not consider --node-name and returns an error when NODE_NAME is empty. Resolve --node-name/NODE_NAME once in cmd/vGPUmonitor, accept that value via a lister constructor, use it for ContainerLister.nodeName, and keep NewClusterManager consistent.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@cmd/vGPUmonitor/metrics.go` around lines 575 - 588, Resolve the effective
node name from --node-name with NODE_NAME as fallback once in start(), then pass
it into nvidia.NewContainerLister through its constructor and use it for
ContainerLister.nodeName without re-reading the environment. Pass the same
resolved value to NewClusterManager, preserving existing behavior when only
NODE_NAME is configured.
🧹 Nitpick comments (1)
cmd/vGPUmonitor/metrics.go (1)

598-607: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick win

Verify labels at the Prometheus registry boundary.

The current test context checks ClusterManager.NodeName and ClusterID, but it does not verify gathered metrics. Add a registry assertion that checks node_name and cluster_id on emitted metric families, including the documented behavior when either value is empty.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@cmd/vGPUmonitor/metrics.go` around lines 598 - 607, Extend the test around
the Prometheus registration flow using prometheus.WrapRegistererWith and
MustRegister to gather metric families from the registry and assert emitted
node_name and cluster_id labels. Cover both populated values and the documented
empty-value behavior, ensuring labels are absent when their corresponding input
is empty.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@cmd/vGPUmonitor/metrics.go`:
- Around line 590-595: Validate containerLister and its Clientset in
NewClusterManager/initMetrics before completing registration, returning an error
when either dependency is nil so Collect cannot reach PodLister or
containerLister operations with invalid state. Alternatively, ensure Collect
safely skips both pod and container metric paths when dependencies are
unavailable, while preserving successful registration for valid inputs.

---

Outside diff comments:
In `@cmd/vGPUmonitor/metrics.go`:
- Around line 575-588: Resolve the effective node name from --node-name with
NODE_NAME as fallback once in start(), then pass it into
nvidia.NewContainerLister through its constructor and use it for
ContainerLister.nodeName without re-reading the environment. Pass the same
resolved value to NewClusterManager, preserving existing behavior when only
NODE_NAME is configured.

---

Nitpick comments:
In `@cmd/vGPUmonitor/metrics.go`:
- Around line 598-607: Extend the test around the Prometheus registration flow
using prometheus.WrapRegistererWith and MustRegister to gather metric families
from the registry and assert emitted node_name and cluster_id labels. Cover both
populated values and the documented empty-value behavior, ensuring labels are
absent when their corresponding input is empty.
🪄 Autofix

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: ca26452d-1ad1-46c7-a062-0ea85043d2d1

📥 Commits

Reviewing files that changed from the base of the PR and between 8a377b8 and 0226b09.

📒 Files selected for processing (3)
  • cmd/vGPUmonitor/metrics.go
  • cmd/vGPUmonitor/metrics_test.go
  • pkg/monitor/nvidia/cudevshr.go
🚧 Files skipped from review as they are similar to previous changes (1)
  • cmd/vGPUmonitor/metrics_test.go

Comment thread cmd/vGPUmonitor/metrics.go
…st and prioritize NodeName from ClusterManager

Signed-off-by: aniket866 <iamaniketkumarmaner@gmail.com>
@aniket866
aniket866 force-pushed the fix/standardized-opentelemetry-dynamic-node-labeling branch from 0226b09 to f9ad876 Compare August 9, 2026 14:40
@codecov

codecov Bot commented Aug 9, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 77.41935% with 7 lines in your changes missing coverage. Please review.

Files with missing lines Patch % Lines
pkg/monitor/nvidia/cudevshr.go 20.00% 4 Missing ⚠️
cmd/vGPUmonitor/metrics.go 91.30% 1 Missing and 1 partial ⚠️
cmd/vGPUmonitor/main.go 66.66% 1 Missing ⚠️
Flag Coverage Δ
unittests 64.34% <77.41%> (+0.13%) ⬆️

Flags with carried forward coverage won't be shown. Click here to find out more.

Files with missing lines Coverage Δ
cmd/vGPUmonitor/main.go 12.16% <66.66%> (+2.43%) ⬆️
cmd/vGPUmonitor/metrics.go 49.51% <91.30%> (+6.01%) ⬆️
pkg/monitor/nvidia/cudevshr.go 84.70% <20.00%> (-2.05%) ⬇️

... and 1 file with indirect coverage changes

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@devGPP23

devGPP23 commented Aug 9, 2026

Copy link
Copy Markdown
Contributor

Hi @aniket866,
great work adding the node_name and cluster_id Prometheus labels

Just a quick heads-up on the PR title since this PR focuses on Prometheus labeling (using prometheus.WrapRegistererWith) rather than the OpenTelemetry SDK or tracing spans, it might be helpful to update the title to reflect the Prometheus work instead.

The LFX umbrella issue (#2126) has separate deliverables for Prometheus metric improvements and an OpenTelemetry tracing PoC. Updating the title will help mentors avoid conflating the two, as the actual OTel SDK tracing PoC is being addressed in a separate PR.

Thanks again for the contribution!

@mesutoezdil

Copy link
Copy Markdown
Contributor

You can view the relevant rule here.
https://github.com/Project-HAMi/HAMi/blob/master/CONTRIBUTING.md#contribution-gates
"4. Review replies. The reply you post must be written by you and must address the specific point raised. Verbatim or canned AI replies, or replies that do not engage the comment, lead to the PR being closed."

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

feat(monitor): Standardized OpenTelemetry and Dynamic Cluster Node Labeling

3 participants