Skip to content

From v0.66.0 - %SHARD_NUM% placeholder not rendered for shardCount: 1 #2001

@rafaip

Description

@rafaip

Description

In v0.66.0, the defaultPlaceholders fallback for rendering %SHARD_NUM% in single-shard VMAgent deployments was removed during a refactor. This causes StatefulSet creation to fail when the VMAgent CR uses %SHARD_NUM% in affinity/labels with shardCount: 1.

Steps to reproduce

  1. Create a VMAgent CR with shardCount: 1 (or unset) and %SHARD_NUM% in the affinity:
  apiVersion: operator.victoriametrics.com/v1beta1
  kind: VMAgent
  metadata:
    name: main
  spec:
    shardCount: 1
    statefulMode: true
    affinity:
      podAntiAffinity:
        requiredDuringSchedulingIgnoredDuringExecution:
          - labelSelector:
              matchLabels:
                shard-num: '%SHARD_NUM%'
            topologyKey: kubernetes.io/hostname
  1. Deploy with operator v0.66.0+

Expected behavior

%SHARD_NUM% is replaced with "0" (as it was in v0.65.0), and the StatefulSet is created successfully.

Actual behavior

The literal string %SHARD_NUM% is passed to the Kubernetes API, which rejects it:

Warning  ReconciliationError  <unknown>  victoria-metrics-operator  cannot reconcile *v1.StatefulSet for vmagent(0): cannot create new sts vmagent-main under namespace victoria-metrics: StatefulSet.apps "vmagent-main" is invalid: spec.template.spec.affinity.podAntiAffinity.requiredDuringSchedulingIgnoredDuringExecution[0].labelSelector.matchLabels: Invalid value: "%SHARD_NUM%": a valid label must be an empty string or consist of alphanumeric characters, '-', '_' or '.', and must start and end with an alphanumeric character (e.g. 'MyValue',  or 'my_value',  or '12345', regex used for validation is '(([A-Za-z0-9][-A-Za-z0-9_.]*)?[A-Za-z0-9])?')

Additionally, the operator deletes the existing StatefulSet before attempting to create the new one, causing a full outage of the VMAgent.

Root cause

PR 1602 (Nov 7, 2025)
In v0.65.0, internal/controller/operator/factory/vmagent/vmagent.go had:

  // To save compatibility in the single-shard version still need to fill in %SHARD_NUM% placeholder           
  var defaultPlaceholders = map[string]string{shardNumPlaceholder: "0"}

This was called in the non-sharded deploy path via:

  newDeploy, err = k8stools.RenderPlaceholders(newDeploy, defaultPlaceholders)                                 

In v0.66.0, this was removed. RenderShard is now only called inside if cr.IsSharded(), which returns false for shardCount <= 1. The placeholder is never rendered.

Impact

  • Any VMAgent with shardCount: 1 (or unset) using %SHARD_NUM% in affinity, labels, or annotations will fail
    to reconcile
  • The operator deletes the existing StatefulSet before the new one is validated, causing data loss / scrape
    gap during the failed upgrade

Environment

  • Operator version: v0.66.1 (helm chart victoria-metrics-operator 0.57.1)
  • CRDs version: v0.66.1 (helm chart victoria-metrics-operator-crds 0.6.1)
  • Previous working version: v0.65.0 (helm chart victoria-metrics-operator 0.56.4)

Metadata

Metadata

Labels

bugSomething isn't working

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions