@gouvfr-anct/timetable-to-osm-opening-hours
Version:
📚 Bibliothèque pour la transformation d'une série de plages horaires représentant un format emploi du temps vers le standard OSM pour les horaires d'ouverture.
52 lines (51 loc) • 2.75 kB
JavaScript
/* eslint-disable-next-line camelcase */
import opening_hours from 'opening_hours';
import { OSM_DAYS_OF_WEEK, WeekDay } from '../utilities';
const MINUTE_TO_MILLISECONDS = 60 * 1000;
const HOUR_TO_MILLISECONDS = 60 * MINUTE_TO_MILLISECONDS;
const DAY_TO_MILLISECONDS = 24 * HOUR_TO_MILLISECONDS;
export const dayOfTheWeek = (date, weekDay) =>
/* eslint-disable-next-line no-mixed-operators */
new Date(date.getTime() + (weekDay + 1 - date.getDay()) * DAY_TO_MILLISECONDS);
const timeToMilliseconds = (time) => {
const [hours, minutes] = time.split(':').map(Number);
/* eslint-disable-next-line no-mixed-operators */
return (hours ?? 0) * HOUR_TO_MILLISECONDS + (minutes ?? 0) * MINUTE_TO_MILLISECONDS;
};
const firstTimeOfTheDay = (date) => {
const dateWithoutTime = new Date(date);
dateWithoutTime.setHours(0, 0, 0, 0);
return dateWithoutTime;
};
const lastTimeOfTheDay = (date) => {
const dateWithoutTime = new Date(date);
dateWithoutTime.setHours(23, 59, 59, 999);
return dateWithoutTime;
};
export const dateTimeFor = (date) => (weekDay, time) => new Date(dayOfTheWeek(firstTimeOfTheDay(date), weekDay).getTime() + timeToMilliseconds(time));
const formatTime = (intervalStart) => intervalStart?.toLocaleTimeString('fr-FR', {
hour: '2-digit',
minute: '2-digit'
});
const appendOsmOpeningHours = (day, [intervalStart, intervalEnd]) => ({
day,
osmHours: `${formatTime(intervalStart)}-${formatTime(intervalEnd)}`
});
const matchingDay = (day) => (openingHours) => openingHours.day === day;
const toUpdatedOsmOpeningHours = (day, [intervalStart, intervalEnd]) => (openingHours) => openingHours.day === day
? {
...openingHours,
osmHours: `${openingHours.osmHours},${formatTime(intervalStart)}-${formatTime(intervalEnd)}`
}
: openingHours;
const appendTimeTableInterval = (timeTableOpeningHours, osmInterval, day) => timeTableOpeningHours.find(matchingDay(day)) == null
? [...timeTableOpeningHours, appendOsmOpeningHours(day, osmInterval)]
: timeTableOpeningHours.map(toUpdatedOsmOpeningHours(day, osmInterval));
export const firstDayOfTheWeek = (date) => dayOfTheWeek(date, WeekDay.Monday);
export const lastDayOfTheWeek = (date) => dayOfTheWeek(date, WeekDay.Sunday);
const dayOfWeek = ([intervalStart]) => OSM_DAYS_OF_WEEK[intervalStart.getDay() - 1] ?? 'Su';
export const toTimetableOsmOpeningHours = (date) => (horairesOSM) => horairesOSM == null
? []
: new opening_hours(horairesOSM, null)
.getOpenIntervals(firstTimeOfTheDay(firstDayOfTheWeek(date)), lastTimeOfTheDay(lastDayOfTheWeek(date)))
.reduce((timeTableOpeningHours, osmInterval) => appendTimeTableInterval(timeTableOpeningHours, osmInterval, dayOfWeek(osmInterval)), []);