microsoft/aspire · error · InvalidOperationException

MCP server configuration

Error message

MCP server configuration '{builder.Resource.Name}' already has a connector. The current Connector Namespace preview supports one connector per MCP server configuration.

What it means

The Connector Namespace preview limits each MCP server configuration to exactly one connector route. WithConnector enforces this by throwing when Resource.Connectors is non-empty, making the preview constraint explicit instead of silently overwriting the previous route.

Solutions

  1. Create an additional MCP server configuration for the second connector and call WithConnector once on each.
  2. Remove one of the WithConnector calls so the config keeps a single connector.
  3. When the preview lifts the one-connector limit, revisit this constraint (it is a preview limitation, not a permanent API rule).

Example fix

// before
var tools = ns.AddMcpServerConfig("tools", options);
tools.WithConnector("db-conn", dbConnection, o);
tools.WithConnector("storage-conn", storageConnection, o); // throws

// after
var tools = ns.AddMcpServerConfig("tools", options)
    .WithConnector("db-conn", dbConnection, o);
var storage = ns.AddMcpServerConfig("storage-tools", storageOptions)
    .WithConnector("storage-conn", storageConnection, o);
Defensive patterns

Strategy: validation

Validate before calling

if (mcp.Resource.Connectors.Count == 0)
{
    mcp.WithConnector(name, connection, connectorOptions);
}

Try / catch

try
{
    mcp.WithConnector(name, connection, connectorOptions);
}
catch (InvalidOperationException ex) when (ex.Message.Contains("already has a connector"))
{
    // create another MCP server configuration for the extra connector
}

Prevention

When it happens

Trigger: Calling WithConnector a second time on the same MCP server configuration, regardless of which connection is used for the second call.

Common situations: Wiring several connectors (database + storage, multiple tools) to one MCP server config; loops or shared helpers that attach connectors to every config in a namespace.

Related errors


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

Appendix: source

Thrown at src/Aspire.Hosting.Azure.ConnectorNamespace/AzureConnectorNamespaceExtensions.cs:602

        ArgumentException.ThrowIfNullOrWhiteSpace(connectorName);
        ArgumentNullException.ThrowIfNull(connection);
        ArgumentNullException.ThrowIfNull(options);

        if (builder.Resource.IsExisting)
        {
            throw new InvalidOperationException(
                $"Existing MCP server configuration '{builder.Resource.Name}' is read-only.");
        }

        if (!ReferenceEquals(builder.Resource.Parent, connection.Resource.Parent))
        {
            throw new InvalidOperationException(
                $"Connector connection '{connection.Resource.Name}' belongs to a different Connector Namespace.");
        }

        if (builder.Resource.Connectors.Count > 0)
        {
            throw new InvalidOperationException(
                $"MCP server configuration '{builder.Resource.Name}' already has a connector. " +
                "The current Connector Namespace preview supports one connector per MCP server configuration.");
        }

        if (options.Operations is null || options.Operations.Length == 0)
        {
            throw new ArgumentException(
                "At least one connector operation must be explicitly allow-listed.",
                nameof(options));
        }

        var operationNames = new HashSet<string>(StringComparer.OrdinalIgnoreCase);
        var connectorDefinition = new AzureConnectorNamespaceMcpConnectorDefinition(
            connectorName,
            options.DisplayName,
            options.Description,
            connection.Resource);
        foreach (var operation in options.Operations)

View on GitHub (pinned to 25830f84bd)