diff --git a/src/main/java/com/primefactorsolutions/views/RequestEmployeeView.java b/src/main/java/com/primefactorsolutions/views/RequestEmployeeView.java index 26872a7..fc58d29 100644 --- a/src/main/java/com/primefactorsolutions/views/RequestEmployeeView.java +++ b/src/main/java/com/primefactorsolutions/views/RequestEmployeeView.java @@ -109,9 +109,11 @@ public class RequestEmployeeView extends Div implements HasUrlParameter .mapToDouble(TimeOffRequest::getAvailableDays) .sum(); double totalPersonalDays = requests.stream() - .filter(req -> !verificationIsHoliday(req)) // Solo los de tipo OTHER + .filter(req -> !verificationIsHoliday(req)) + .filter(req -> !req.getCategory().name().startsWith("VACATION")) .mapToDouble(TimeOffRequest::getAvailableDays) .sum(); + double totalAvailableDays = totalHoliday + totalVacations + totalPersonalDays; return new VerticalLayout( diff --git a/src/main/java/com/primefactorsolutions/views/RequestsListView.java b/src/main/java/com/primefactorsolutions/views/RequestsListView.java index 1694682..aa1de7e 100644 --- a/src/main/java/com/primefactorsolutions/views/RequestsListView.java +++ b/src/main/java/com/primefactorsolutions/views/RequestsListView.java @@ -17,6 +17,8 @@ import jakarta.annotation.security.PermitAll; import org.springframework.context.annotation.Scope; import org.vaadin.firitin.components.grid.PagingGrid; +import java.time.LocalDate; +import java.time.Period; import java.util.*; import java.util.stream.Collectors; @@ -160,31 +162,92 @@ public class RequestsListView extends Main { private String getGeneralTotal(final Employee employee) { List employeeRequests = requestService.findRequestsByEmployeeId(employee.getId()); List vacations = vacationService.findVacations(); - double totalUtilized = employeeRequests.stream() - .filter(Objects::nonNull) - .mapToDouble(request -> { - Double daysBalance = request.getAvailableDays(); - return daysBalance != null ? daysBalance : 0.0; - }) - .sum(); - double totalUnused = employeeRequests.stream() - .filter(Objects::nonNull) - .mapToDouble(request -> { - Double daysBalance = request.getDaysBalance(); - return daysBalance != null ? daysBalance : 0.0; - }) - .sum(); - double totalAvailable = vacations.stream() - .filter(Objects::nonNull) - .mapToDouble(request -> { - Double daysBalance = request.getDuration(); - return daysBalance != null ? daysBalance : 0.0; - }) - .sum(); - double generalTotal = (totalAvailable - totalUtilized) + totalUnused; + double totalUtilized = calculateTotalUtilized(employeeRequests); + double totalAvailable = calculateTotalAvailable(vacations, employeeRequests, employee); + double generalTotal = totalAvailable - totalUtilized; return String.valueOf(generalTotal); } + private Set getExcludedCategories() { + return Set.of( + TimeOffRequestType.MATERNITY, + TimeOffRequestType.PATERNITY, + TimeOffRequestType.MARRIAGE, + TimeOffRequestType.FATHERS_DAY, + TimeOffRequestType.MOTHERS_DAY + ); + } + + private Set getGenderSpecificExclusions() { + return Set.of( + TimeOffRequestType.INTERNATIONAL_WOMENS_DAY, + TimeOffRequestType.NATIONAL_WOMENS_DAY + ); + } + + private double calculateTotalUtilized(final List employeeRequests) { + return employeeRequests.stream() + .filter(Objects::nonNull) + .mapToDouble(request -> request.getDaysToBeTake() != null ? request.getDaysToBeTake() : 0.0) + .sum(); + } + + private double calculateTotalAvailable(final List vacations, final List employeeRequests, + final Employee employee) { + double vacationDays = calculateVacationDaysBasedOnService(employee.getDateOfEntry()); + Set excludedCategories = getExcludedCategories(); + Set genderSpecificExclusions = getGenderSpecificExclusions(); + Set employeeRequestCategories = employeeRequests.stream() + .map(TimeOffRequest::getCategory) + .collect(Collectors.toSet()); + + double availableVacationDays = vacations.stream() + .filter(Objects::nonNull) + .filter(vacation -> shouldIncludeVacation( + vacation, + excludedCategories, + genderSpecificExclusions, + employee, employeeRequestCategories + )) + .mapToDouble(vacation -> vacation.getDuration() != null ? vacation.getDuration() : 0.0) + .sum(); + + return vacationDays + availableVacationDays; + } + + private double calculateVacationDaysBasedOnService(final LocalDate dateOfEntry) { + int yearsOfService = dateOfEntry != null ? Period.between(dateOfEntry, LocalDate.now()).getYears() : 0; + if (yearsOfService < 1) { + return 0; + } + if (yearsOfService <= 5) { + return 15; + } + if (yearsOfService <= 10) { + return 20; + } + return 30; + } + + private boolean shouldIncludeVacation(final Vacation vacation, + final Set excludedCategories, + final Set genderSpecificExclusions, + final Employee employee, + final Set employeeRequestCategories) { + if (excludedCategories.contains(vacation.getCategory()) + && !employeeRequestCategories.contains(vacation.getCategory())) { + return false; + } + if (!isFemale(employee) && genderSpecificExclusions.contains(vacation.getCategory())) { + return false; + } + return true; + } + + private boolean isFemale(final Employee employee) { + return employee.getGender() == Employee.Gender.FEMALE; + } + private ComboBox createEmployeeFilter() { employeeFilter = new ComboBox<>("Employee"); List employees = new ArrayList<>(employeeService.findAllEmployees()); diff --git a/src/main/resources/data.sql b/src/main/resources/data.sql index 763b158..70f9e42 100644 --- a/src/main/resources/data.sql +++ b/src/main/resources/data.sql @@ -76,7 +76,7 @@ values ('9c6f12ba-e333-4e7a-b8a6-caa0982bd8c3', 1, '5c6f11fe-c341-4be7-a9a6-bba0 insert into time_off_request (id, version, employee_id, category, state, available_days, expiration, start_date, end_date, days_to_be_take, days_balance) values ('9d6f12ba-e444-4e7a-b8a6-caa0982bd8d4', 1, '5c6f11fe-c341-4be7-a9a6-bba0081ad7c6', 'GOOD_FRIDAY', 'COMPLETED', 1, '2024-03-29', '2024-03-29', '2024-03-29', 1, 0); insert into time_off_request (id, version, employee_id, category, state, available_days, expiration, start_date, end_date, days_to_be_take, days_balance) -values ('9e6f12ba-e555-4e7a-b8a6-caa0982bd8e5', 1, '5c6f11fe-c341-4be7-a9a6-bba0081ad7c6', 'VACATION_CURRENT_MANAGEMENT', 'APPROVED', 30, '2026-11-01', '2024-11-01', '2024-11-30', 30, 0); +values ('9e6f12ba-e555-4e7a-b8a6-caa0982bd8e5', 1, '5c6f11fe-c341-4be7-a9a6-bba0081ad7c6', 'VACATION_CURRENT_MANAGEMENT', 'IN_USE', 30, '2026-11-01', '2024-11-01', '2024-11-30', 30, 0); insert into time_off_request (id, version, employee_id, category, state, available_days, expiration, start_date, end_date, days_to_be_take, days_balance) values ('8c653f2a-f9a3-4d67-b3b6-12ad98fe0983', 1, 'f6ab3c6d-7078-45f6-9b22-4e37637bfec6', 'LABOR_DAY', 'REQUESTED', 1, '2025-05-01', '2024-05-01', '2024-05-01', 1, 0);