X-Git-Url: https://git.piment-noir.org/?a=blobdiff_plain;f=src%2Fcharging-station%2FChargingStationUtils.ts;h=9da406c282d448b8b713dd116658433c4e291994;hb=522e4b058bc5ed1015cdf902e36a107490824f73;hp=8d595b22acae2be8e7d0a4fe0f19edd243f884ad;hpb=252a7d22e33f6c4a9bfcc83cb4fb941f76d15dab;p=e-mobility-charging-stations-simulator.git diff --git a/src/charging-station/ChargingStationUtils.ts b/src/charging-station/ChargingStationUtils.ts index 8d595b22..9da406c2 100644 --- a/src/charging-station/ChargingStationUtils.ts +++ b/src/charging-station/ChargingStationUtils.ts @@ -10,13 +10,10 @@ import { addWeeks, differenceInDays, differenceInWeeks, - endOfDay, - endOfWeek, isAfter, isBefore, isWithinInterval, - startOfDay, - startOfWeek, + toDate, } from 'date-fns'; import type { ChargingStation } from './ChargingStation'; @@ -57,6 +54,7 @@ import { isNotEmptyString, isNullOrUndefined, isUndefined, + isValidDate, logger, secureRandom, } from '../utils'; @@ -686,13 +684,14 @@ const getLimitFromChargingProfiles = ( ): ChargingProfilesLimit | undefined => { const debugLogMsg = `${logPrefix} ${moduleName}.getLimitFromChargingProfiles: Matching charging profile found for power limitation: %j`; const currentDate = new Date(); + const connectorStatus = chargingStation.getConnectorStatus(connectorId); for (const chargingProfile of chargingProfiles) { if ( - chargingProfile.validFrom && - chargingProfile.validTo && + isValidDate(chargingProfile.validFrom) && + isValidDate(chargingProfile.validTo) && !isWithinInterval(currentDate, { - start: chargingProfile.validFrom, - end: chargingProfile.validTo, + start: chargingProfile.validFrom!, + end: chargingProfile.validTo!, }) ) { logger.debug( @@ -703,13 +702,12 @@ const getLimitFromChargingProfiles = ( continue; } const chargingSchedule = chargingProfile.chargingSchedule; - if (!chargingSchedule?.startSchedule) { + if (connectorStatus?.transactionStarted && !chargingSchedule?.startSchedule) { logger.debug( `${logPrefix} ${moduleName}.getLimitFromChargingProfiles: startSchedule is not defined in charging profile id ${chargingProfile.chargingProfileId}. Trying to set it to the connector transaction start date`, ); // OCPP specifies that if startSchedule is not defined, it should be relative to start of the connector transaction - chargingSchedule.startSchedule = - chargingStation.getConnectorStatus(connectorId)?.transactionStart; + chargingSchedule.startSchedule = connectorStatus?.transactionStart; } if (!(chargingSchedule?.startSchedule instanceof Date)) { logger.warn( @@ -726,60 +724,21 @@ const getLimitFromChargingProfiles = ( ); continue; } - // Adjust recurring start schedule if (chargingProfile.chargingProfileKind === ChargingProfileKindType.RECURRING) { - switch (chargingProfile.recurrencyKind) { - case RecurrencyKindType.DAILY: - if (isBefore(chargingSchedule.startSchedule, startOfDay(currentDate))) { - addDays( - chargingSchedule.startSchedule, - differenceInDays(chargingSchedule.startSchedule, endOfDay(currentDate)), - ); - if ( - isBefore(chargingSchedule.startSchedule, startOfDay(currentDate)) || - isAfter(chargingSchedule.startSchedule, endOfDay(currentDate)) - ) { - logger.error( - `${logPrefix} ${moduleName}.getLimitFromChargingProfiles: Recurring ${ - chargingProfile.recurrencyKind - } charging profile id ${ - chargingProfile.chargingProfileId - } startSchedule ${chargingSchedule.startSchedule.toISOString()} is not properly translated to the current day`, - ); - } - } - break; - case RecurrencyKindType.WEEKLY: - if (isBefore(chargingSchedule.startSchedule, startOfWeek(currentDate))) { - addWeeks( - chargingSchedule.startSchedule, - differenceInWeeks(chargingSchedule.startSchedule, endOfWeek(currentDate)), - ); - if ( - isBefore(chargingSchedule.startSchedule, startOfWeek(currentDate)) || - isAfter(chargingSchedule.startSchedule, endOfWeek(currentDate)) - ) { - logger.error( - `${logPrefix} ${moduleName}.getLimitFromChargingProfiles: Recurring ${ - chargingProfile.recurrencyKind - } charging profile id ${ - chargingProfile.chargingProfileId - } startSchedule ${chargingSchedule.startSchedule.toISOString()} is not properly translated to the current week`, - ); - } - } - break; - } - } else if (chargingProfile.chargingProfileKind === ChargingProfileKindType.RELATIVE) { - chargingSchedule.startSchedule = - chargingStation.getConnectorStatus(connectorId)?.transactionStart; + prepareRecurringChargingProfile(chargingProfile, currentDate, logPrefix); + } else if ( + chargingProfile.chargingProfileKind === ChargingProfileKindType.RELATIVE && + connectorStatus?.transactionStarted + ) { + chargingSchedule.startSchedule = connectorStatus?.transactionStart; } // Check if the charging profile is active if ( + isValidDate(chargingSchedule.startSchedule) && isAfter(addSeconds(chargingSchedule.startSchedule!, chargingSchedule.duration!), currentDate) ) { if (isNotEmptyArray(chargingSchedule.chargingSchedulePeriod)) { - // Handling of only one period + // Handling of only one schedule period if ( chargingSchedule.chargingSchedulePeriod.length === 1 && chargingSchedule.chargingSchedulePeriod[0].startPeriod === 0 @@ -801,7 +760,7 @@ const getLimitFromChargingProfiles = ( currentDate, ) ) { - // Found the schedule: last but one is the correct one + // Found the schedule period: last but one is the correct one const result: ChargingProfilesLimit = { limit: lastButOneSchedule!.limit, matchingChargingProfile: chargingProfile, @@ -831,6 +790,73 @@ const getLimitFromChargingProfiles = ( } }; +/** + * Adjust recurring charging profile startSchedule to the current recurrency time interval if needed + * + * @param chargingProfile - + * @param currentDate - + * @param logPrefix - + */ +const prepareRecurringChargingProfile = ( + chargingProfile: ChargingProfile, + currentDate: Date, + logPrefix: string, +) => { + const chargingSchedule = chargingProfile.chargingSchedule; + let recurringInterval: Interval; + switch (chargingProfile.recurrencyKind) { + case RecurrencyKindType.DAILY: + recurringInterval = { + start: chargingSchedule.startSchedule!, + end: addDays(chargingSchedule.startSchedule!, 1), + }; + if ( + !isWithinInterval(currentDate, recurringInterval) && + isBefore(chargingSchedule.startSchedule!, currentDate) + ) { + chargingSchedule.startSchedule = addDays( + chargingSchedule.startSchedule!, + differenceInDays(chargingSchedule.startSchedule!, recurringInterval.end), + ); + recurringInterval = { + start: chargingSchedule.startSchedule, + end: addDays(chargingSchedule.startSchedule, 1), + }; + } + break; + case RecurrencyKindType.WEEKLY: + recurringInterval = { + start: chargingSchedule.startSchedule!, + end: addWeeks(chargingSchedule.startSchedule!, 1), + }; + if ( + !isWithinInterval(currentDate, recurringInterval) && + isBefore(chargingSchedule.startSchedule!, currentDate) + ) { + chargingSchedule.startSchedule = addWeeks( + chargingSchedule.startSchedule!, + differenceInWeeks(chargingSchedule.startSchedule!, recurringInterval.end), + ); + recurringInterval = { + start: chargingSchedule.startSchedule, + end: addWeeks(chargingSchedule.startSchedule, 1), + }; + } + break; + } + if (!isWithinInterval(currentDate, recurringInterval!)) { + logger.error( + `${logPrefix} ${moduleName}.getLimitFromChargingProfiles: Recurring ${ + chargingProfile.recurrencyKind + } charging profile id ${ + chargingProfile.chargingProfileId + } startSchedule ${chargingSchedule.startSchedule!.toISOString()} is not properly translated to current recurrency time interval [${toDate( + recurringInterval!.start, + ).toISOString()}, ${toDate(recurringInterval!.end).toISOString()}]`, + ); + } +}; + const getRandomSerialNumberSuffix = (params?: { randomBytesLength?: number; upperCase?: boolean;