dotnet/efcore · error · OperationException

A migration name must be specified.

Error message

A migration name must be specified.

What it means

PrepareForMigration is the shared front door for any operation that scaffolds a migration (AddMigration path). It rejects a null, empty, or whitespace-only migration name before doing any work, because the name becomes both the class name and the file name. The check is string.IsNullOrWhiteSpace, so ' ' fails too.

Solutions

  1. Provide a non-empty migration name: 'dotnet ef migrations add InitialCreate'.
  2. In scripted usage, validate the name variable is non-empty before invoking EF.
  3. Avoid names that are only whitespace.

Example fix

# before
dotnet ef migrations add
# after
dotnet ef migrations add InitialCreate
Defensive patterns

Strategy: validation

Validate before calling

if (string.IsNullOrWhiteSpace(migrationName))
{
    throw new ArgumentException("A migration name is required.", nameof(migrationName));
}

Try / catch

try { operations.AddMigration(name, outputDir, contextType, ns, dryRun); }
catch (OperationException ex) when (ex.Message.Contains("migration name must be specified"))
{ /* supply a non-empty name */ }

Prevention

When it happens

Trigger: Calling any migration-scaffolding path that routes through PrepareForMigration with a name that is null, empty, or whitespace-only. Typically the CLI/PMC parse a missing positional/argument as null or empty string.

Common situations: Forgetting the migration name positional argument: 'dotnet ef migrations add' with no name; a script/CI step that interpolates an unset variable into the name; a GUI/tool that submits an empty string.

Related errors


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

Appendix: source

Thrown at src/EFCore.Design/Design/Internal/MigrationsOperations.cs:440

        var migrationsAssembly = scope.ServiceProvider.GetRequiredService<IMigrationsAssembly>();
        var compiledAssembly = compiler.CompileMigration(migration, context.GetType());
        migrationsAssembly.AddMigrations(compiledAssembly);

        migrator.Migrate(migration.MigrationId);

        _reporter.WriteInformation(DesignStrings.MigrationCreatedAndApplied(migration.MigrationId));

        return files;
    }

    /// <summary>
    ///     Prepares common resources for migration operations.
    /// </summary>
    public virtual IServiceProvider PrepareForMigration(string name, DbContext context)
    {
        if (string.IsNullOrWhiteSpace(name))
        {
            throw new OperationException(DesignStrings.MigrationNameRequired);
        }

        var invalidPathChars = Path.GetInvalidFileNameChars();
        if (name.Any(c => invalidPathChars.Contains(c)))
        {
            throw new OperationException(
                DesignStrings.BadMigrationName(name, string.Join("','", invalidPathChars)));
        }

        var contextClassName = context.GetType().Name;
        if (string.Equals(name, contextClassName, StringComparison.Ordinal))
        {
            throw new OperationException(
                DesignStrings.ConflictingContextAndMigrationName(name));
        }

        var services = _servicesBuilder.Build(context);
        EnsureServices(services);

View on GitHub (pinned to 3a2006ef56)