dotnet/orleans · error · InvalidOperationException
AZURE_CLIENT_ID must contain the user-assigned managed ident
Error message
AZURE_CLIENT_ID must contain the user-assigned managed identity client ID.
What it means
An InvalidOperationException thrown by AzureTableServiceClientFactory.Create when AzureTable:ServiceUri is a valid HTTPS URI but AZURE_CLIENT_ID does not parse as a GUID. The factory builds a DefaultAzureCredential with ManagedIdentityClientId, which must be the client ID (a Guid) of a user-assigned managed identity; a non-GUID value would produce a credential that cannot resolve the identity.
Source
Thrown at samples/Deployment/AzureContainerApps/Infrastructure/AzureTableServiceClientFactory.cs:26
public static class AzureTableServiceClientFactory
{
public static TableServiceClient Create(IConfiguration configuration, IHostEnvironment environment)
{
var serviceUriValue = configuration["AzureTable:ServiceUri"];
if (!string.IsNullOrWhiteSpace(serviceUriValue))
{
if (!Uri.TryCreate(serviceUriValue, UriKind.Absolute, out var serviceUri)
|| serviceUri.Scheme != Uri.UriSchemeHttps)
{
throw new InvalidOperationException(
"AzureTable:ServiceUri must be an absolute HTTPS Azure Table service URI.");
}
var credentialOptions = new DefaultAzureCredentialOptions();
var managedIdentityClientId = GetRequiredValue(configuration, "AZURE_CLIENT_ID");
if (!Guid.TryParse(managedIdentityClientId, out _))
{
throw new InvalidOperationException(
"AZURE_CLIENT_ID must contain the user-assigned managed identity client ID.");
}
credentialOptions.ManagedIdentityClientId = managedIdentityClientId;
return new TableServiceClient(serviceUri, new DefaultAzureCredential(credentialOptions));
}
var connectionString = configuration["AzureTable:ConnectionString"];
if (environment.IsDevelopment()
&& string.Equals(connectionString, "UseDevelopmentStorage=true", StringComparison.OrdinalIgnoreCase))
{
return new TableServiceClient(connectionString);
}
throw new InvalidOperationException(
"Configure AzureTable:ServiceUri for Azure, or use Azurite with "
+ "AzureTable:ConnectionString=UseDevelopmentStorage=true in Development.");
}View on GitHub (pinned to fca799fa70)
Solutions
- Set AZURE_CLIENT_ID to the user-assigned managed identity's client ID (a GUID) found in the identity's Azure portal properties.
- Confirm you are using the 'Client ID' (appId), not the 'Object ID' or 'Principal ID'.
- If using a system-assigned identity instead, remove ServiceUri handling or refactor the factory to omit ManagedIdentityClientId.
Example fix
// before (env) AZURE_CLIENT_ID=my-storage-account // after AZURE_CLIENT_ID=12345678-1234-1234-1234-1234567890ab
Defensive patterns
Strategy: validation
Validate before calling
var clientId = configuration["AZURE_CLIENT_ID"];
if (!Guid.TryParse(clientId, out _))
throw new InvalidOperationException("AZURE_CLIENT_ID must be a GUID (user-assigned managed identity client ID)."); Prevention
- Use the managed identity's Client ID (a GUID), not its Object/Principal ID.
- Copy the value from the identity's portal properties, not the tenant/app registration overview.
- For system-assigned identities, omit ManagedIdentityClientId.
When it happens
Trigger: The HTTPS service URI path is taken, but AZURE_CLIENT_ID is missing, an object ID (not a client ID), an application URI, or a mistyped string. Guid.TryParse returns false.
Common situations: Confusing the managed identity's object/principal ID with its client ID. Copying the tenant ID. The env var unset in the container app but ServiceUri set, so GetRequiredValue already caught empty — here the value is present but malformed.
Related errors
- AzureTable:ServiceUri must be an absolute HTTPS Azure Table
- Configure AzureTable:ServiceUri for Azure, or use Azurite wi
- {key} is not configured.
- WEBSITE_PRIVATE_PORTS must contain at least one TCP port.
- The required setting '{name}' isn't configured.
AI-assisted analysis of dotnet/orleans@fca799fa70 (2026-08-13).
Data as JSON: /api/errors/a8bbb158e0564f1c.
Report an issue: GitHub.