Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Migration does not work with custom default schema #3359

Open
newclaus opened this issue Nov 11, 2024 · 1 comment
Open

Migration does not work with custom default schema #3359

newclaus opened this issue Nov 11, 2024 · 1 comment

Comments

@newclaus
Copy link

newclaus commented Nov 11, 2024

Step:

  1. Create new db with default schema 'public'. Then apply some EF migrations. Table __EFMIgrationsHistory must be created
  2. Customize search_path in the db
    ALTER ROLE ALL SET search_path TO 'custom'
    Do not specify search path in connection string.
    3, Create new migration and apply it

There is such exception.

Unhandled exception. Npgsql.PostgresException (0x80004005): 42P07: relation "__EFMigrationsHistory" already exists
   at Npgsql.Internal.NpgsqlConnector.ReadMessageLong(Boolean async, DataRowLoadingMode dataRowLoadingMode, Boolean readingNotifications, Boolean isReadingPrependedMessage)
   at System.Runtime.CompilerServices.PoolingAsyncValueTaskMethodBuilder`1.StateMachineBox`1.System.Threading.Tasks.Sources.IValueTaskSource<TResult>.GetResult(Int16 token)
   at Npgsql.NpgsqlDataReader.NextResult(Boolean async, Boolean isConsuming, CancellationToken cancellationToken)
   at Npgsql.NpgsqlDataReader.NextResult(Boolean async, Boolean isConsuming, CancellationToken cancellationToken)
   at Npgsql.NpgsqlCommand.ExecuteReader(Boolean async, CommandBehavior behavior, CancellationToken cancellationToken)
   at Npgsql.NpgsqlCommand.ExecuteReader(Boolean async, CommandBehavior behavior, CancellationToken cancellationToken)
   at Npgsql.NpgsqlCommand.ExecuteNonQuery(Boolean async, CancellationToken cancellationToken)
   at [Microsoft.EntityFrameworkCore.Storage](http://microsoft.entityframeworkcore.storage/).RelationalCommand.ExecuteNonQueryAsync(RelationalCommandParameterObject parameterObject, CancellationToken cancellationToken)
   at [Microsoft.EntityFrameworkCore.Storage](http://microsoft.entityframeworkcore.storage/).RelationalCommand.ExecuteNonQueryAsync(RelationalCommandParameterObject parameterObject, CancellationToken cancellationToken)
   at [Microsoft.EntityFrameworkCore.Storage](http://microsoft.entityframeworkcore.storage/).RelationalCommand.ExecuteNonQueryAsync(RelationalCommandParameterObject parameterObject, CancellationToken cancellationToken)
   at Microsoft.EntityFrameworkCore.Migrations.Internal.Migrator.MigrateAsync(String targetMigration, CancellationToken cancellationToken)
   at Npgsql.EntityFrameworkCore.PostgreSQL.Migrations.Internal.NpgsqlMigrator.MigrateAsync(String targetMigration, CancellationToken cancellationToken)

It's because repository falls back in schema 'public':

protected override string ExistsSql
{
get
{
var stringTypeMapping = Dependencies.TypeMappingSource.GetMapping(typeof(string));
return
$"""
SELECT EXISTS (
SELECT 1 FROM pg_catalog.pg_class c
JOIN pg_catalog.pg_namespace n ON n.oid=c.relnamespace
WHERE n.nspname={stringTypeMapping.GenerateSqlLiteral(TableSchema ?? "public")} AND
c.relname={stringTypeMapping.GenerateSqlLiteral(TableName)}
)
""";
}
}

In my project I've by-passed this behavior by searching with schema only when TableSchema is specified, there is no fallback in public. If schema is not specified, searchin is performed only with table name

@RoystonS
Copy link

I hit exactly this issue last week. It's inconsistent behaviour because if you use the command-line tooling to generate the corresponding SQL script (ef migrations script), there's no mention of the explicit public schema.

Btw, the workaround I ended up putting in was to add a DbCommandInterceptor which intercepts the above SQL running and removes public and replaces it with a schema of my choice.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants