Skip to content

feature: Add configurable labels for Argo Workflows - #2781

Open
Capiru wants to merge 6 commits into
Netflix:masterfrom
Capiru:ISSUE-2780-add-argo-workflows-labels
Open

feature: Add configurable labels for Argo Workflows#2781
Capiru wants to merge 6 commits into
Netflix:masterfrom
Capiru:ISSUE-2780-add-argo-workflows-labels

Conversation

@Capiru

@Capiru Capiru commented Feb 4, 2026

Copy link
Copy Markdown

Summary

Adds METAFLOW_ARGO_WORKFLOWS_LABELS for configuring labels on Argo WorkflowTemplates and generated Workflow resources.

Custom labels are intentionally not applied to Pods, JobSets, or Sensors. Step-level Kubernetes labels remain controlled by METAFLOW_KUBERNETES_LABELS and @kubernetes(labels=...).

Metaflow-owned labels take precedence over configured labels.

Usage

export METAFLOW_ARGO_WORKFLOWS_LABELS="team=ml-platform,cost-center=12345,environment=production"
python myflow.py argo-workflows create

Configured labels are added to:

  • WorkflowTemplate.metadata.labels
  • WorkflowTemplate.spec.workflowMetadata.labels, which supplies labels to generated Workflow resources

Testing

  • Tests default and configured labels
  • Tests protection of Metaflow-owned labels
  • Tests invalid configuration
  • Verifies labels in compiled WorkflowTemplate JSON

Fixes #2780

@Capiru Capiru changed the title ISSUE-2780 Add argo workflows labels feature: Add configurable labels for Argo Workflows Feb 4, 2026
@saikonen
saikonen self-requested a review February 4, 2026 13:22
@greptile-apps

greptile-apps Bot commented Jul 7, 2026

Copy link
Copy Markdown
Contributor

Greptile Summary

This PR adds configurable labels for Argo Workflow resources. The main changes are:

  • New METAFLOW_ARGO_WORKFLOWS_LABELS configuration.
  • Parsing and validation for configured Argo labels.
  • WorkflowTemplate and Workflow metadata label emission.
  • Protection for Metaflow-owned labels.
  • Tests for configured labels and compiled Argo output.

Confidence Score: 4/5

This is close, but the label key validation should be fixed before merging.

  • Workflow-level label application and Metaflow-owned label precedence look consistent with the changed tests.
  • User-supplied label prefixes can still pass local validation even though Kubernetes rejects them.
  • A malformed configured label can make Argo resource creation fail later instead of failing cleanly during Metaflow validation.

Files Needing Attention: metaflow/plugins/kubernetes/kube_utils.py

Important Files Changed

Filename Overview
metaflow/metaflow_config.py Adds the new Argo labels configuration default.
metaflow/plugins/argo/argo_workflows.py Parses configured Argo labels and applies them to workflow-level metadata while preserving Metaflow-owned labels.
metaflow/plugins/kubernetes/kube_utils.py Adds optional key validation for Kubernetes labels, but prefix validation still accepts keys Kubernetes rejects.
test/unit/test_argo_workflows_labels.py Adds unit coverage for configured Argo labels, protected labels, and invalid label values.
test/ux/core/test_argo_compilation.py Adds compilation coverage for configured labels in Argo WorkflowTemplate output.

Reviews (5): Last reviewed commit: "Improve Argo workflow label tests" | Re-trigger Greptile

Comment thread metaflow/plugins/argo/argo_workflows.py Outdated
Comment thread metaflow/plugins/argo/argo_workflows.py Outdated
Comment thread metaflow/plugins/argo/argo_workflows.py Outdated
Comment thread metaflow/plugins/argo/argo_workflows.py Outdated
self._schedule, self._timezone = self._get_schedule()

self._base_labels = self._base_kubernetes_labels()
self._base_labels = self._base_argo_labels()

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

just to double-check. base_labels also applies to sensors. Is it intended that the configurable ARGO_WORKFLOWS_LABELS applies to all argo resources, not only workflow/workflow templates?

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

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

This is a nice catch, I made it explicit so that it only applies to Workflow/Templates

Comment thread metaflow/plugins/argo/argo_workflows.py Outdated
Comment thread metaflow/plugins/argo/argo_workflows.py Outdated
Comment thread metaflow/plugins/kubernetes/kube_utils.py
Comment thread metaflow/plugins/argo/argo_workflows.py Outdated
def validate_label_key(key: str):
prefix, _, name = key.rpartition("/")
if prefix:
prefix_regex = r"^[A-Za-z0-9]([-A-Za-z0-9.]{0,251}[A-Za-z0-9])?$"

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

P1 Prefix Validation Incomplete This regex still accepts label prefixes that Kubernetes rejects. For example, METAFLOW_ARGO_WORKFLOWS_LABELS="Team/name=ml" passes because uppercase letters are allowed here, and a single 64-character prefix component also passes because only total prefix length is checked. Those labels then reach Argo metadata and fail later when Kubernetes validates the resource. Please validate the prefix as a DNS subdomain, including lowercase-only components and the per-component length limit.

Comment thread metaflow/plugins/argo/argo_workflows.py
Comment on lines +99 to +100
prefix_regex = r"^[A-Za-z0-9]([-A-Za-z0-9.]{0,251}[A-Za-z0-9])?$"
if not re.search(prefix_regex, prefix):

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

P1 Prefix validation remains loose

This prefix regex still accepts label keys that Kubernetes rejects. For example, METAFLOW_ARGO_WORKFLOWS_LABELS="Team/name=ml", "a..b/name=ml", or a key with a 64-character prefix component before /name can pass local validation. Those labels are then emitted into Argo metadata and the resource can fail later when Kubernetes validates it. Please validate the prefix as a DNS-1123 subdomain, including lowercase labels, non-empty dot-separated components, and the per-component length limit.

Comment on lines 198 to +199
self._base_labels = self._base_kubernetes_labels()
self._workflow_labels = self._base_argo_labels()

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

P1 Labels still miss resources

This split sends configured Argo labels only through _workflow_labels, while pods, JobSets, and Sensors keep using _base_labels. With METAFLOW_ARGO_WORKFLOWS_LABELS="team=ml", the WorkflowTemplate and Workflow get team=ml, but workflow pods, JobSets, and Sensors do not. Selectors, policy, or cost attribution that target those resources can still miss the workflow. The configured labels need to be included on those resource paths as defaults while keeping internal labels protected and preserving step-level overrides.

Capiru and others added 6 commits August 31, 2026 00:45
- validate label keys (not just values) since ARGO_WORKFLOWS_LABELS keys are
  fully user-supplied
- protect internal labels (app.kubernetes.io/part-of) from being overridden
  by custom env labels
- scope custom labels to WorkflowTemplate/Workflow level only; pod/JobSet/
  Sensor metadata keep using internal-only labels
@talsperre
talsperre force-pushed the ISSUE-2780-add-argo-workflows-labels branch from 98fc92f to 692c2c2 Compare August 31, 2026 00:46
def validate_label_key(key: str):
prefix, _, name = key.rpartition("/")
if prefix:
prefix_regex = r"^[A-Za-z0-9]([-A-Za-z0-9.]{0,251}[A-Za-z0-9])?$"

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

P1 Prefix validation incomplete

The new key-validation path still accepts label prefixes that Kubernetes rejects. When METAFLOW_ARGO_WORKFLOWS_LABELS is set to values like Team/name=ml, a..b/name=ml, a-/name=ml, or a key with a 64-character prefix component before /name, this regex can pass the key locally. The label is then emitted into WorkflowTemplate and Workflow metadata, where Kubernetes rejects it because label prefixes must be DNS subdomains with lowercase, non-empty dot-separated labels, each starting and ending alphanumeric and each at most 63 characters. Please validate the prefix component-by-component before accepting user-supplied label keys.

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Enhancement: Allow Argo Label customization

3 participants