我有一个ASP.NET MVC应用程序。当通过 CustomerController 创建新客户时,我运行一个新的后台任务(使用 HostingEnvironment.QueueBackgroundWorkItem )为该客户创建一个新的Azure SqlDatabase。
我使用Entity Framework Code First创建/初始化新数据库。这是代码:
// My ConnectionString
var con = "...";
// Initialization strategy: create db and execute all Migrations
// MyConfiguration is just a DbMigrationsConfiguration with AutomaticMigrationsEnabled = true
Database.SetInitializer(strategy: new MigrateDatabaseToLatestVersion<CustomerDataContext, MyConfiguration>(useSuppliedContext: true));
using (var context = new CustomerDataContext(con))
{
// Neither 'Connection Timeout=300' in ConnectionString nor this line helps -> TimeoutException will rise after 30-40s
context.Database.CommandTimeout = 300;
// create the db - this lines throws the exception after ~40s
context.Database.Initialize(true);
}
我的问题是我在大约40秒后总是得到 TimeoutException 。我认为这是因为Azure无法在这么短的时间内初始化新数据库。不要误解我的意思:Azure将很好地创建数据库,但我想等待那一点/摆脱 TimeoutException 。
EDIT1: 我在我的ConnectionString中使用 Connection Timeout = 300 ,但我的应用并不关心这一点;大约40年后,我总是遇到一个SqlError。
EDIT2: 引发的异常是 SqlException 。 消息:超时已过期。操作完成之前经过的超时时间或服务器没有响应。 源:。Net SqlClient数据提供程序
EDIT3: 我现在可以说,这与ASP.NET / IIS无关。即使在简单的UnitTest方法中,上面的代码也会失败。
答案 0 :(得分:7)
在使用Code First Migrations时,似乎还有另一个CommandTimeout设置涉及数据库初始化过程。我想在这里分享我的解决方案,以防任何人遇到这个问题。
感谢Rowan Miller提示他指出解决方案。
这是我的代码:
// Initialisation strategy
Database.SetInitializer(strategy: new CreateDatabaseIfNotExists<MyDataContext>());
// Use DbContext
using (var context = new MyDataContext(myConnectionString))
{
// Setting the CommandTimeout here does not prevent the database
// initialization process from raising a TimeoutException when using
// Code First Migrations so I think it's not needed here.
//context.Database.CommandTimeout = 300;
// this will create the database if it does not exist
context.Database.Initialize(force: false);
}
我的Configuration.cs类:
public sealed class Configuration : DbMigrationsConfiguration<MyDataContext>
{
public Configuration()
{
AutomaticMigrationsEnabled = false;
AutomaticMigrationDataLossAllowed = false;
// Very important! Gives me enough time to wait for Azure
// to initialize (Create -> Migrate -> Seed) the database.
// Usually Azure needs 1-2 minutes so the default value of
// 30 seconds is not big enough!
CommandTimeout = 300;
}
}
答案 1 :(得分:1)
命令超时和连接超时是两种不同的设置。在这种情况下,您只需增加commandtimeout。您可以在web.config中增加连接超时:Connection Timeout=120
。您希望增加连接超时的唯一时间是在创建数据库时。