我有兩個控制器測試用例。我想確保每個測試用例都在接收一個唯一的Session實例,以模擬InstancePerWebApiRequest。我當前的實現有缺陷,因爲它在多個測試用例中與單個ISession實例一起工作。但是,如果我在一個測試用例後處理範圍,那麼即使我已經重新請求Autofac提供了一個新的測試用例,我仍然被告知我的會話已關閉。爲測試用例內的InstancePerApiRequest生成一個ISession
下面是我得到了什麼:
public class AutofacRegistrations
{
public static void RegisterAndSetResolver()
{
var containerBuilder = new ContainerBuilder();
containerBuilder.RegisterApiControllers(Assembly.GetExecutingAssembly());
// Per Design Patterns: Elements of Reusable Object-Oriented Software - an abstract factory is often used as a singleton.
containerBuilder.Register(x => new NHibernateConfiguration().Configure().BuildSessionFactory()).SingleInstance();
containerBuilder.RegisterType<NHibernateDaoFactory>().As<IDaoFactory>().SingleInstance();
containerBuilder.RegisterType<StreamusManagerFactory>().As<IManagerFactory>().SingleInstance();
// Everything else wants an instance of Session per API request, so indicate that:
containerBuilder.Register(x => x.Resolve<ISessionFactory>().OpenSession()).InstancePerApiRequest();
containerBuilder.Register(x => LogManager.GetLogger(MethodBase.GetCurrentMethod().DeclaringType)).InstancePerApiRequest();
ILifetimeScope container = containerBuilder.Build();
var dependencyResolver = new AutofacWebApiDependencyResolver(container);
GlobalConfiguration.Configuration.DependencyResolver = dependencyResolver;
}
}
下面我宣佈我的工廠爲單身人士和指示,我想每個API請求一個ISession。
這裏是我的設置我的測試方法如下:
public abstract class StreamusTest
{
protected ILog Logger;
protected IDaoFactory DaoFactory;
protected IManagerFactory ManagerFactory;
protected Helpers Helpers;
protected ISession Session;
private IDependencyScope Scope;
[TestFixtureSetUp]
public void TestFixtureSetUp()
{
StreamusWebApi.InitializeApplication();
// TODO: I feel like this is incorrect because Session is only generated once. Shouldn't it be SessionPerTestCase?
Scope = GlobalConfiguration.Configuration.DependencyResolver.BeginScope();
Logger = (ILog)Scope.GetService(typeof(ILog));
DaoFactory = (IDaoFactory)Scope.GetService(typeof(IDaoFactory));
ManagerFactory = (IManagerFactory)Scope.GetService(typeof(IManagerFactory));
Session = (ISession)Scope.GetService(typeof(ISession));
Helpers = new Helpers(Logger, Session, ManagerFactory);
}
[SetUp]
public void SetUp()
{
// TODO: I think I want to be generating a Scope per SetUp and dispose of it in TearDown.
// Scope = GlobalConfiguration.Configuration.DependencyResolver.BeginScope();
// Logger = (ILog)Scope.GetService(typeof(ILog));
// Session = (ISession)Scope.GetService(typeof(ISession));
}
[TearDown]
public void TearDown()
{
// Scope.Dispose();
}
[TestFixtureTearDown]
public void TestFixtureTearDown()
{
Scope.Dispose();
}
}
我覺得這是不正確,因爲我只在TestFixtureSetup實例我曾經範圍。如果我在每個測試用例(在TearDown中)後處理我的作用域,那麼我的第二個測試用例會拋出一個異常,指出Session已關閉。
我相信我的當前實現在我的所有測試用例中使用單個Session,這是不正確的。任何人都可以提供一些關於如何正確設置的建議?
這裏是我的實際測試的情況下,以供參考:
[TestFixture]
public class ClientErrorControllerTest : StreamusTest
{
private ClientErrorController ClientErrorController;
[SetUp]
public new void TestFixtureSetUp()
{
ClientErrorController = new ClientErrorController(Logger, Session, ManagerFactory);
}
[Test]
public void CreateError_ShortMessage_ErrorCreated()
{
var clientErrorDto = new ClientErrorDto
{
Message = "Hello World",
ClientVersion = "0.99",
LineNumber = 2
};
ClientErrorDto createdErrorDto = ClientErrorController.Create(clientErrorDto);
Assert.NotNull(createdErrorDto);
}
[Test]
public void CreateError_LongMessage_MessageTruncatedErrorCreated()
{
var clientErrorDto = new ClientErrorDto
{
Message =
"Hello World This is a Really Long Message Which is going to be over 255 characters in length when finished which will cause the end result message to be truncated with three periods as to not overflow the database. Can I confirm that this is happening? Thanks",
ClientVersion = "0.99",
LineNumber = 2
};
ClientErrorDto createdErrorDto = ClientErrorController.Create(clientErrorDto);
Assert.NotNull(createdErrorDto);
Assert.That(createdErrorDto.Message.Length == 255);
}
}