diff --git a/src/api/NetworkResurrector.Api.Application/CommandHandlers/CancelActionHandler.cs b/src/api/NetworkResurrector.Api.Application/CommandHandlers/CancelActionHandler.cs new file mode 100644 index 0000000..2263e09 --- /dev/null +++ b/src/api/NetworkResurrector.Api.Application/CommandHandlers/CancelActionHandler.cs @@ -0,0 +1,64 @@ +using MediatR; +using Microsoft.Extensions.Configuration; +using Microsoft.Extensions.Logging; +using NetworkResurrector.Agent.PublishedLanguage.Dto; +using NetworkResurrector.Agent.Wrapper.Services; +using NetworkResurrector.Api.Domain.Constants; +using NetworkResurrector.Api.Domain.Repositories; +using NetworkResurrector.Api.PublishedLanguage.Commands; +using NetworkResurrector.Api.PublishedLanguage.Events; +using System; +using System.Threading; +using System.Threading.Tasks; + +namespace NetworkResurrector.Api.Application.CommandHandlers +{ + public class CancelMachineHandler : IRequestHandler + { + private readonly ILogger _logger; + private readonly INetworkRepository _repository; + private readonly IResurrectorAgentService _resurrectorAgentService; + private readonly IConfiguration _configuration; + + public CancelMachineHandler(ILogger logger, INetworkRepository repository, IResurrectorAgentService resurrectorAgentService, IConfiguration configuration) + { + _logger=logger; + _repository=repository; + _resurrectorAgentService=resurrectorAgentService; + _configuration=configuration; + } + + public async Task Handle(CancelAction command, CancellationToken cancellationToken) + { + var powerConfiguration = await _repository.GetPowerActionConfiguration(command.MachineId, command.ActionId); + _logger.LogDebug($"Start canceling action '{powerConfiguration.PowerAction.PowerActionCode}' for machine {command.MachineId}"); + + var machine = await _repository.GetMachine(command.MachineId); + + //log activity + + var ipAddressOrMachineName = machine.IPv4Address ?? machine.MachineName; + ActionCanceled result; + + switch (powerConfiguration.Performer.PerformerCode) + { + case PowerActionPerformers.NETWORK_RESURRECTOR_AGENT: + if (machine.Agent == null) + throw new Exception($"Cannot use network resurrector agent as cancel performer for action '{powerConfiguration.PowerAction.PowerActionCode}' and machine '{ipAddressOrMachineName}' because it is not configured."); + + var owner = new ActionOwner(_configuration.GetValue("Service:Code")); + var cancelResultByAgent = await _resurrectorAgentService.Cancel(ipAddressOrMachineName, machine.Agent.AgentPort, owner); + var status = cancelResultByAgent.Success ? $"Action '{powerConfiguration.PowerAction.PowerActionCode}' successfully canceled for machine '{ipAddressOrMachineName}'." : $"Action '{powerConfiguration.PowerAction.PowerActionCode}' could not be canceled for machine '{ipAddressOrMachineName}'."; + result = new ActionCanceled(cancelResultByAgent.Success, status); + break; + + default: + throw new Exception($"Power action performer {powerConfiguration.Performer.PerformerCode} is not implemented."); + } + + _logger.LogDebug($"Action '{powerConfiguration.PowerAction.PowerActionCode}' cancellation finished for machine {command.MachineId}. Success: {result.Success}; Status: {result.Status}"); + + return result; + } + } +} \ No newline at end of file diff --git a/src/api/NetworkResurrector.Api.Application/CommandHandlers/LogoutUserHandler.cs b/src/api/NetworkResurrector.Api.Application/CommandHandlers/LogoutUserHandler.cs index 2a02fbc..40bf250 100644 --- a/src/api/NetworkResurrector.Api.Application/CommandHandlers/LogoutUserHandler.cs +++ b/src/api/NetworkResurrector.Api.Application/CommandHandlers/LogoutUserHandler.cs @@ -46,9 +46,9 @@ namespace NetworkResurrector.Api.Application.CommandHandlers throw new Exception($"Cannot use network resurrector agent as logout performer for machine '{ipAddressOrMachineName}' because it is not configured."); var owner = new ActionOwner(_configuration.GetValue("Service:Code")); - var LogoutResultByAgent = await _resurrectorAgentService.Logout(ipAddressOrMachineName, machine.Agent.AgentPort, owner); - var status = LogoutResultByAgent.Success ? $"The user from machine '{ipAddressOrMachineName}' was successfully logged out." : $"The user from machine '{ipAddressOrMachineName}' could not be logged out."; - result = new UserLoggedOut(LogoutResultByAgent.Success, status); + var logoutResultByAgent = await _resurrectorAgentService.Logout(ipAddressOrMachineName, machine.Agent.AgentPort, owner); + var status = logoutResultByAgent.Success ? $"The user from machine '{ipAddressOrMachineName}' was successfully logged out." : $"The user from machine '{ipAddressOrMachineName}' could not be logged out."; + result = new UserLoggedOut(logoutResultByAgent.Success, status); break; default: diff --git a/src/api/NetworkResurrector.Api.Domain.Data/Repositories/NetworkRepository.cs b/src/api/NetworkResurrector.Api.Domain.Data/Repositories/NetworkRepository.cs index ee77343..f211415 100644 --- a/src/api/NetworkResurrector.Api.Domain.Data/Repositories/NetworkRepository.cs +++ b/src/api/NetworkResurrector.Api.Domain.Data/Repositories/NetworkRepository.cs @@ -43,5 +43,18 @@ namespace NetworkResurrector.Api.Domain.Data.Repositories return config; } + + public async Task GetPowerActionConfiguration(int machineId, int actionId) + { + var config = await _dbContext.PowerActionConfigurations + .Include(z => z.PowerAction) + .Include(z => z.Performer) + .FirstOrDefaultAsync(z => z.MachineId == machineId && z.PowerActionId == actionId); + + if (config == null) + throw new Exception($"Action '{actionId}' is not configured for machine '{machineId}'."); + + return config; + } } } diff --git a/src/api/NetworkResurrector.Api.Domain/Repositories/INetworkRepository.cs b/src/api/NetworkResurrector.Api.Domain/Repositories/INetworkRepository.cs index 9d1c272..060c2fc 100644 --- a/src/api/NetworkResurrector.Api.Domain/Repositories/INetworkRepository.cs +++ b/src/api/NetworkResurrector.Api.Domain/Repositories/INetworkRepository.cs @@ -9,5 +9,6 @@ namespace NetworkResurrector.Api.Domain.Repositories Task GetMachines(); Task GetMachine(int machineId); Task GetPowerActionConfiguration(int machineId, string actionCode); + Task GetPowerActionConfiguration(int machineId, int actionId); } } diff --git a/src/api/NetworkResurrector.Api.PublishedLanguage/Commands/CancelAction.cs b/src/api/NetworkResurrector.Api.PublishedLanguage/Commands/CancelAction.cs new file mode 100644 index 0000000..69b3d99 --- /dev/null +++ b/src/api/NetworkResurrector.Api.PublishedLanguage/Commands/CancelAction.cs @@ -0,0 +1,11 @@ +using NDB.Application.DataContracts; +using NetworkResurrector.Api.PublishedLanguage.Events; + +namespace NetworkResurrector.Api.PublishedLanguage.Commands +{ + public class CancelAction : Command + { + public int MachineId { get; set; } + public int ActionId { get; set; } + } +} \ No newline at end of file diff --git a/src/api/NetworkResurrector.Api.PublishedLanguage/Events/ActionCanceled.cs b/src/api/NetworkResurrector.Api.PublishedLanguage/Events/ActionCanceled.cs new file mode 100644 index 0000000..51dd8da --- /dev/null +++ b/src/api/NetworkResurrector.Api.PublishedLanguage/Events/ActionCanceled.cs @@ -0,0 +1,4 @@ +namespace NetworkResurrector.Api.PublishedLanguage.Events +{ + public record ActionCanceled(bool Success, string Status); +} diff --git a/src/api/NetworkResurrector.Api/Controllers/ResurrectorController.cs b/src/api/NetworkResurrector.Api/Controllers/ResurrectorController.cs index a33bd33..46fe152 100644 --- a/src/api/NetworkResurrector.Api/Controllers/ResurrectorController.cs +++ b/src/api/NetworkResurrector.Api/Controllers/ResurrectorController.cs @@ -53,11 +53,25 @@ namespace NetworkResurrector.Api.Controllers return Ok(result); } + [HttpPost("logout")] + public async Task LogoutUser([FromBody] LogoutUser logoutUser) + { + var result = await _mediator.Send(logoutUser); + return Ok(result); + } + [HttpPost("lock")] public async Task LockMachine([FromBody] LockMachine lockMachine) { var result = await _mediator.Send(lockMachine); return Ok(result); } + + [HttpPost("cancel")] + public async Task CancelAction([FromBody] CancelAction cancelAction) + { + var result = await _mediator.Send(cancelAction); + return Ok(result); + } } }