FINERACT-1971: Fix for infinite recursive loop in CalendarUtils when tenant and system TZ is different
This commit is contained in:
committed by
Arnold Gálovics
parent
9efe4f7ed5
commit
f681ee9ca5
+1
-1
@@ -61,7 +61,7 @@ public class ApplicationCurrency extends AbstractPersistableCustom {
|
||||
currency.displaySymbol);
|
||||
}
|
||||
|
||||
private ApplicationCurrency(final String code, final String name, final int decimalPlaces, final Integer inMultiplesOf,
|
||||
public ApplicationCurrency(final String code, final String name, final int decimalPlaces, final Integer inMultiplesOf,
|
||||
final String nameCode, final String displaySymbol) {
|
||||
this.code = code;
|
||||
this.name = name;
|
||||
|
||||
+2
-2
@@ -38,11 +38,11 @@ public class MoneyHelper {
|
||||
@Autowired
|
||||
private ConfigurationDomainService configurationDomainService;
|
||||
|
||||
@PostConstruct
|
||||
// This is a hack, but fixing this is not trivial, because some @Entity
|
||||
// domain classes use this helper
|
||||
@PostConstruct
|
||||
@SuppressFBWarnings("ST_WRITE_TO_STATIC_FROM_INSTANCE_METHOD")
|
||||
public void someFunction() {
|
||||
public void initialize() {
|
||||
staticConfigurationDomainService = configurationDomainService;
|
||||
}
|
||||
|
||||
|
||||
+6
-5
@@ -25,11 +25,12 @@ import lombok.Getter;
|
||||
@Getter
|
||||
public enum RepaymentRescheduleType {
|
||||
|
||||
INVALID(0, "RepaymentRescheduleType.invalid"), SAME_DAY(1, "RepaymentRescheduleType.same.day"), MOVE_TO_NEXT_WORKING_DAY(2,
|
||||
"RepaymentRescheduleType.move.to.next.working.day"), MOVE_TO_NEXT_REPAYMENT_MEETING_DAY(3,
|
||||
"RepaymentRescheduleType.move.to.next.repayment.meeting.day"), MOVE_TO_PREVIOUS_WORKING_DAY(4,
|
||||
"RepaymentRescheduleType.move.to.previous.working.day"), MOVE_TO_NEXT_MEETING_DAY(5,
|
||||
"RepaymentRescheduleType.move.to.next.meeting.day");
|
||||
INVALID(0, "RepaymentRescheduleType.invalid"), //
|
||||
SAME_DAY(1, "RepaymentRescheduleType.same.day"), //
|
||||
MOVE_TO_NEXT_WORKING_DAY(2, "RepaymentRescheduleType.move.to.next.working.day"), //
|
||||
MOVE_TO_NEXT_REPAYMENT_MEETING_DAY(3, "RepaymentRescheduleType.move.to.next.repayment.meeting.day"), //
|
||||
MOVE_TO_PREVIOUS_WORKING_DAY(4, "RepaymentRescheduleType.move.to.previous.working.day"), //
|
||||
MOVE_TO_NEXT_MEETING_DAY(5, "RepaymentRescheduleType.move.to.next.meeting.day"); //
|
||||
|
||||
private final Integer value;
|
||||
private final String code;
|
||||
|
||||
+1
-1
@@ -51,7 +51,7 @@ public class WorkingDays extends AbstractPersistableCustom {
|
||||
|
||||
}
|
||||
|
||||
protected WorkingDays(final String recurrence, final Integer repaymentReschedulingType, final Boolean extendTermForDailyRepayments,
|
||||
public WorkingDays(final String recurrence, final Integer repaymentReschedulingType, final Boolean extendTermForDailyRepayments,
|
||||
final Boolean extendTermForRepaymentsOnHolidays) {
|
||||
this.recurrence = recurrence;
|
||||
this.repaymentReschedulingType = repaymentReschedulingType;
|
||||
|
||||
+1
-1
@@ -33,7 +33,7 @@ public final class WorkingDaysUtil {
|
||||
public static LocalDate getOffSetDateIfNonWorkingDay(final LocalDate date, final LocalDate nextMeetingDate,
|
||||
final WorkingDays workingDays) {
|
||||
|
||||
// If date is not a non working day then return date.
|
||||
// If date is a working day then return date.
|
||||
if (isWorkingDay(workingDays, date)) {
|
||||
return date;
|
||||
}
|
||||
|
||||
+20
-14
@@ -32,6 +32,7 @@ import java.util.Collection;
|
||||
import java.util.Iterator;
|
||||
import java.util.List;
|
||||
import java.util.StringTokenizer;
|
||||
import lombok.extern.slf4j.Slf4j;
|
||||
import net.fortuna.ical4j.model.Date;
|
||||
import net.fortuna.ical4j.model.DateList;
|
||||
import net.fortuna.ical4j.model.DateTime;
|
||||
@@ -53,19 +54,18 @@ import org.apache.fineract.portfolio.calendar.domain.CalendarFrequencyType;
|
||||
import org.apache.fineract.portfolio.calendar.domain.CalendarWeekDaysType;
|
||||
import org.apache.fineract.portfolio.common.domain.NthDayType;
|
||||
import org.apache.fineract.portfolio.common.domain.PeriodFrequencyType;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
@Slf4j
|
||||
public final class CalendarUtils {
|
||||
|
||||
public static final String FLOATING_TIMEZONE_PROPERTY_KEY = "net.fortuna.ical4j.timezone.date.floating";
|
||||
|
||||
private CalendarUtils() {
|
||||
|
||||
}
|
||||
|
||||
private static final Logger LOG = LoggerFactory.getLogger(CalendarUtils.class);
|
||||
|
||||
static {
|
||||
System.setProperty("net.fortuna.ical4j.timezone.date.floating", "true");
|
||||
System.setProperty(FLOATING_TIMEZONE_PROPERTY_KEY, "true");
|
||||
}
|
||||
|
||||
public static LocalDateTime getNextRecurringDate(final String recurringRule, final LocalDateTime seedDate,
|
||||
@@ -119,7 +119,7 @@ public final class CalendarUtils {
|
||||
try {
|
||||
formattedDate = new Date(seedDateStr, DateUtils.DEFAULT_DATETIME_FORMAT);
|
||||
} catch (final ParseException e) {
|
||||
LOG.error("Invalid date: {}", seedDateStr, e);
|
||||
log.error("Invalid date: {}", seedDateStr, e);
|
||||
}
|
||||
return formattedDate;
|
||||
}
|
||||
@@ -170,15 +170,15 @@ public final class CalendarUtils {
|
||||
numberOfDays);
|
||||
}
|
||||
|
||||
private static Collection<LocalDate> convertToLocalDateList(final DateList dates, final LocalDate seedDate,
|
||||
static Collection<LocalDate> convertToLocalDateList(final DateList dates, final LocalDate seedDate,
|
||||
final PeriodFrequencyType frequencyType, boolean isSkippMeetingOnFirstDay, final Integer numberOfDays) {
|
||||
final Collection<LocalDate> recurringDates = new ArrayList<>();
|
||||
|
||||
for (@SuppressWarnings("rawtypes")
|
||||
final Iterator iterator = dates.iterator(); iterator.hasNext();) {
|
||||
final Date date = (Date) iterator.next();
|
||||
recurringDates.add((LocalDate) adjustDate(LocalDate.ofInstant(date.toInstant(), DateUtils.getDateTimeZoneOfTenant()), seedDate,
|
||||
frequencyType));
|
||||
for (final Date date : dates) {
|
||||
LocalDateTime dateTimeInProperTz = getLocalDateTimeFromICal4JDate(date);
|
||||
ZoneId tenantZoneId = DateUtils.getDateTimeZoneOfTenant();
|
||||
|
||||
recurringDates.add((LocalDate) adjustDate(dateTimeInProperTz.atZone(tenantZoneId).toLocalDate(), seedDate, frequencyType));
|
||||
}
|
||||
|
||||
if (isSkippMeetingOnFirstDay) {
|
||||
@@ -188,6 +188,12 @@ public final class CalendarUtils {
|
||||
return recurringDates;
|
||||
}
|
||||
|
||||
private static LocalDateTime getLocalDateTimeFromICal4JDate(Date date) {
|
||||
java.util.Calendar cal = java.util.Calendar.getInstance();
|
||||
cal.setTime(date);
|
||||
return LocalDateTime.ofInstant(cal.toInstant(), cal.getTimeZone().toZoneId());
|
||||
}
|
||||
|
||||
private static Collection<LocalDate> skipMeetingOnFirstdayOfMonth(final Collection<LocalDate> recurringDates,
|
||||
final Integer numberOfDays) {
|
||||
final Collection<LocalDate> adjustedRecurringDates = new ArrayList<>();
|
||||
@@ -220,10 +226,10 @@ public final class CalendarUtils {
|
||||
return recur;
|
||||
} catch (final ParseException e) {
|
||||
// TODO Auto-generated catch block
|
||||
LOG.error("Problem occurred in getICalRecur function", e);
|
||||
log.error("Problem occurred in getICalRecur function", e);
|
||||
} catch (final ValidationException e) {
|
||||
// TODO Auto-generated catch block
|
||||
LOG.error("Problem occurred in getICalRecur function", e);
|
||||
log.error("Problem occurred in getICalRecur function", e);
|
||||
}
|
||||
|
||||
return null;
|
||||
|
||||
Reference in New Issue
Block a user