EF6结合AAD认证本地正常,部署到Azure后数据库连接失败
你遇到的核心问题是:部署到Azure后,EF6仍在使用System.Data.SqlClient而非Microsoft.Data.SqlClient,导致不支持Authentication=Active Directory Default连接字符串参数,抛出"Invalid value for key 'authentication'"异常。本地正常但部署后失效,大概率是程序集加载优先级或Azure环境下的DbProviderFactories配置覆盖导致的。
1. 强制EF6使用指定的DbProviderFactory(代码配置)
在ApplicationDbContext的构造函数中,直接指定使用Microsoft.Data.SqlClient.SqlClientFactory,绕过配置文件可能的加载问题:
public class ApplicationDbContext : DbContext { public ApplicationDbContext() : base(CreateConnection(), true) {} private static DbConnection CreateConnection() { var connectionString = ConfigurationManager.ConnectionStrings["DefaultConnection"].ConnectionString; var factory = Microsoft.Data.SqlClient.SqlClientFactory.Instance; var connection = factory.CreateConnection(); connection.ConnectionString = connectionString; return connection; } // 其余代码保持不变... }
这种方式直接跳过EF6的默认提供程序解析逻辑,强制使用Microsoft.Data.SqlClient的连接工厂,避免配置被覆盖。
2. 确认Azure部署包中的程序集
- 检查Azure部署的bin目录,确保不存在
System.Data.Entity.SqlServer.dll(这是EF6默认的System.Data.SqlClient提供程序),同时确认ErikEJ.EntityFramework.SqlServer.dll和Microsoft.Data.SqlClient.dll已正确部署。 - 如果使用Web Deploy,确保发布时勾选了"Include all files from the project directory",避免依赖程序集缺失。
3. 修正web.config中的DbProviderFactories配置(添加clear)
Azure环境可能存在全局的DbProviderFactories配置,导致你的<remove>指令失效。添加<clear/>先清空所有已注册的工厂,再添加Microsoft.Data.SqlClient:
<system.data> <DbProviderFactories> <clear/> <!-- 先清空所有已注册的工厂 --> <remove invariant="System.Data.SqlClient"/> <add name="SqlClient Data Provider" invariant="Microsoft.Data.SqlClient" description=".NET Framework Data Provider for SqlServer" type="Microsoft.Data.SqlClient.SqlClientFactory, Microsoft.Data.SqlClient" /> </DbProviderFactories> </system.data>
4. 显式指定EF6的提供程序(代码配置)
在Application_Start(Global.asax.cs)中,手动注册EF6的提供程序,确保优先级高于默认的System.Data.SqlClient提供程序:
protected void Application_Start() { // 注册Microsoft.Data.SqlClient的EF6提供程序 DbConfiguration.Loaded += (sender, args) => { args.ReplaceService<DbProviderServices>( (s, k) => System.Data.Entity.SqlServer.MicrosoftSqlProviderServices.Instance); args.ReplaceService<DbProviderFactory>( (s, k) => Microsoft.Data.SqlClient.SqlClientFactory.Instance); }; // 其余初始化代码... }
5. 检查Azure App Service的.NET Framework版本
确保Azure App Service的运行时版本设置为**.NET Framework 4.8**,避免因版本兼容问题导致程序集加载异常:
- 进入Azure Portal -> 你的App Service -> 配置 -> 常规设置 -> .NET Framework版本,选择v4.8。
部署后,在Azure App Service的日志流中查看是否有程序集加载错误,或者在健康检查中添加日志输出当前使用的DbProvider类型:
// 健康检查中添加日志 using (var conn = new Microsoft.Data.SqlClient.SqlConnection(connectionString)) { conn.Open(); // 输出当前连接的提供程序类型 Trace.WriteLine($"Connection provider: {conn.GetType().Assembly.FullName}"); // 执行Select 1 using (var cmd = conn.CreateCommand()) { cmd.CommandText = "SELECT 1"; cmd.ExecuteScalar(); } }
如果输出显示Microsoft.Data.SqlClient,说明配置生效。
内容的提问来源于stack exchange,提问作者ØTS

