microsoft/aspire · error · InvalidOperationException

Kubernetes namespace

Error message

Kubernetes namespace '{@namespace}' is invalid. Use lowercase letters, numbers, and hyphens, start and end with an alphanumeric character, and stay within 63 characters. Set an explicit namespace with .WithHelm(h => h.WithNamespace("my-namespace")).

What it means

The Kubernetes namespace the engine resolved for the Helm deployment is validated against RFC-1123 DNS-label rules (lowercase alphanumerics and hyphens, start/end alphanumeric, max 63 characters). An invalid namespace would be rejected by the Kubernetes API anyway, so Aspire fails fast with an actionable message before invoking helm.

Solutions

  1. Set an explicit valid namespace with .WithHelm(h => h.WithNamespace("my-namespace")) using only lowercase letters, numbers, and hyphens.
  2. Fix the configured/derived namespace source (e.g. sanitize a CI branch name before using it as a namespace).
  3. Keep the namespace at 63 characters or fewer (this is the standard Kubernetes namespace limit).

Example fix

// before
.WithHelm(h => h.WithNamespace("My_Namespace"))

// after
.WithHelm(h => h.WithNamespace("my-namespace"))
Defensive patterns

Strategy: validation

Validate before calling

static bool IsValidKubernetesNamespace(string? ns) =>
    !string.IsNullOrEmpty(ns) && ns.Length <= 63 &&
    System.Text.RegularExpressions.Regex.IsMatch(ns, "^[a-z0-9]([-a-z0-9]*[a-z0-9])?$");
// validate before WithNamespace() / deploy.

Type guard

static bool IsValidKubernetesNamespace(string? ns) =>
    !string.IsNullOrEmpty(ns) && ns.Length <= 63 &&
    System.Text.RegularExpressions.Regex.IsMatch(ns, "^[a-z0-9]([-a-z0-9]*[a-z0-9])?$");

Prevention

When it happens

Trigger: ResolveNamespaceAsync resolves the namespace (from the Kubernetes environment resource configuration) and calls ValidateKubernetesNamespace; the error is thrown when the namespace exceeds KubernetesNamespaceMaxLength (63) or fails DnsLabelPattern - uppercase letters, underscores, dots, leading/trailing hyphen, or empty after derivation.

Common situations: Setting a namespace with an underscore or uppercase via .WithHelm(h => h.WithNamespace(...)), environment names derived from branch names containing '/' or '_' in CI, or copying a namespace from a context that allows dots.

Understand the failure class

Background: "invalid id" errors: invalid identifier format — why libraries reject IDs before lookup, and how to fix them — this error's family across 37 libraries.

Related errors


AI-assisted analysis of microsoft/aspire@25830f84bd (2026-09-16). Data as JSON: /api/errors/1e41f0773ccc4be1. Report an issue: GitHub.

Appendix: source

Thrown at src/Aspire.Hosting.Kubernetes/Deployment/HelmDeploymentEngine.cs:106

    private const int HelmReleaseNameMaxLength = 53;
    private const int KubernetesNamespaceMaxLength = 63;

    private static void ValidateHelmReleaseName(string releaseName)
    {
        if (releaseName.Length > HelmReleaseNameMaxLength || !DnsLabelPattern().IsMatch(releaseName))
        {
            throw new InvalidOperationException(
                $"Helm release name '{releaseName}' is invalid. Use lowercase letters, numbers, and hyphens, " +
                $"start and end with an alphanumeric character, and stay within {HelmReleaseNameMaxLength} characters. " +
                "Set an explicit release name with .WithHelm(h => h.WithReleaseName(\"my-release\")).");
        }
    }

    private static void ValidateKubernetesNamespace(string @namespace)
    {
        if (@namespace.Length > KubernetesNamespaceMaxLength || !DnsLabelPattern().IsMatch(@namespace))
        {
            throw new InvalidOperationException(
                $"Kubernetes namespace '{@namespace}' is invalid. Use lowercase letters, numbers, and hyphens, " +
                $"start and end with an alphanumeric character, and stay within {KubernetesNamespaceMaxLength} characters. " +
                "Set an explicit namespace with .WithHelm(h => h.WithNamespace(\"my-namespace\")).");
        }
    }

    [GeneratedRegex("^[a-z0-9]([-a-z0-9]*[a-z0-9])?$")]
    private static partial Regex DnsLabelPattern();

    /// <summary>
    /// Creates the deployment pipeline steps for the Helm engine.
    /// </summary>
    internal static Task<IReadOnlyList<PipelineStep>> CreateStepsAsync(
        KubernetesEnvironmentResource environment,
        PipelineStepFactoryContext factoryContext)
    {
        var model = factoryContext.PipelineContext.Model;
        var steps = new List<PipelineStep>();

View on GitHub (pinned to 25830f84bd)