microsoft/aspire · error

The Azure deployment state for AKS environment

Error message

The Azure deployment state for AKS environment '{Name}' does not contain the deployed cluster identity.

What it means

Thrown by GetAksCredentialsForDestroyAsync when the cached Azure deployment state for the AKS environment has no 'ClusterResourceId' output. The library reads the deployment outputs left by a prior deploy to find the managed cluster ID during destroy; a missing output means the state is incomplete or from a different/failed deployment.

Solutions

  1. Re-deploy the AKS environment so fresh, complete deployment state (including the cluster identity output) is written, then retry destroy
  2. Verify the Bicep template still emits the cluster resource ID output and was not customized/trimmed
  3. Delete the stale deployment state for this environment so the pipeline treats it as never deployed and re-runs the full flow
  4. If the cluster was deleted out-of-band, remove the environment from the app model or its state entry instead of destroying

Example fix

// before: destroying with stale state after manually trimming Bicep outputs
// output clusterResourceId string
// after: restore the output in the AKS Bicep module
// output clusterResourceId string = aksCluster.id
// then: aspire run/publish to refresh state before destroy
Defensive patterns

Strategy: validation

Validate before calling

var state = await GetDeploymentStateAsync();
if (state.Data is null || !state.Data.ContainsKey("ClusterResourceId"))
    throw new InvalidOperationException("Deployment state missing ClusterResourceId; redeploy before destroy.");

Prevention

When it happens

Trigger: Running aspire destroy/publish pipeline (getDestroyCredentialsStep) for an AzureKubernetesEnvironmentResource whose recorded deployment state lacks the cluster resource ID output.

Common situations: The Bicep module was edited and no longer emits the cluster ID output; the deployment state file was truncated, hand-edited, or written by a partially failed deploy; deploying a newer/older template than the one that created the state.

Understand the failure class

Background: Record Not Found Errors: "not found", RecordNotFound, and "was not found" — what they mean and how to fix them — this error's family across 28 libraries.

Related errors


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

Appendix: source

Thrown at src/Aspire.Hosting.Azure.Kubernetes/AzureKubernetesEnvironmentResource.AksPipeline.cs:399

        //     "name": { "type": "String", "value": "aks-abc123" }
        //   }
        // Read it directly because the provisioning step that normally populates Outputs is not
        // part of a fresh destroy process.
        ResourceIdentifier? clusterResourceId;
        try
        {
            clusterResourceId = GetPersistedAksResourceId(deploymentStateSection.Data);
        }
        catch (Exception ex) when (ex is not OperationCanceledException)
        {
            throw new InvalidOperationException(
                $"The Azure deployment state for AKS environment '{Name}' contains invalid outputs.",
                ex);
        }

        if (clusterResourceId is null)
        {
            throw new InvalidOperationException(
                $"The Azure deployment state for AKS environment '{Name}' does not contain the deployed cluster identity.");
        }

        // Scope is persisted as a JSON string using the same shape produced by
        // BicepUtilities.SetScopeAsync:
        //   { "resourceGroup": "shared-rg", "subscription": "00000000-..." }
        // A missing property means the resource did not pin that scope value, so only that value
        // falls back to global Azure deployment state. Older state without Scope uses the persisted
        // resource ID so a changed AppHost scope cannot redirect cleanup to another cluster or wait
        // on provisioning that is not part of the destroy graph.
        string subscriptionId;
        string? resourceGroupName;
        if (deploymentStateSection.Data["Scope"] is not null)
        {
            string? scopedSubscription;
            string? scopedResourceGroup;
            try
            {

View on GitHub (pinned to 25830f84bd)