/// <summary> /// Initializes a new instance of the <see cref="ServerRegistrationService"/> class. /// </summary> /// <param name="uowProvider">A UnitOfWork provider.</param> /// <param name="repositoryFactory">A repository factory.</param> /// <param name="logger">A logger.</param> /// <param name="eventMessagesFactory"></param> public ServerRegistrationService(IScopeUnitOfWorkProvider uowProvider, RepositoryFactory repositoryFactory, ILogger logger, IEventMessagesFactory eventMessagesFactory) : base(uowProvider, repositoryFactory, logger, eventMessagesFactory) { _lrepo = new LockingRepository <IServerRegistrationRepository>(UowProvider, x => RepositoryFactory.CreateServerRegistrationRepository(x), LockingRepositoryIds, LockingRepositoryIds); }
public void OuterScopeBadIsolationLevel() { var uowProvider = new PetaPocoUnitOfWorkProvider(Logger); var sqlSyntax = ApplicationContext.DatabaseContext.SqlSyntax; var lrepo = new LockingRepository <IServerRegistrationRepository>(uowProvider, x => CreateRepository(x, Logger, CacheHelper, sqlSyntax), new[] { Constants.Locks.Servers }, new[] { Constants.Locks.Servers }); // this creates a IsolationLevel.Unspecified scope using (var scope = ApplicationContext.ScopeProvider.CreateScope()) { // so outer scope creates IsolationLevel.ReadCommitted (default) transaction // then WithReadLocked creates a IsolationLevel.RepeatableRead scope, which // fails - levels conflict try { lrepo.WithReadLocked(xrepo => { xrepo.Repository.DeactiveStaleServers(TimeSpan.Zero); }); Assert.Fail("Expected: Exception."); } catch (Exception e) { Assert.AreEqual("Scope requires isolation level RepeatableRead, but got ReadCommitted from parent.", e.Message); } scope.Complete(); } }
public void NoOuterScopeJustWorks() { var uowProvider = new PetaPocoUnitOfWorkProvider(Logger); var sqlSyntax = ApplicationContext.DatabaseContext.SqlSyntax; var lrepo = new LockingRepository <IServerRegistrationRepository>(uowProvider, x => CreateRepository(x, Logger, CacheHelper, sqlSyntax), new[] { Constants.Locks.Servers }, new[] { Constants.Locks.Servers }); IServerRegistration reg = null; lrepo.WithWriteLocked(xrepo => { xrepo.Repository.AddOrUpdate(reg = new ServerRegistration("a1234", "i1234", DateTime.Now)); // no need - autocommit by default //xrepo.UnitOfWork.Commit(); }); Assert.IsNull(((ScopeProvider)ApplicationContext.ScopeProvider).AmbientScope); Assert.AreNotEqual(0, reg.Id); // that's cheating somehow because it will not really hit the DB because of the cache var reg2 = lrepo.WithReadLocked(xrepo => { return(xrepo.Repository.Get(reg.Id)); }); Assert.IsNull(((ScopeProvider)ApplicationContext.ScopeProvider).AmbientScope); Assert.IsNotNull(reg2); Assert.AreEqual("a1234", reg2.ServerAddress); Assert.AreEqual("i1234", reg2.ServerIdentity); // this really makes sure there's something in database using (var scope = ApplicationContext.ScopeProvider.CreateScope()) { var reg3 = scope.Database.Fetch <dynamic>("SELECT * FROM umbracoServer WHERE id=@id", new { id = reg2.Id }).FirstOrDefault(); Assert.IsNotNull(reg3); Assert.AreEqual("a1234", reg3.address); Assert.AreEqual("i1234", reg3.computerName); } Assert.IsNull(((ScopeProvider)ApplicationContext.ScopeProvider).AmbientScope); }
public void OuterScopeGoodIsolationLevel() { var uowProvider = new PetaPocoUnitOfWorkProvider(Logger); var sqlSyntax = ApplicationContext.DatabaseContext.SqlSyntax; var lrepo = new LockingRepository <IServerRegistrationRepository>(uowProvider, x => CreateRepository(x, Logger, CacheHelper, sqlSyntax), new[] { Constants.Locks.Servers }, new[] { Constants.Locks.Servers }); // this creates a IsolationLevel.RepeatableRead scope using (var scope = ApplicationContext.ScopeProvider.CreateScope(IsolationLevel.RepeatableRead)) { // so outer scope creates IsolationLevel.RepeatableRead transaction // then WithReadLocked creates a IsolationLevel.RepeatableRead scope, which // suceeds - no level conflict lrepo.WithReadLocked(xrepo => { xrepo.Repository.DeactiveStaleServers(TimeSpan.Zero); }); scope.Complete(); } }