dotnet/efcore · error · OperationException

More than one DbContext named

Error message

More than one DbContext named '{name}' was found. Specify which one to use by providing its fully qualified name using its exact case.

What it means

OperationException MultipleContextsWithQualifiedName thrown when both case-insensitive and exact-case filtering returned multiple matches, and none of those matches lives in the default (null) namespace. The supplied name is still ambiguous and must be made unique.

Solutions

  1. Supply a name that includes enough namespace prefix to select exactly one type.
  2. Rename the colliding context classes to be globally unique.
  3. Use `dotnet ef dbcontext list` output to copy the precise name.

Example fix

# before - 'Models.AppDbContext' resolves to two types in different root namespaces
> dotnet ef migrations add Init --context Models.AppDbContext

# after
> dotnet ef migrations add Init --context MyApp.Api.Models.AppDbContext
Defensive patterns

Strategy: validation

Validate before calling

var cs = types.Where(t => t.Name.Equals(name, StringComparison.Ordinal)).ToList();
if (cs.Count > 1 && cs.All(t => t.Namespace is not null))
    throw new InvalidOperationException($"'{name}' is still ambiguous; include the namespace.");

Try / catch

try { operations.CreateContext(name); }
catch (OperationException ex) when (ex.Message.Contains("fully qualified name using its exact case"))
{ /* extend the name with the full namespace prefix */ }

Prevention

When it happens

Trigger: Multiple contexts share the same fully-qualified-looking name across different namespaces, and none has no namespace. The final disambiguation step (select types with null namespace) yields nothing.

Common situations: Heavily nested module projects where contexts share short names across sub-namespaces; renaming/restructuring namespaces left duplicate short names.

Related errors


AI-assisted analysis of dotnet/efcore@3a2006ef56 (2026-08-11). Data as JSON: /api/errors/d4709005c1d79e3a. Report an issue: GitHub.

Appendix: source

Thrown at src/EFCore.Design/Design/Internal/DbContextOperations.cs:774

        }

        // Disambiguate using case
        candidates = FilterTypes(candidates, name, StringComparison.Ordinal);
        if (candidates.Count == 0)
        {
            throw new OperationException(DesignStrings.MultipleContextsWithName(name));
        }

        if (candidates.Count == 1)
        {
            return candidates;
        }

        // Allow selecting types in the default namespace
        candidates = candidates.Where(t => t.Key.Namespace == null).ToDictionary();
        if (candidates.Count == 0)
        {
            throw new OperationException(DesignStrings.MultipleContextsWithQualifiedName(name));
        }

        Check.DebugAssert(candidates.Count == 1, $"candidates.Count is {candidates.Count}");

        return candidates;
    }

    private static Dictionary<Type, Func<DbContext>?> FilterTypes(
        Dictionary<Type, Func<DbContext>?> types,
        string name,
        StringComparison comparisonType)
        => types
            .Where(t => string.Equals(t.Key.Name, name, comparisonType)
                || string.Equals(t.Key.FullName, name, comparisonType)
                || string.Equals(t.Key.AssemblyQualifiedName, name, comparisonType))
            .ToDictionary();
}

View on GitHub (pinned to 3a2006ef56)