Skip to content

Instantly share code, notes, and snippets.

@ohaal
Last active August 25, 2023 14:17
Show Gist options
  • Save ohaal/3f11b27f35a9e65c3091b71176bbe900 to your computer and use it in GitHub Desktop.
Save ohaal/3f11b27f35a9e65c3091b71176bbe900 to your computer and use it in GitHub Desktop.
Sjekk om dato er norsk hellidag / arbeidsdag
/**
* Add X working days to a LocalDateTime
*
* @param startingDate
* @param workingDaysToAdd
* @return First working day after LocalDateTime with working days added
*/
public static LocalDateTime addWorkingDays(LocalDateTime startingDate, int workingDaysToAdd) {
int days = 0;
int workingDays = 0;
// Add days until we have added "workingDaysToAdd" amount of working days
while(Math.abs(workingDaysToAdd) > workingDays) {
if (!isNorwegianHoliday(startingDate.toLocalDate().plusDays(days)))
workingDays++;
if (workingDaysToAdd >= 0) days++;
else days--;
}
// Make sure we don't land on a Norwegian holiday, especially when workingdaysToAdd=0
while (isNorwegianHoliday(startingDate.toLocalDate().plusDays(days))) {
if (workingDaysToAdd >= 0) days++;
else days--;
}
LocalDateTime result = startingDate.plusDays(days);
return result;
}
/**
* Check if date is an official Norwegian holiday
* @param d Date to check
* @return
*/
public static boolean isNorwegianHoliday(LocalDate d) {
// Lørdager (inkl. Påskeaften)
if (DayOfWeek.SATURDAY.equals(d.getDayOfWeek())) return true;
// Søndager (inkl. Palmesøndag, 1. påskedag, 1. pinsedag)
if (DayOfWeek.SUNDAY.equals(d.getDayOfWeek())) return true;
// 01.01 Første nyttårsdag
if (d.getDayOfYear() == 1) return true;
// 01.05 Arbeidernes dag
if (d.getDayOfMonth() == 1 && Month.MAY.equals(d.getMonth())) return true;
// 17.05 Grunnlovsdag
if (d.getDayOfMonth() == 17 && Month.MAY.equals(d.getMonth())) return true;
// 25.12 1. juledag
if (d.getDayOfMonth() == 25 && Month.DECEMBER.equals(d.getMonth())) return true;
// 26.12 2. juledag
if (d.getDayOfMonth() == 26 && Month.DECEMBER.equals(d.getMonth())) return true;
LocalDate easterSunday = getEasterSunday(d.getYear());
// Skjærtorsdag
if (easterSunday.minusDays(3).equals(d)) return true;
// Langfredag
if (easterSunday.minusDays(2).equals(d)) return true;
// 2. påskedag
if (easterSunday.plusDays(1).equals(d)) return true;
// Kristi Himmelfartsdag
if (easterSunday.plusDays(39).equals(d)) return true;
// 2. pinsedag
if (easterSunday.plusDays(50).equals(d)) return true;
return false;
}
/**
* Algorithm for calculating the date of Easter Sunday (Meeus/Jones/Butcher Gregorian algorithm)
* Based on https://no.wikipedia.org/wiki/P%C3%A5skeformelen#Meeus/Jones/Butchers_formel_(bare_for_gregoriansk_kalender)
*
* @param year
* @return LocalDate of Easter Sunday in that year
*/
public static LocalDate getEasterSunday(int year) {
int Y = year;
int a = Y % 19;
int b = Y / 100;
int c = Y % 100;
int d = b / 4;
int e = b % 4;
int f = (b + 8) / 25;
int g = (b - f + 1) / 3;
int h = (19 * a + b - d - g + 15) % 30;
int i = c / 4;
int k = c % 4;
int L = (32 + 2 * e + 2 * i - h - k) % 7;
int m = (a + 11 * h + 22 * L) / 451;
int month = (h + L - 7 * m + 114) / 31;
int day = ((h + L - 7 * m + 114) % 31) + 1;
LocalDate ld = LocalDate.of(year, month, day);
return ld;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment