private bool TryStartCriticalSection() { if (_started) { throw new ExecutionException("There is already an active critical section"); } _started = true; var startRequest = new StartCriticalSectionRequest(new TaskId(_taskExecutionInstance.ApplicationName, _taskExecutionInstance.TaskName), _taskExecutionInstance.TaskExecutionId, _taskExecutionOptions.TaskDeathMode, _criticalSectionType); if (_taskExecutionOptions.TaskDeathMode == TaskDeathMode.Override) { startRequest.OverrideThreshold = _taskExecutionOptions.OverrideThreshold.Value; } if (_taskExecutionOptions.TaskDeathMode == TaskDeathMode.KeepAlive) { startRequest.KeepAliveDeathThreshold = _taskExecutionOptions.KeepAliveDeathThreshold.Value; } var response = _criticalSectionRepository.Start(startRequest); if (response.GrantStatus == GrantStatus.Denied) { _started = false; return(false); } return(true); }
public void If_OverrideMode_TokenNotAvailableAndNothingInQueue_ThenAddToQueueAndDeny() { // ARRANGE var executionHelper = new ExecutionsHelper(); var taskDefinitionId = executionHelper.InsertTask(TestConstants.ApplicationName, TestConstants.TaskName); executionHelper.InsertUnlimitedExecutionToken(taskDefinitionId); // Create execution 1 and assign critical section to it var taskExecutionId1 = executionHelper.InsertOverrideTaskExecution(taskDefinitionId); executionHelper.InsertUnavailableCriticalSectionToken(taskDefinitionId, taskExecutionId1); // Create second execution var taskExecutionId2 = executionHelper.InsertOverrideTaskExecution(taskDefinitionId); var request = new StartCriticalSectionRequest(new TaskId(TestConstants.ApplicationName, TestConstants.TaskName), taskExecutionId2, TaskDeathMode.Override, CriticalSectionType.User); request.OverrideThreshold = new TimeSpan(0, 1, 0); // ACT var sut = CreateSut(); var response = sut.Start(request); // ASSERT var isInQueue = executionHelper.GetQueueCount(taskExecutionId2) == 1; Assert.AreEqual(true, isInQueue); Assert.AreEqual(GrantStatus.Denied, response.GrantStatus); }
public void If_OverrideMode_TokenAvailableAndIsFirstInQueue_ThenRemoveFromQueueAndGrant() { // ARRANGE var executionHelper = new ExecutionsHelper(); var taskDefinitionId = executionHelper.InsertTask(TestConstants.ApplicationName, TestConstants.TaskName); executionHelper.InsertUnlimitedExecutionToken(taskDefinitionId); // Create execution 1 and create available critical section token var taskExecutionId1 = executionHelper.InsertOverrideTaskExecution(taskDefinitionId); executionHelper.InsertIntoCriticalSectionQueue(taskDefinitionId, 1, taskExecutionId1); executionHelper.InsertAvailableCriticalSectionToken(taskDefinitionId, "0"); var request = new StartCriticalSectionRequest(new TaskId(TestConstants.ApplicationName, TestConstants.TaskName), taskExecutionId1, TaskDeathMode.Override, CriticalSectionType.User); request.OverrideThreshold = new TimeSpan(0, 1, 0); // ACT var sut = CreateSut(); var response = sut.Start(request); // ASSERT var numberOfQueueRecords = executionHelper.GetQueueCount(taskExecutionId1); Assert.AreEqual(0, numberOfQueueRecords); Assert.AreEqual(GrantStatus.Granted, response.GrantStatus); }
public void If_KeepAliveMode_TokenNotAvailableAndAlreadyInQueue_ThenDoNotAddToQueueAndDeny() { // ARRANGE var executionHelper = new ExecutionsHelper(); var taskDefinitionId = executionHelper.InsertTask(TestConstants.ApplicationName, TestConstants.TaskName); executionHelper.InsertUnlimitedExecutionToken(taskDefinitionId); // Create execution 1 and assign critical section to it var taskExecutionId1 = executionHelper.InsertKeepAliveTaskExecution(taskDefinitionId); executionHelper.InsertUnavailableCriticalSectionToken(taskDefinitionId, taskExecutionId1); // Create second execution and insert into queue var taskExecutionId2 = executionHelper.InsertKeepAliveTaskExecution(taskDefinitionId); executionHelper.InsertIntoCriticalSectionQueue(taskDefinitionId, 1, taskExecutionId2); var request = new StartCriticalSectionRequest(new TaskId(TestConstants.ApplicationName, TestConstants.TaskName), taskExecutionId2, TaskDeathMode.KeepAlive, CriticalSectionType.User); request.KeepAliveDeathThreshold = new TimeSpan(0, 10, 0); // ACT var sut = CreateSut(); var response = sut.Start(request); // ASSERT var numberOfQueueRecords = executionHelper.GetQueueCount(taskExecutionId2); Assert.AreEqual(1, numberOfQueueRecords); Assert.AreEqual(GrantStatus.Denied, response.GrantStatus); }
public StartCriticalSectionResponse Start(StartCriticalSectionRequest startRequest) { ValidateStartRequest(startRequest); var taskDefinition = _taskRepository.EnsureTaskDefinition(startRequest.TaskId); var granted = TryAcquireCriticalSection(startRequest.TaskId, taskDefinition.TaskDefinitionId, startRequest.TaskExecutionId, startRequest.Type); return(new StartCriticalSectionResponse() { GrantStatus = granted ? GrantStatus.Granted : GrantStatus.Denied }); }
public async Task <StartCriticalSectionResponse> StartAsync(StartCriticalSectionRequest startRequest) { ValidateStartRequest(startRequest); var taskDefinition = await _taskRepository.EnsureTaskDefinitionAsync(startRequest.TaskId).ConfigureAwait(false); var granted = await TryAcquireCriticalSectionAsync(startRequest.TaskId, taskDefinition.TaskDefinitionId, startRequest.TaskExecutionId, startRequest.Type).ConfigureAwait(false); return(new StartCriticalSectionResponse() { GrantStatus = granted ? GrantStatus.Granted : GrantStatus.Denied }); }
private void ValidateStartRequest(StartCriticalSectionRequest startRequest) { if (startRequest.TaskDeathMode == TaskDeathMode.KeepAlive) { if (!startRequest.KeepAliveDeathThreshold.HasValue) { throw new ExecutionArgumentsException("KeepAliveDeathThreshold must be set when using KeepAlive mode"); } } else if (startRequest.TaskDeathMode == TaskDeathMode.Override) { if (!startRequest.OverrideThreshold.HasValue) { throw new ExecutionArgumentsException("OverrideThreshold must be set when using Override mode"); } } }
public void If_KeepAliveMode_TokenAvailableAndIsNotFirstInQueueButFirstHasExpiredTimeout_ThenRemoveBothFromQueueAndGrant() { // ARRANGE var executionHelper = new ExecutionsHelper(); var taskDefinitionId = executionHelper.InsertTask(TestConstants.ApplicationName, TestConstants.TaskName); var keepAliveThreshold = new TimeSpan(0, 0, 5); // Create execution 1 and add it to the queue var taskExecutionId1 = executionHelper.InsertKeepAliveTaskExecution(taskDefinitionId, new TimeSpan(0, 0, 1), keepAliveThreshold); executionHelper.InsertUnlimitedExecutionToken(taskDefinitionId); executionHelper.SetKeepAlive(taskExecutionId1); executionHelper.InsertIntoCriticalSectionQueue(taskDefinitionId, 1, taskExecutionId1); Thread.Sleep(6000); // Create execution 2 and add it to the queue var taskExecutionId2 = executionHelper.InsertKeepAliveTaskExecution(taskDefinitionId); executionHelper.SetKeepAlive(taskExecutionId2); executionHelper.InsertIntoCriticalSectionQueue(taskDefinitionId, 2, taskExecutionId2); // Create an available critical section token executionHelper.InsertAvailableCriticalSectionToken(taskDefinitionId, "0"); var request = new StartCriticalSectionRequest(new TaskId(TestConstants.ApplicationName, TestConstants.TaskName), taskExecutionId2, TaskDeathMode.KeepAlive, CriticalSectionType.User); request.KeepAliveDeathThreshold = keepAliveThreshold; // ACT var sut = CreateSut(); var response = sut.Start(request); // ASSERT var numberOfQueueRecordsForExecution1 = executionHelper.GetQueueCount(taskExecutionId1); var numberOfQueueRecordsForExecution2 = executionHelper.GetQueueCount(taskExecutionId2); Assert.AreEqual(0, numberOfQueueRecordsForExecution1); Assert.AreEqual(0, numberOfQueueRecordsForExecution2); Assert.AreEqual(GrantStatus.Granted, response.GrantStatus); }
public async Task If_OverrideMode_TokenAvailableAndIsNotFirstInQueueButFirstHasCompleted_ThenRemoveBothFromQueueAndGrant() { // ARRANGE var executionHelper = new ExecutionsHelper(); var taskDefinitionId = executionHelper.InsertTask(TestConstants.ApplicationName, TestConstants.TaskName); executionHelper.InsertUnlimitedExecutionToken(taskDefinitionId); // Create execution 1 and add it to the queue var taskExecutionId1 = executionHelper.InsertOverrideTaskExecution(taskDefinitionId); executionHelper.InsertIntoCriticalSectionQueue(taskDefinitionId, 1, taskExecutionId1); executionHelper.SetTaskExecutionAsCompleted(taskExecutionId1); // Create execution 2 and add it to the queue var taskExecutionId2 = executionHelper.InsertOverrideTaskExecution(taskDefinitionId); executionHelper.InsertIntoCriticalSectionQueue(taskDefinitionId, 2, taskExecutionId2); // Create an available critical section token executionHelper.InsertAvailableCriticalSectionToken(taskDefinitionId, "0"); var request = new StartCriticalSectionRequest(new TaskId(TestConstants.ApplicationName, TestConstants.TaskName), taskExecutionId2, TaskDeathMode.Override, CriticalSectionType.User); request.OverrideThreshold = new TimeSpan(0, 30, 0); // ACT var sut = CreateSut(); var response = await sut.StartAsync(request); // ASSERT var numberOfQueueRecordsForExecution1 = executionHelper.GetQueueCount(taskExecutionId1); var numberOfQueueRecordsForExecution2 = executionHelper.GetQueueCount(taskExecutionId2); Assert.Equal(0, numberOfQueueRecordsForExecution1); Assert.Equal(0, numberOfQueueRecordsForExecution2); Assert.Equal(GrantStatus.Granted, response.GrantStatus); }
public async Task If_KeepAliveMode_TokenAvailableAndIsNotFirstInQueue_ThenDoNotChangeQueueAndDeny() { // ARRANGE var executionHelper = new ExecutionsHelper(); var taskDefinitionId = executionHelper.InsertTask(TestConstants.ApplicationName, TestConstants.TaskName); executionHelper.InsertUnlimitedExecutionToken(taskDefinitionId); // Create execution 1 and add it to the queue var taskExecutionId1 = executionHelper.InsertKeepAliveTaskExecution(taskDefinitionId); executionHelper.InsertIntoCriticalSectionQueue(taskDefinitionId, 1, taskExecutionId1); // Create execution 2 and add it to the queue var taskExecutionId2 = executionHelper.InsertKeepAliveTaskExecution(taskDefinitionId); executionHelper.InsertIntoCriticalSectionQueue(taskDefinitionId, 2, taskExecutionId2); // Create an available critical section token executionHelper.InsertAvailableCriticalSectionToken(taskDefinitionId, "0"); var request = new StartCriticalSectionRequest(new TaskId(TestConstants.ApplicationName, TestConstants.TaskName), taskExecutionId2, TaskDeathMode.KeepAlive, CriticalSectionType.User); request.KeepAliveDeathThreshold = new TimeSpan(0, 1, 0); // ACT var sut = CreateSut(); var response = await sut.StartAsync(request); // ASSERT var numberOfQueueRecords = executionHelper.GetQueueCount(taskExecutionId2); Assert.Equal(1, numberOfQueueRecords); Assert.Equal(GrantStatus.Denied, response.GrantStatus); }
public void If_OverrideMode_TokenAvailableAndNothingInQueue_ThenGrant() { // ARRANGE var executionHelper = new ExecutionsHelper(); var taskDefinitionId = executionHelper.InsertTask(TestConstants.ApplicationName, TestConstants.TaskName); var taskExecutionId = executionHelper.InsertOverrideTaskExecution(taskDefinitionId); executionHelper.InsertUnlimitedExecutionToken(taskDefinitionId); var request = new StartCriticalSectionRequest(new TaskId(TestConstants.ApplicationName, TestConstants.TaskName), taskExecutionId, TaskDeathMode.Override, CriticalSectionType.User); request.OverrideThreshold = new TimeSpan(0, 1, 0); // ACT var sut = CreateSut(); var response = sut.Start(request); // ASSERT Assert.AreEqual(GrantStatus.Granted, response.GrantStatus); }