88 lines
2.8 KiB
TypeScript
88 lines
2.8 KiB
TypeScript
import type { ValueObject } from '@core/shared/domain/ValueObject';
|
|
import { RacingDomainValidationError } from '../errors/RacingDomainError';
|
|
import { MonthlyRecurrencePattern } from './MonthlyRecurrencePattern';
|
|
import { WeekdaySet } from './WeekdaySet';
|
|
|
|
export type WeeklyRecurrenceStrategyProps = {
|
|
kind: 'weekly';
|
|
weekdays: WeekdaySet;
|
|
};
|
|
|
|
export type EveryNWeeksRecurrenceStrategyProps = {
|
|
kind: 'everyNWeeks';
|
|
weekdays: WeekdaySet;
|
|
intervalWeeks: number;
|
|
};
|
|
|
|
export type MonthlyNthWeekdayRecurrenceStrategyProps = {
|
|
kind: 'monthlyNthWeekday';
|
|
monthlyPattern: MonthlyRecurrencePattern;
|
|
};
|
|
|
|
export type RecurrenceStrategyProps =
|
|
| WeeklyRecurrenceStrategyProps
|
|
| EveryNWeeksRecurrenceStrategyProps
|
|
| MonthlyNthWeekdayRecurrenceStrategyProps;
|
|
|
|
export class RecurrenceStrategy implements ValueObject<RecurrenceStrategyProps> {
|
|
private constructor(private readonly strategy: RecurrenceStrategyProps) {}
|
|
|
|
get props(): RecurrenceStrategyProps {
|
|
return this.strategy;
|
|
}
|
|
|
|
static weekly(weekdays: WeekdaySet): RecurrenceStrategy {
|
|
if (weekdays.getAll().length === 0) {
|
|
throw new RacingDomainValidationError('weekdays are required for weekly recurrence');
|
|
}
|
|
|
|
return new RecurrenceStrategy({
|
|
kind: 'weekly',
|
|
weekdays,
|
|
});
|
|
}
|
|
|
|
static everyNWeeks(intervalWeeks: number, weekdays: WeekdaySet): RecurrenceStrategy {
|
|
if (!Number.isInteger(intervalWeeks) || intervalWeeks <= 0) {
|
|
throw new RacingDomainValidationError('intervalWeeks must be a positive integer');
|
|
}
|
|
if (weekdays.getAll().length === 0) {
|
|
throw new RacingDomainValidationError('weekdays are required for everyNWeeks recurrence');
|
|
}
|
|
|
|
return new RecurrenceStrategy({
|
|
kind: 'everyNWeeks',
|
|
weekdays,
|
|
intervalWeeks,
|
|
});
|
|
}
|
|
|
|
static monthlyNthWeekday(pattern: MonthlyRecurrencePattern): RecurrenceStrategy {
|
|
return new RecurrenceStrategy({
|
|
kind: 'monthlyNthWeekday',
|
|
monthlyPattern: pattern,
|
|
});
|
|
}
|
|
|
|
equals(other: ValueObject<RecurrenceStrategyProps>): boolean {
|
|
const otherProps = other.props;
|
|
if (this.strategy.kind !== otherProps.kind) {
|
|
return false;
|
|
}
|
|
switch (this.strategy.kind) {
|
|
case 'weekly':
|
|
return this.strategy.weekdays.equals((otherProps as WeeklyRecurrenceStrategyProps).weekdays);
|
|
case 'everyNWeeks':
|
|
const everyN = otherProps as EveryNWeeksRecurrenceStrategyProps;
|
|
return this.strategy.intervalWeeks === everyN.intervalWeeks && this.strategy.weekdays.equals(everyN.weekdays);
|
|
case 'monthlyNthWeekday':
|
|
const monthly = otherProps as MonthlyNthWeekdayRecurrenceStrategyProps;
|
|
return this.strategy.monthlyPattern.equals(monthly.monthlyPattern);
|
|
default:
|
|
return false;
|
|
}
|
|
}
|
|
}
|
|
|
|
export { RecurrenceStrategyFactory } from './RecurrenceStrategyFactory';
|