using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Authentication.JwtBearer; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc; using Microsoft.FeatureManagement.Mvc; using LCU.API.Internal.Operations.IncentiveApi.Configuration; using LCU.API.Internal.Operations.IncentiveApi.Extensions; using LCU.API.Internal.Operations.IncentiveApiLib.Services; using LCU.API.Internal.Operations.IncentiveApiLib.Persistence; using LCU.Library.Internal.IncentiveApiModels.Requests; using LCU.Library.Internal.IncentiveApiModels.Common; using LCU.API.Internal.Operations.IncentiveApi.Models.DataTransfer; using LCU.API.Internal.Operations.IncentiveApi.Models.Dayforce; using LCU.API.Internal.Operations.IncentiveApi.Authorization; using LCU.API.Internal.Operations.IncentiveApi.Exceptions; using LCU.API.Internal.Operations.IncentiveApi.Services.Dayforce; namespace LCU.API.Internal.Operations.IncentiveApi.Controllers; [FeatureGate(FeatureFlags.EnableControllers)] [Authorize(AuthenticationSchemes = JwtBearerDefaults.AuthenticationScheme)] [ApiController] [Route("api/[controller]")] public class EmployeeController : ControllerBase { private readonly ICurrentUserService _currentUserService; private readonly IDayForceSyncService _dayForceSyncService; private readonly IUserService _userService; public EmployeeController( ICurrentUserService currentUserService, IDayForceSyncService dayForceSyncService, IUserService userService ) { _currentUserService = currentUserService; _dayForceSyncService = dayForceSyncService; _userService = userService; } [HttpGet("")] public async Task GetAllUsers([FromQuery] string query, [FromQuery] string role) { try { var searchRequest = new UserSearchRequest { Query = query, Role = role }; var result = await _userService.GetAllUsersAsync(searchRequest); return Ok(result); } catch (Exception ex) { Log.Error(ex, $"Failure in {GetType().Name}"); return StatusCode(StatusCodes.Status500InternalServerError); } } [HttpGet("terminated")] [RequirePermission("GENERATE_PAYOUT_FILES")] public IActionResult GetTerminatedUsers([FromQuery] int month, [FromQuery] int year) { try { var monthRange = new MonthRange(year, month); var result = _userService.GetTerminatedUsersAsync(monthRange); return Ok(result); } catch (ArgumentException ex) { Log.Error(ex, $"Bad Request in {GetType().Name}"); return BadRequest(ex.Message); } catch (Exception ex) { Log.Error(ex, $"Failure in {GetType().Name}"); return StatusCode(StatusCodes.Status500InternalServerError); } } [HttpGet("resolve")] public async Task ResolveUser( [FromQuery] string employeeId = null, [FromQuery] string email = null ) { try { var count = 0; if (!string.IsNullOrWhiteSpace(employeeId)) { count++; } if (!string.IsNullOrWhiteSpace(email)) { count++; } if (count > 1) { return BadRequest("Please provide only one query argument."); } var result = await _userService.FindUserAsync(employeeId, email); return Ok(result); } catch (Exception ex) { Log.Error(ex, $"Failure in {GetType().Name}"); return StatusCode(StatusCodes.Status500InternalServerError); } } [HttpGet("me")] public async Task GetCurrentEmployee() { try { var currentUser = _currentUserService.GetCurrentUser(); if (currentUser?.Email == null) { Log.Warning("Failed To Get Current User From Auth Context"); return Unauthorized("No AD User Found."); } var result = await _userService.GetUserByAdEmailAsync(currentUser.Email); if (result == null) { Log.Warning($"Failed To Get Current User From Email: {currentUser.Email}"); return NoContent(); } return Ok(result); } catch (Exception ex) { Log.Error(ex, $"Failure in {GetType().Name}"); return StatusCode(StatusCodes.Status500InternalServerError); } } [HttpGet("{employeeId}")] [RequirePermission("ASSIGN_PERMISSIONS_TO_ASSOCIATES,ASSIGN_ASSOCIATES_TO_DEPARTMENT")] public async Task GetEmployeeById(string employeeId = null) { try { if (employeeId == null) { return BadRequest("no_employee_id"); } var result = await _userService.GetUserByEmployeeIdAsync(employeeId); if (result == null) { return NoContent(); } return Ok(result); } catch (Exception ex) { Log.Error(ex, $"Failure in {GetType().Name}"); return StatusCode(StatusCodes.Status500InternalServerError); } } [RequirePermission("ASSIGN_ASSOCIATES_TO_DEPARTMENT")] [HttpPost("{employeeId}/AssignDept", Name = "AssignDept")] public async Task AssignDepartment( string employeeId, [FromBody] DepartmentAssignmentRequest assignment ) { if (!ModelState.IsValid) { return BadRequest(ModelState.GetErrorMessages()); } try { var currentUser = _currentUserService.GetCurrentUser(); if (currentUser?.Email == null) { return Unauthorized("No AD User Found."); } var employee = await _userService.GetUserByAdEmailAsync(currentUser.Email); if (UserService.ValidateChangePermission(employee.EmployeeId, employeeId)) { return StatusCode(403, "Not allowed to assign yourself to a department."); } await _userService.AssignDepartments(employeeId, assignment); return (Ok()); } catch (NotFoundException ex) { return NotFound(ex.Message); } catch (BadDepartmentAssignmentException ex) { return BadRequest(ex.Message); } catch (Exception ex) { Log.Error(ex, $"Failure in {GetType().Name}"); return StatusCode(StatusCodes.Status500InternalServerError); } } [HttpPut("{employeeId}/UpdatePerms", Name = "UpdatePerms")] public async Task AssignPermission( string employeeId, [FromBody] AdditionalPermissionRequest request ) { if (!ModelState.IsValid) { return BadRequest(ModelState.GetErrorMessages()); } try { var response = await _userService.UpdatePermissions(employeeId, request); return Ok(response); } catch (NotFoundException ex) { return NotFound(ex.Message); } catch (Exception ex) { Log.Error(ex, $"Failure in {GetType().Name}"); return StatusCode(StatusCodes.Status500InternalServerError); } } [RequirePermission("ASSIGN_ASSOCIATES_TO_DEPARTMENT")] [HttpPost("{employeeId}/UpdateDept/{assignmentId:int}", Name = "UpdateDept")] public async Task UpdateDepartmentAssignment( string employeeId, int assignmentId, [FromBody] DepartmentUpdateRequest request ) { try { var currentUser = _currentUserService.GetCurrentUser(); if (currentUser?.Email == null) { return Unauthorized("No AD User Found."); } var employee = await _userService.GetUserByAdEmailAsync(currentUser.Email); if (UserService.ValidateChangePermission(employee.EmployeeId, employeeId)) { return StatusCode(403, "Not allowed to terminate yourself from a department."); } await _userService.UpdateDepartmentAssignment(request); return (Ok()); } catch (NotFoundException ex) { return NotFound(ex.Message); } catch (BadDepartmentAssignmentException ex) { return BadRequest(ex.Message); } catch (Exception ex) { Log.Error(ex, $"Failure in {GetType().Name}"); return StatusCode(StatusCodes.Status500InternalServerError); } } [HttpGet("GetHcmSystemUsers")] [RequirePermission("MANAGE_EMPLOYEE_DETAILS")] public async Task GetHcmSystemUsers(string email = "", string employeeId = "", string fullName = "") { try { var result = await _dayForceSyncService.GetMatchingHcmUsers(email, employeeId, fullName); return Ok(result); } catch (Exception ex) { Log.Error(ex, $"Failure in {GetType().Name}"); return StatusCode(StatusCodes.Status500InternalServerError); } } [HttpPost("UpdateEmployeeDetails", Name = "UpdateEmployeeDetails")] [RequirePermission("MANAGE_EMPLOYEE_DETAILS")] public async Task UpdateEmployeeDetails([FromBody] EmployeeDetailsUpdate request) { try { var currentUser = _currentUserService.GetCurrentUser(); if (currentUser?.Email == null) { return Unauthorized("No AD User Found."); } var result = await _userService.GetUserByAdEmailAsync(request.OldEmail); if (result == null) { return NoContent(); } var updatedUserResult = await _dayForceSyncService.UpdateEmployeeDetails(request); if (updatedUserResult.UpdatedSuccessfully) { return Ok(updatedUserResult); } return BadRequest(updatedUserResult); } catch (Exception ex) { Log.Error(ex, $"Failure in {GetType().Name}"); return StatusCode(StatusCodes.Status500InternalServerError); } } [HttpGet("SyncEmployeeIds")] [RequirePermission("MANAGE_EMPLOYEE_DETAILS")] public async Task SyncEmployeeIds() { try { var result = await _userService.SyncActiveUserIds(); return Ok(result); } catch (Exception ex) { Log.Error(ex, $"Failure in {GetType().Name}"); return StatusCode(StatusCodes.Status500InternalServerError); } } [HttpPost("sync", Name = "ForceRefresh")] public async Task SyncDayForce() { try { Log.Information("DayForce Sync was forced"); var request = new DayforceProcessRequest(); await _dayForceSyncService.SyncDayForceUsers(request); Log.Information("DayForce forced Sync has completed"); return Ok(); } catch (Exception ex) { Log.Information("DayForce forced Sync has failed"); Log.Error(ex, $"Failure in {GetType().Name}"); return StatusCode(StatusCodes.Status500InternalServerError); } } }