microsoft/aspire · error
Could not resolve subnet ID for AGC load balancer
Error message
Could not resolve subnet ID for AGC load balancer '{lb.Name}'. What it means
Thrown by ApplyAlbCrdAsync when the subnet ID reference configured on an AGC (Azure Gateway with Containers) load balancer resource resolves to null or empty. kubectl cannot apply the ApplicationLoadBalancer CR without a concrete subnet resource ID.
Solutions
- Ensure the AKS/vnet Bicep module outputs the subnet resource ID and that the reference is wired via .WithSubnetId(...) or equivalent
- Verify the subnet reference points to a deployed virtual network subnet, not a name or prefix
- Re-run the deploy so referenced outputs are resolved before the ALB step
- Log the resolved SubnetIdReference value to confirm it is a full ARM subnet ID like /subscriptions/.../subnets/<name>
Example fix
// before
// var alb = aks.AddAlbLoadBalancer("alb"); // subnet never set
// after
// var alb = aks.AddAlbLoadBalancer("alb").WithSubnetId(vnet, "app-subnet"); Defensive patterns
Strategy: validation
Validate before calling
var subnetId = await ((IValueProvider)lb.SubnetIdReference).GetValueAsync(ct);
if (string.IsNullOrWhiteSpace(subnetId) || !subnetId.StartsWith("/subscriptions/"))
throw new InvalidOperationException($"Subnet ID unresolved or malformed: '{subnetId}'"); Prevention
- Always wire the ALB to a deployed vnet subnet via the supported API
- Assert the resolved value is a full ARM subnet ID before deploy
When it happens
Trigger: During deploy, the pipeline calls GetValueAsync on lb.SubnetIdReference (an IValueProvider) and receives null/empty, e.g. because the referenced subnet output has not been evaluated or the reference is misconfigured.
Common situations: The SubnetId points to a resource whose value comes from an Azure output that failed to resolve; the load balancer was configured without a subnet or with an empty string; wiring the reference to the wrong parameter type.
Understand the failure class
Background: "must not be empty", "cannot be empty" — required-field validation errors across open-source libraries — this error's family across 41 libraries.
Related errors
- AzureKubernetesLoadBalancerResource
- Cannot apply AGC ApplicationLoadBalancer CR for
- Timed out waiting for the 'azure-alb-external' GatewayClass…
- AppHost:DeploymentStatePathSha256 is required to isolate…
- az aks get-credentials failed
AI-assisted analysis of microsoft/aspire@25830f84bd (2026-09-16).
Data as JSON: /api/errors/7fcb5eea90e8fc6f.
Report an issue: GitHub.
Appendix: source
Thrown at src/Aspire.Hosting.Azure.Kubernetes/AzureKubernetesEnvironmentResource.AksPipeline.cs:543
if (lb.DisplacedDelegationServiceName is { } displaced)
{
// The subnet had an explicit non-trafficControllers service delegation when
// AddLoadBalancer was called. AzureSubnetResource emits only the LAST
// AzureSubnetServiceDelegationAnnotation, so AGC's trafficControllers
// delegation displaced the user's. Warn at deploy time so the user can
// either remove the original delegation or use a separate subnet.
context.Logger.LogWarning(
"AddLoadBalancer overrode an existing service delegation '{DisplacedServiceName}' " +
"on the subnet for AGC load balancer '{LoadBalancerName}' with " +
"'Microsoft.ServiceNetworking/trafficControllers'. AGC requires this delegation; " +
"if you need '{DisplacedServiceName}' to remain, use a separate subnet for the load balancer.",
displaced, lb.Name, displaced);
}
var subnetId = await ((IValueProvider)lb.SubnetIdReference).GetValueAsync(context.CancellationToken).ConfigureAwait(false);
if (string.IsNullOrEmpty(subnetId))
{
throw new InvalidOperationException(
$"Could not resolve subnet ID for AGC load balancer '{lb.Name}'.");
}
var kubeConfigPath = KubernetesEnvironment.KubeConfigPath
?? throw new InvalidOperationException(
$"Cannot apply AGC ApplicationLoadBalancer CR for '{lb.Name}': " +
$"kubeconfig was not set by aks-get-credentials-{Name}.");
// Wait for the azure-alb-external GatewayClass to appear. The AGC ALB
// controller add-on installs it asynchronously, so polling is required
// even after the AKS cluster reports Succeeded. 10-minute budget matches
// the E2E test budget in KubernetesGatewayTlsDeploymentTests.cs.
await WaitForAzureAlbGatewayClassAsync(
kubeConfigPath, context.Logger, TimeSpan.FromMinutes(10),
context.CancellationToken).ConfigureAwait(false);
// Apply the ApplicationLoadBalancer CR via kubectl apply -f - using stdin
// so we don't need a temp file. JSON is a valid YAML subset for kubectl.View on GitHub (pinned to 25830f84bd)