diff --git a/src/EFCore.SqlServer.HierarchyId/Extensions/SqlServerHierarchyIdDbContextOptionsBuilderExtensions.cs b/src/EFCore.SqlServer.HierarchyId/Extensions/SqlServerHierarchyIdDbContextOptionsBuilderExtensions.cs index 74c21901203..86a3e314b2c 100644 --- a/src/EFCore.SqlServer.HierarchyId/Extensions/SqlServerHierarchyIdDbContextOptionsBuilderExtensions.cs +++ b/src/EFCore.SqlServer.HierarchyId/Extensions/SqlServerHierarchyIdDbContextOptionsBuilderExtensions.cs @@ -16,8 +16,9 @@ public static class SqlServerHierarchyIdDbContextOptionsBuilderExtensions /// /// The builder being used to configure SQL Server. /// The options builder so that further configuration can be chained. - public static SqlServerDbContextOptionsBuilder UseHierarchyId( - this SqlServerDbContextOptionsBuilder optionsBuilder) + public static T UseHierarchyId( + this T optionsBuilder) + where T : SqlEngineDbContextOptionsBuilderBase { var coreOptionsBuilder = ((IRelationalDbContextOptionsBuilderInfrastructure)optionsBuilder).OptionsBuilder; diff --git a/src/EFCore.SqlServer.HierarchyId/Scaffolding/Internal/SqlServerHierarchyIdCodeGeneratorPlugin.cs b/src/EFCore.SqlServer.HierarchyId/Scaffolding/Internal/SqlServerHierarchyIdCodeGeneratorPlugin.cs index 28097fe1132..b30818fda61 100644 --- a/src/EFCore.SqlServer.HierarchyId/Scaffolding/Internal/SqlServerHierarchyIdCodeGeneratorPlugin.cs +++ b/src/EFCore.SqlServer.HierarchyId/Scaffolding/Internal/SqlServerHierarchyIdCodeGeneratorPlugin.cs @@ -13,6 +13,13 @@ namespace Microsoft.EntityFrameworkCore.SqlServer.Scaffolding.Internal; /// public class SqlServerHierarchyIdCodeGeneratorPlugin : ProviderCodeGeneratorPlugin { + private static readonly MethodInfo UseHierarchyIdMethodInfo + = typeof(SqlServerHierarchyIdDbContextOptionsBuilderExtensions) + .GetRuntimeMethods() + .First(m => m.Name == nameof(SqlServerHierarchyIdDbContextOptionsBuilderExtensions.UseHierarchyId) + && m.GetParameters() is [{ ParameterType: var parameterType }] + && parameterType.TryGetElementType(typeof(SqlEngineDbContextOptionsBuilderBase<>)) is not null); + /// /// This is an internal API that supports the Entity Framework Core infrastructure and not subject to /// the same compatibility standards as public APIs. It may be changed or removed without notice in @@ -20,8 +27,5 @@ public class SqlServerHierarchyIdCodeGeneratorPlugin : ProviderCodeGeneratorPlug /// doing so can result in application failures when updating to a new Entity Framework Core release. /// public override MethodCallCodeFragment GenerateProviderOptions() - => new( - typeof(SqlServerHierarchyIdDbContextOptionsBuilderExtensions).GetRuntimeMethod( - nameof(SqlServerHierarchyIdDbContextOptionsBuilderExtensions.UseHierarchyId), - [typeof(SqlServerDbContextOptionsBuilder)])!); + => new(UseHierarchyIdMethodInfo); } diff --git a/src/EFCore.SqlServer.NTS/Extensions/SqlServerNetTopologySuiteDbContextOptionsBuilderExtensions.cs b/src/EFCore.SqlServer.NTS/Extensions/SqlServerNetTopologySuiteDbContextOptionsBuilderExtensions.cs index 2d16c843968..5bb1c19304a 100644 --- a/src/EFCore.SqlServer.NTS/Extensions/SqlServerNetTopologySuiteDbContextOptionsBuilderExtensions.cs +++ b/src/EFCore.SqlServer.NTS/Extensions/SqlServerNetTopologySuiteDbContextOptionsBuilderExtensions.cs @@ -21,8 +21,9 @@ public static class SqlServerNetTopologySuiteDbContextOptionsBuilderExtensions /// /// The build being used to configure SQL Server. /// The options builder so that further configuration can be chained. - public static SqlServerDbContextOptionsBuilder UseNetTopologySuite( - this SqlServerDbContextOptionsBuilder optionsBuilder) + public static T UseNetTopologySuite( + this T optionsBuilder) + where T : SqlEngineDbContextOptionsBuilderBase { var coreOptionsBuilder = ((IRelationalDbContextOptionsBuilderInfrastructure)optionsBuilder).OptionsBuilder; diff --git a/src/EFCore.SqlServer.NTS/Scaffolding/Internal/SqlServerNetTopologySuiteCodeGeneratorPlugin.cs b/src/EFCore.SqlServer.NTS/Scaffolding/Internal/SqlServerNetTopologySuiteCodeGeneratorPlugin.cs index 1a211cd4936..6046bce88e3 100644 --- a/src/EFCore.SqlServer.NTS/Scaffolding/Internal/SqlServerNetTopologySuiteCodeGeneratorPlugin.cs +++ b/src/EFCore.SqlServer.NTS/Scaffolding/Internal/SqlServerNetTopologySuiteCodeGeneratorPlugin.cs @@ -12,9 +12,11 @@ namespace Microsoft.EntityFrameworkCore.SqlServer.Scaffolding.Internal; public class SqlServerNetTopologySuiteCodeGeneratorPlugin : ProviderCodeGeneratorPlugin { private static readonly MethodInfo UseNetTopologySuiteMethodInfo - = typeof(SqlServerNetTopologySuiteDbContextOptionsBuilderExtensions).GetRuntimeMethod( - nameof(SqlServerNetTopologySuiteDbContextOptionsBuilderExtensions.UseNetTopologySuite), - [typeof(SqlServerDbContextOptionsBuilder)])!; + = typeof(SqlServerNetTopologySuiteDbContextOptionsBuilderExtensions) + .GetRuntimeMethods() + .First(m => m.Name == nameof(SqlServerNetTopologySuiteDbContextOptionsBuilderExtensions.UseNetTopologySuite) + && m.GetParameters() is [{ ParameterType: var parameterType }] + && parameterType.TryGetElementType(typeof(SqlEngineDbContextOptionsBuilderBase<>)) is not null); /// /// This is an internal API that supports the Entity Framework Core infrastructure and not subject to diff --git a/src/EFCore.SqlServer/Infrastructure/AzureSqlDbContextOptionsBuilder.cs b/src/EFCore.SqlServer/Infrastructure/AzureSqlDbContextOptionsBuilder.cs index eed86e36130..9f069f73291 100644 --- a/src/EFCore.SqlServer/Infrastructure/AzureSqlDbContextOptionsBuilder.cs +++ b/src/EFCore.SqlServer/Infrastructure/AzureSqlDbContextOptionsBuilder.cs @@ -1,8 +1,6 @@ // Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. -using Microsoft.EntityFrameworkCore.SqlServer.Infrastructure.Internal; - namespace Microsoft.EntityFrameworkCore.Infrastructure; /// @@ -13,8 +11,7 @@ namespace Microsoft.EntityFrameworkCore.Infrastructure; /// /// and it is not designed to be directly constructed in your application code. /// -public class AzureSqlDbContextOptionsBuilder - : RelationalDbContextOptionsBuilder +public class AzureSqlDbContextOptionsBuilder : SqlEngineDbContextOptionsBuilderBase { /// /// Initializes a new instance of the class. diff --git a/src/EFCore.SqlServer/Infrastructure/AzureSynapseDbContextOptionsBuilder.cs b/src/EFCore.SqlServer/Infrastructure/AzureSynapseDbContextOptionsBuilder.cs index ae23ab4a2fb..436838e2b98 100644 --- a/src/EFCore.SqlServer/Infrastructure/AzureSynapseDbContextOptionsBuilder.cs +++ b/src/EFCore.SqlServer/Infrastructure/AzureSynapseDbContextOptionsBuilder.cs @@ -1,8 +1,6 @@ // Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. -using Microsoft.EntityFrameworkCore.SqlServer.Infrastructure.Internal; - namespace Microsoft.EntityFrameworkCore.Infrastructure; /// @@ -13,8 +11,7 @@ namespace Microsoft.EntityFrameworkCore.Infrastructure; /// /// and it is not designed to be directly constructed in your application code. /// -public class AzureSynapseDbContextOptionsBuilder - : RelationalDbContextOptionsBuilder +public class AzureSynapseDbContextOptionsBuilder : SqlEngineDbContextOptionsBuilderBase { /// /// Initializes a new instance of the class. diff --git a/src/EFCore.SqlServer/Infrastructure/SqlEngineDbContextOptionsBuilder.cs b/src/EFCore.SqlServer/Infrastructure/SqlEngineDbContextOptionsBuilder.cs index 3a324ab8a4d..616969e9357 100644 --- a/src/EFCore.SqlServer/Infrastructure/SqlEngineDbContextOptionsBuilder.cs +++ b/src/EFCore.SqlServer/Infrastructure/SqlEngineDbContextOptionsBuilder.cs @@ -1,8 +1,6 @@ // Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. -using Microsoft.EntityFrameworkCore.SqlServer.Infrastructure.Internal; - namespace Microsoft.EntityFrameworkCore.Infrastructure; /// @@ -13,8 +11,7 @@ namespace Microsoft.EntityFrameworkCore.Infrastructure; /// /// and it is not designed to be directly constructed in your application code. /// -public class SqlEngineDbContextOptionsBuilder - : RelationalDbContextOptionsBuilder +public class SqlEngineDbContextOptionsBuilder : SqlEngineDbContextOptionsBuilderBase { /// /// Initializes a new instance of the class. diff --git a/src/EFCore.SqlServer/Infrastructure/SqlEngineDbContextOptionsBuilderBase.cs b/src/EFCore.SqlServer/Infrastructure/SqlEngineDbContextOptionsBuilderBase.cs new file mode 100644 index 00000000000..42f66acfc35 --- /dev/null +++ b/src/EFCore.SqlServer/Infrastructure/SqlEngineDbContextOptionsBuilderBase.cs @@ -0,0 +1,15 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +using Microsoft.EntityFrameworkCore.SqlServer.Infrastructure.Internal; + +namespace Microsoft.EntityFrameworkCore.Infrastructure; + +/// +/// Base class for SQL Server, Azure SQL, Azure Synapse, etc. specific builders. +/// +public abstract class SqlEngineDbContextOptionsBuilderBase(DbContextOptionsBuilder optionsBuilder) + : RelationalDbContextOptionsBuilder(optionsBuilder) + where TSelf : SqlEngineDbContextOptionsBuilderBase +{ +} diff --git a/src/EFCore.SqlServer/Infrastructure/SqlServerDbContextOptionsBuilder.cs b/src/EFCore.SqlServer/Infrastructure/SqlServerDbContextOptionsBuilder.cs index 3e6560ce581..ab8d5649ca8 100644 --- a/src/EFCore.SqlServer/Infrastructure/SqlServerDbContextOptionsBuilder.cs +++ b/src/EFCore.SqlServer/Infrastructure/SqlServerDbContextOptionsBuilder.cs @@ -1,8 +1,6 @@ // Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. -using Microsoft.EntityFrameworkCore.SqlServer.Infrastructure.Internal; - namespace Microsoft.EntityFrameworkCore.Infrastructure; /// @@ -13,8 +11,7 @@ namespace Microsoft.EntityFrameworkCore.Infrastructure; /// /// and it is not designed to be directly constructed in your application code. /// -public class SqlServerDbContextOptionsBuilder - : RelationalDbContextOptionsBuilder +public class SqlServerDbContextOptionsBuilder : SqlEngineDbContextOptionsBuilderBase { /// /// Initializes a new instance of the class. diff --git a/test/EFCore.SqlServer.Tests/Extensions/AzureSqlDbContextOptionsExtensionsTest.cs b/test/EFCore.SqlServer.Tests/Extensions/AzureSqlDbContextOptionsExtensionsTest.cs new file mode 100644 index 00000000000..ba25e6611fa --- /dev/null +++ b/test/EFCore.SqlServer.Tests/Extensions/AzureSqlDbContextOptionsExtensionsTest.cs @@ -0,0 +1,16 @@ +// Licensed to the .NET Foundation under one or more agreements. +// The .NET Foundation licenses this file to you under the MIT license. + +// ReSharper disable InconsistentNaming +namespace Microsoft.EntityFrameworkCore; + +public class AzureSqlDbContextOptionsExtensionsTest +{ + [ConditionalFact] + public void Can_call_UseNetTopologySuite_with_UseAzureSql() + { + // This test just makes sure we can call/compile UseNetTopologySuite with UseAzureSql. + var optionsBuilder = new DbContextOptionsBuilder(); + optionsBuilder.UseAzureSql("Database=Crunchie", b => b.UseNetTopologySuite()); + } +}