我正在尝试构建一个快速测试,每次运行时都会删除并重新创建数据库。我有以下内容:
[TestClass]
public class PocoTest
{
private TransactionScope _transactionScope;
private ProjectDataSource _dataSource;
private Repository _repository = new Repository();
private const string _cstring = "Data Source=.;Initial Catalog=test_db;Trusted_Connection=True";
[TestInitialize]
public virtual void TestInitialize()
{
_dataSource = new ProjectDataSource(_cstring);
_dataSource.Database.Delete();
_dataSource.Database.CreateIfNotExists();
_transactionScope = new TransactionScope();
}
[TestMethod]
public void TestBasicOperations()
{
var item = _repository.AddItem(new Item(){Details = "Test Item"});
// AddItem makes a call through the data context to add a set and then calls datacontext.SaveChanges()
}
[TestCleanup]
public void TestCleanup()
{
// rollback
if (_transactionScope != null)
{
_transactionScope.Dispose();
}
}
然而,当我运行测试时,我收到以下错误:
结果消息:测试方法 Project.Repository.UnitTests.PocoTest.TestBasicOperations投掷 exception:System.Data.SqlClient.SqlException:CREATE DATABASE 多语句交易中不允许使用该语句。
ProjectDataSource在这里:
public class ProjectDataSource : DbContext, IProjectDataSource
{
public ProjectDataSource() : base("DefaultConnection")
{
}
public ProjectDataSource(string connectionString) : base(connectionString)
{
}
public DbSet<Set> Sets { get; set; }
}
存储库:
public class Repository : IRepository
{
private readonly ProjectDataSource _db = new ProjectDataSource();
public Item AddItem(Item item)
{
_db.Items.Add(item);
_db.SaveChanges();
return item;
}
}
为什么会这样?
此外 - 如果它有任何区别 - 如果我在TestMethod中注释掉AddItem行,则不会发生错误。
答案 0 :(得分:5)
您也可以使用08-Apr-2016 18:25:02.364 INFO [http-nio-8443-exec-2] org.apache.coyote.http11.AbstractHttp11Processor.process Error parsing HTTP request header
Note: further occurrences of HTTP header parsing errors will be logged at DEBUG level.
java.lang.ArrayIndexOutOfBoundsException: -64
答案 1 :(得分:3)
如果有其他人遇到此问题:
在我的Repository类中,我有另一个通常标记为“dbContext”的定义 - ProjectDataSource。这意味着在我的测试类中创建了一个上下文,而在我的Repository对象中创建了另一个上下文。将connectionstring发送到我的repo类解决了这个问题:
在存储库中:
public class Repository : IRepository
{
private readonly ProjectDataSource _db;
public Repository(string connectionString)
{
_db = new ProjectDataSource(connectionString);
}
public Repository()
{
_db = new ProjectDataSource();
}
从我的测试:
private TransactionScope _transactionScope;
private Repository _repository;
private ProjectDataSource _dataSource;
private const string _connectionString = "Data Source=.;Initial Catalog=test_db;Trusted_Connection=True";
[TestInitialize]
public virtual void TestInitialize()
{
_repository = new Repository(_connectionString);
_dataSource = new ProjectDataSource(_connectionString);
_dataSource.Database.Delete();
_dataSource.Database.CreateIfNotExists();
_transactionScope = new TransactionScope();
}
答案 2 :(得分:3)
有关您的信息,此错误是由设计发生的,只要在活动事务中向 Microsoft SQL Server 发出不可处理的命令,就会发生此错误。
因此,解决方案是授予 Database.CreateIfNotExists()从任何事务范围中击出数据库。请记住, SQL Profiler 是您的朋友。
您可以大致updated list of commands that are not allowed to run whithin transactions。
注意:如果我想知道为什么我提供基于Sybase产品的列表,请记住Microsoft SQL Server与Sybase的引擎共享其大部分基本遗传。如需进一步阅读,请参阅https://en.wikipedia.org/wiki/Microsoft_SQL_Server
答案 3 :(得分:1)
您不能对某些SQL命令使用隐式提交。 创建和删除数据库就是一个例子 SQL Server将执行 AUTOCommit
请参阅MS SQL帮助中的备注部分。 http://msdn.microsoft.com/en-us/library/ms176061.aspx
以及有关自动提交的更多信息...... http://msdn.microsoft.com/en-us/library/ms187878%28v=sql.105%29
答案 4 :(得分:1)
尝试此代码
使用(TransactionScope ts = new TransactionScope(TransactionScopeOption.Suppress))
{
var sqlCommand = String.Format(“ Create DATABASE [{0}]”,“ TempBackupDB”);
_context.Database.ExecuteSqlCommand(TransactionalBehavior.DoNotEnsureTransaction,sqlCommand);
ts.Complete();
}
答案 5 :(得分:-1)
您需要在包管理器控制台上运行 Update-Database 命令。