microsoft/aspire · error · InvalidOperationException
Dashboard testing is not supported in publish mode.
Error message
Dashboard testing is not supported in publish mode.
What it means
ConfigureDashboardTesting in DistributedApplicationTestingBuilder throws this InvalidOperationException when the test builder runs in publish mode (ExecutionContext.IsPublishMode). Dashboard testing configuration (fixed ports, anonymous access, interactivity suppression) only applies to run mode, so publish-mode execution is rejected rather than misconfigured.
Solutions
- Run dashboard tests in run mode; do not enable publish mode in the test host configuration
- Use the publish-mode APIs (e.g. builder.CreatePublishModeSnapshot / publishing tests) instead of the dashboard testing builder for deployment validation
- Remove env/config that flips IsPublishMode (check for ASPNETCORE / ASPIRE publish switches in test setup)
Example fix
// before var builder = await DistributedApplicationTestingBuilder.CreateAsync<Projects.AppHost>([], (o, _) => o.EnablePublishMode = true); // publish mode // after var builder = await DistributedApplicationTestingBuilder.CreateAsync<Projects.AppHost>(); // run mode, dashboard testing allowed
Defensive patterns
Strategy: try-catch
Validate before calling
var execContext = builder.ExecutionContext;
if (execContext.IsPublishMode) { /* use publishing APIs instead of dashboard testing */ } Try / catch
try
{
var builder = await DistributedApplicationTestingBuilder.CreateAsync<Projects.AppHost>();
}
catch (InvalidOperationException ex) when (ex.Message.Contains("publish mode"))
{
// switch to publish-mode test APIs
} Prevention
- Keep dashboard tests in run mode
- Remove publish-mode env/config flags from the test host setup
- Use dedicated publishing test APIs for deployment validation
When it happens
Trigger: Creating a DistributedApplicationTestingBuilder whose execution context is publish mode — e.g. tests invoking the publishing pipeline or setting publish-mode environment flags before the dashboard testing configuration is applied.
Common situations: Reusing the testing builder for publish/deployment tests; environment variables (ASPIRE_*/DOTNET_* publish flags) leaking into test host config; mixing run-mode and publish-mode test setups.
Understand the failure class
Background: UnsupportedOperationException and "is not supported" errors: when a library deliberately refuses a call — this error's family across 30 libraries.
Related errors
- The dashboard URL is not available in publish mode.
- Array params contains empty item
- Array params contains null item
- Endpoint ' ' for resource ' ' not found.
- InvalidOperationException with caller-provided…
AI-assisted analysis of microsoft/aspire@25830f84bd (2026-09-16).
Data as JSON: /api/errors/937462ad5f95f0be.
Report an issue: GitHub.
Appendix: source
Thrown at src/Aspire.Hosting.Testing/DistributedApplicationTestingBuilder.cs:360
$"{KnownConfigNames.DashboardFrontendBrowserToken}={browserToken}",
$"{KnownConfigNames.DashboardResourceServiceClientApiKey}={resourceServiceApiKey}"
];
applicationOptions.Args = hostBuilderOptions.Args;
hostBuilderOptions.Configuration ??= new();
AddDashboardTestingConfiguration(hostBuilderOptions.Configuration);
}
private static void ConfigureDashboardTesting(IDistributedApplicationBuilder builder, DashboardTestingState dashboardTestingState)
{
if (!dashboardTestingState.Enabled)
{
return;
}
if (builder.ExecutionContext.IsPublishMode)
{
throw new InvalidOperationException(Properties.Resources.DashboardTestingPublishModeExceptionMessage);
}
// Apply these after the builder has loaded environment variables and command-line arguments so test
// automation cannot accidentally opt back into fixed ports, anonymous access, or interactivity.
// Callers can still override runtime settings through the returned builder; constructor-time service
// selection, including dashboard authentication, has already completed.
AddDashboardTestingConfiguration(builder.Configuration);
// Restore the generated browser token if something cleared it. DistributedApplicationBuilder freezes the
// token into AppHost:BrowserToken during construction, but DashboardOptions does not read that key until the
// application starts, so AppHost code running between those two points can blank it. DashboardEventHandlers
// treats a null or empty token as a request for Unsecured frontend authentication, which would silently
// downgrade the authenticated default this opt-in promises, so the guard mirrors that same emptiness check
// and leaves any non-empty token, including a deliberately chosen one, alone. This runs after the AppHost
// entry point has finished configuring, because the builder is not handed back until it reaches Build(), and
// before the caller sees the builder, so a test that wants the anonymous dashboard can still choose it
// through the returned builder.
if (string.IsNullOrEmpty(builder.Configuration["AppHost:BrowserToken"]))View on GitHub (pinned to 25830f84bd)