{"record":{"id":"cf2652d65ddb9ced","repo":"microsoft/aspire","slug":"apphost-path-not-found-in-configuration","errorCode":null,"errorMessage":"AppHost path not found in configuration.","messagePattern":"AppHost path not found in configuration\\.","errorType":"exception","errorClass":"InvalidOperationException","httpStatus":null,"severity":"error","filePath":"src/Aspire.Hosting/Backchannel/AuxiliaryBackchannelRpcTarget.cs","lineNumber":870,"sourceCode":"    #region V1 API Methods (Legacy - Keep for backward compatibility)\n\n    /// <summary>\n    /// Gets information about the AppHost for the MCP server.\n    /// </summary>\n    /// <param name=\"cancellationToken\">A cancellation token.</param>\n    /// <returns>The AppHost information including the fully qualified path and process ID.</returns>\n    /// <exception cref=\"InvalidOperationException\">Thrown when AppHost information is not available.</exception>\n    public Task<AppHostInformation> GetAppHostInformationAsync(CancellationToken cancellationToken = default)\n    {\n        // The cancellationToken parameter is not currently used, but is retained for API consistency and potential future support for cancellation.\n        _ = cancellationToken;\n\n        // First try to get the file path (with extension), otherwise fall back to the path (without extension)\n        var appHostPath = configuration[\"AppHost:FilePath\"] ?? configuration[\"AppHost:Path\"];\n        if (string.IsNullOrEmpty(appHostPath))\n        {\n            logger.LogError(\"AppHost path not found in configuration.\");\n            throw new InvalidOperationException(\"AppHost path not found in configuration.\");\n        }\n\n        // Get the CLI process ID if the AppHost was launched via the CLI\n        int? cliProcessId = null;\n        var cliPidString = configuration[KnownConfigNames.CliProcessId];\n        if (!string.IsNullOrEmpty(cliPidString) && int.TryParse(cliPidString, out var parsedCliPid))\n        {\n            cliProcessId = parsedCliPid;\n        }\n        DateTimeOffset? cliStartedAt = null;\n        var cliStartedAtString = configuration[KnownConfigNames.CliProcessStarted];\n        if (!string.IsNullOrEmpty(cliStartedAtString) && long.TryParse(cliStartedAtString, out var parsedCliStartedAt))\n        {\n            cliStartedAt = DateTimeOffset.FromUnixTimeSeconds(parsedCliStartedAt);\n        }\n\n        // ASPIRE_CLI_STARTED_STABLE is the stable launcher-CLI identity time that current CLIs stamp\n        // alongside the legacy value, in Unix milliseconds. It survives wall-clock steps, so surfacing it","sourceCodeStart":852,"sourceCodeEnd":888,"githubUrl":"https://github.com/microsoft/aspire/blob/25830f84bd145686607ad00c057b3f84e2e51d43/src/Aspire.Hosting/Backchannel/AuxiliaryBackchannelRpcTarget.cs#L852-L888","documentation":"GetAppHostInformationAsync reads the AppHost file path from configuration keys AppHost:FilePath (preferred) or AppHost:Path (fallback). When neither is set, it logs an error and throws this InvalidOperationException because the response cannot be built without a path.","triggerScenarios":"Calling the auxiliary backchannel GetAppHostInformationAsync RPC in a host process whose configuration lacks AppHost:FilePath/AppHost:Path — e.g. AppHost launched by a custom runner instead of the Aspire CLI/DCP, or config keys removed/renamed.","commonSituations":"Launching the AppHost directly via `dotnet run` or a custom host without Aspire's launcher wiring; environment variable or appsettings omissions; mixing Aspire versions where the config key names changed.","solutions":["Launch the AppHost through the Aspire CLI or AppHost runner, which sets AppHost:FilePath.","Set configuration AppHost:FilePath (full path with extension) explicitly, e.g. env var AppHost__FilePath=/path/to/AppHost.csproj.","Verify KnownConfigNames wiring — AppHost:Path is only a fallback; prefer FilePath.","Check that config sources (appsettings, env vars) are actually loaded in the host process."],"exampleFix":"// before\ndotnet run --project MyApproj // config lacks AppHost:FilePath\n// after\nAppHost__FilePath=/path/to/MyApp.AppHost/MyApp.AppHost.csproj dotnet run --project MyApp.AppHost","handlingStrategy":"validation","validationCode":"if (string.IsNullOrEmpty(configuration[\"AppHost:FilePath\"]) && string.IsNullOrEmpty(configuration[\"AppHost:Path\"]))\n    throw new InvalidOperationException(\"Set AppHost:FilePath (e.g. env AppHost__FilePath) before calling get-apphost-information.\");","typeGuard":null,"tryCatchPattern":"try { await rpc.GetAppHostInformationAsync(); }\ncatch (InvalidOperationException ex) when (ex.Message.Contains(\"AppHost path not found\")) { logger.LogError(ex, \"Launch via aspire CLI or set AppHost__FilePath.\"); }","preventionTips":["Launch the AppHost via the Aspire CLI/DCP so AppHost:FilePath is set.","Set AppHost__FilePath explicitly when using a custom runner.","Verify config env vars are visible in the AppHost process."],"tags":["configuration","apphost","backchannel"],"backgroundTag":"missing-required-config-field","analyzedSha":"25830f84bd145686607ad00c057b3f84e2e51d43","analyzedAt":"2026-09-16T11:10:06.193Z","contentChangedAt":"2026-09-16T11:10:06.193Z","schemaVersion":2},"datasetVersion":"2026-09-21T04:17:39.646Z"}