swedish-salary-day
Version:
Calculate the next or previous salary payout date according to configured rules.
89 lines (70 loc) • 2.17 kB
text/typescript
import { isHoliday as isHolidaySweden } from 'se-bank-holidays';
export interface Config {
dayOfMonth: number;
isHoliday?: (date: Date) => boolean;
resolveSaturday?: 'previous-work-day' | 'next-work-day';
resolveSunday?: 'previous-work-day' | 'next-work-day';
}
const defaultConfig: Config = {
dayOfMonth: 25,
resolveSaturday: 'previous-work-day',
resolveSunday: 'previous-work-day',
isHoliday: isHolidaySweden,
};
export function nextSalaryDay(referenceDate: Date | number, config: Config = defaultConfig): Date {
if (typeof referenceDate === 'number') {
// eslint-disable-next-line no-param-reassign
referenceDate = new Date(referenceDate);
}
let salaryDay = new Date(
referenceDate.getFullYear(),
referenceDate.getMonth(),
config.dayOfMonth + 1,
);
salaryDay.setUTCMinutes(0);
salaryDay.setUTCHours(0);
if (referenceDate > salaryDay) {
salaryDay.setMonth(salaryDay.getMonth() + 1);
salaryDay.setUTCMinutes(0);
salaryDay.setUTCHours(0);
}
salaryDay = setSalaryDay(salaryDay, config);
return salaryDay;
}
export function previousSalaryDay(referenceDate: Date | number, config: Config = defaultConfig) {
if (typeof referenceDate === 'number') {
// eslint-disable-next-line no-param-reassign
referenceDate = new Date(referenceDate);
}
let salaryDay = new Date(
referenceDate.getFullYear(),
referenceDate.getMonth(),
config.dayOfMonth + 1,
);
salaryDay.setUTCMinutes(0);
salaryDay.setUTCHours(0);
if (referenceDate < salaryDay) {
salaryDay.setMonth(salaryDay.getMonth() - 1);
salaryDay.setUTCMinutes(0);
salaryDay.setUTCHours(0);
}
salaryDay = setSalaryDay(salaryDay, config);
return salaryDay;
}
const SATURDAY = 6;
const SUNDAY = 0;
function setSalaryDay(date: Date, config: Config) {
const dayOfWeek = date.getDay();
if (dayOfWeek === SATURDAY) {
date.setDate(date.getDate() + (config.resolveSaturday === 'previous-work-day' ? -1 : 2));
}
if (dayOfWeek === SUNDAY) {
date.setDate(date.getDate() + (config.resolveSunday === 'previous-work-day' ? -2 : 1));
}
if (config.isHoliday) {
while (config.isHoliday(date)) {
date.setDate(date.getDate() - 1);
}
}
return date;
}