Skip to content

Commit 252f1bf

Browse files
committed
Support for database collations (part of #1050).
1 parent bd77ee5 commit 252f1bf

4 files changed

Lines changed: 50 additions & 80 deletions

File tree

src/FirebirdSql.EntityFrameworkCore.Firebird/Migrations/FbMigrationsSqlGenerator.cs

Lines changed: 2 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -16,13 +16,14 @@
1616
//$Authors = Jiri Cincura (jiri@cincura.net)
1717

1818
using System;
19+
using System.Collections.Generic;
1920
using System.Globalization;
2021
using System.Linq;
2122
using FirebirdSql.Data.FirebirdClient;
2223
using FirebirdSql.EntityFrameworkCore.Firebird.Infrastructure.Internal;
2324
using FirebirdSql.EntityFrameworkCore.Firebird.Metadata;
2425
using FirebirdSql.EntityFrameworkCore.Firebird.Metadata.Internal;
25-
using FirebirdSql.EntityFrameworkCore.Firebird.Migrations.Operations;
26+
using Microsoft.EntityFrameworkCore.Infrastructure;
2627
using Microsoft.EntityFrameworkCore.Metadata;
2728
using Microsoft.EntityFrameworkCore.Migrations;
2829
using Microsoft.EntityFrameworkCore.Migrations.Operations;
@@ -46,12 +47,6 @@ protected override void Generate(MigrationOperation operation, IModel model, Mig
4647
{
4748
switch (operation)
4849
{
49-
case FbCreateDatabaseOperation createDatabaseOperation:
50-
Generate(createDatabaseOperation, model, builder);
51-
break;
52-
case FbDropDatabaseOperation dropDatabaseOperation:
53-
Generate(dropDatabaseOperation, model, builder);
54-
break;
5550
default:
5651
base.Generate(operation, model, builder);
5752
break;
@@ -309,23 +304,6 @@ protected override void Generate(EnsureSchemaOperation operation, IModel model,
309304
=> throw new NotSupportedException("Schemas are not supported by Firebird.");
310305

311306

312-
public virtual void Generate(FbCreateDatabaseOperation operation, IModel model, MigrationCommandListBuilder builder)
313-
{
314-
if (Options.HasFlag(MigrationsSqlGenerationOptions.Script))
315-
throw new NotSupportedException("Creating database from script is not supported.");
316-
317-
FbConnection.CreateDatabase(operation.ConnectionString, pageSize: 16384);
318-
}
319-
320-
public virtual void Generate(FbDropDatabaseOperation operation, IModel model, MigrationCommandListBuilder builder)
321-
{
322-
if (Options.HasFlag(MigrationsSqlGenerationOptions.Script))
323-
throw new NotSupportedException("Dropping database from script is not supported.");
324-
325-
FbConnection.ClearPool(operation.ConnectionString);
326-
FbConnection.DropDatabase(operation.ConnectionString);
327-
}
328-
329307
protected override void ColumnDefinition(string schema, string table, string name, ColumnOperation operation, IModel model, MigrationCommandListBuilder builder)
330308
{
331309
builder.Append(Dependencies.SqlGenerationHelper.DelimitIdentifier(name));

src/FirebirdSql.EntityFrameworkCore.Firebird/Migrations/Operations/FbCreateDatabaseOperation.cs

Lines changed: 0 additions & 25 deletions
This file was deleted.

src/FirebirdSql.EntityFrameworkCore.Firebird/Migrations/Operations/FbDropDatabaseOperation.cs

Lines changed: 0 additions & 25 deletions
This file was deleted.

src/FirebirdSql.EntityFrameworkCore.Firebird/Storage/Internal/FbDatabaseCreator.cs

Lines changed: 48 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,8 @@
2020
using System.Threading.Tasks;
2121
using FirebirdSql.Data.FirebirdClient;
2222
using Microsoft.EntityFrameworkCore;
23+
using Microsoft.EntityFrameworkCore.Infrastructure;
24+
using Microsoft.EntityFrameworkCore.Metadata;
2325
using Microsoft.EntityFrameworkCore.Storage;
2426

2527
namespace FirebirdSql.EntityFrameworkCore.Firebird.Storage.Internal;
@@ -39,10 +41,42 @@ public FbDatabaseCreator(RelationalDatabaseCreatorDependencies dependencies, IFb
3941
public override void Create()
4042
{
4143
FbConnection.CreateDatabase(_connection.ConnectionString, pageSize: 16384);
44+
45+
var designTimeModel = Dependencies.CurrentContext.Context.GetService<IDesignTimeModel>().Model;
46+
47+
var collation = designTimeModel.GetCollation();
48+
if (collation != null)
49+
{
50+
Dependencies.ExecutionStrategy.Execute(
51+
_connection,
52+
connection => CreateAlterCollationCommand(collation).ExecuteNonQuery(
53+
new RelationalCommandParameterObject(
54+
connection,
55+
null,
56+
null,
57+
Dependencies.CurrentContext.Context,
58+
Dependencies.CommandLogger)));
59+
}
4260
}
43-
public override Task CreateAsync(CancellationToken cancellationToken = default)
61+
public override async Task CreateAsync(CancellationToken cancellationToken = default)
4462
{
45-
return FbConnection.CreateDatabaseAsync(_connection.ConnectionString, pageSize: 16384, cancellationToken: cancellationToken);
63+
await FbConnection.CreateDatabaseAsync(_connection.ConnectionString, pageSize: 16384, cancellationToken: cancellationToken).ConfigureAwait(false);
64+
65+
var designTimeModel = Dependencies.CurrentContext.Context.GetService<IDesignTimeModel>().Model;
66+
67+
var collation = designTimeModel.GetCollation();
68+
if (collation != null)
69+
{
70+
await Dependencies.ExecutionStrategy.ExecuteAsync(
71+
_connection,
72+
connection => CreateAlterCollationCommand(collation).ExecuteNonQueryAsync(
73+
new RelationalCommandParameterObject(
74+
connection,
75+
null,
76+
null,
77+
Dependencies.CurrentContext.Context,
78+
Dependencies.CommandLogger))).ConfigureAwait(false);
79+
}
4680
}
4781

4882
public override void Delete()
@@ -76,7 +110,7 @@ public override async Task<bool> ExistsAsync(CancellationToken cancellationToken
76110
{
77111
try
78112
{
79-
await _connection.OpenAsync(cancellationToken);
113+
await _connection.OpenAsync(cancellationToken).ConfigureAwait(false);
80114
return true;
81115
}
82116
catch (FbException)
@@ -85,7 +119,7 @@ public override async Task<bool> ExistsAsync(CancellationToken cancellationToken
85119
}
86120
finally
87121
{
88-
await _connection.CloseAsync();
122+
await _connection.CloseAsync().ConfigureAwait(false);
89123
}
90124
}
91125

@@ -113,12 +147,20 @@ public override Task<bool> HasTablesAsync(CancellationToken cancellationToken =
113147
null,
114148
Dependencies.CurrentContext.Context,
115149
Dependencies.CommandLogger),
116-
ct))
150+
ct).ConfigureAwait(false))
117151
!= 0,
118152
cancellationToken);
119153
}
120154

121155
IRelationalCommand CreateHasTablesCommand()
122156
=> _rawSqlCommandBuilder
123157
.Build("SELECT COUNT(*) FROM rdb$relations WHERE COALESCE(rdb$system_flag, 0) = 0 AND rdb$view_blr IS NULL");
124-
}
158+
159+
IRelationalCommand CreateAlterCollationCommand(string collation)
160+
=> _rawSqlCommandBuilder
161+
.Build($@"EXECUTE BLOCK
162+
AS
163+
BEGIN
164+
execute statement 'alter character set ' || (select coalesce(trim(rdb$character_set_name), 'NONE') from rdb$database) || ' set default collation {collation}';
165+
END");
166+
}

0 commit comments

Comments
 (0)