1 import _Ajv
, { type JSONSchemaType
, type ValidateFunction
} from
'ajv'
2 import _ajvFormats from
'ajv-formats'
4 import { OCPPConstants
} from
'./OCPPConstants.js'
5 import { OCPPServiceUtils
} from
'./OCPPServiceUtils.js'
6 import { type ChargingStation
, getIdTagsFile
} from
'../../charging-station/index.js'
7 import { OCPPError
} from
'../../exception/index.js'
11 IncomingRequestCommand
,
14 } from
'../../types/index.js'
15 import { logger
, setDefaultErrorParams
} from
'../../utils/index.js'
16 type Ajv
= _Ajv
.default
17 // eslint-disable-next-line @typescript-eslint/no-redeclare
18 const Ajv
= _Ajv
.default
19 const ajvFormats
= _ajvFormats
.default
21 const moduleName
= 'OCPPIncomingRequestService'
23 export abstract class OCPPIncomingRequestService
{
24 private static instance
: OCPPIncomingRequestService
| null = null
25 private readonly version
: OCPPVersion
26 private readonly ajv
: Ajv
27 private readonly jsonValidateFunctions
: Map
<IncomingRequestCommand
, ValidateFunction
<JsonType
>>
28 protected abstract jsonSchemas
: Map
<IncomingRequestCommand
, JSONSchemaType
<JsonType
>>
30 protected constructor (version
: OCPPVersion
) {
31 this.version
= version
33 keywords
: ['javaType'],
34 multipleOfPrecision
: 2
37 this.jsonValidateFunctions
= new Map
<IncomingRequestCommand
, ValidateFunction
<JsonType
>>()
38 this.incomingRequestHandler
= this.incomingRequestHandler
.bind(this)
39 this.validateIncomingRequestPayload
= this.validateIncomingRequestPayload
.bind(this)
42 public static getInstance
<T
extends OCPPIncomingRequestService
>(this: new () => T
): T
{
43 if (OCPPIncomingRequestService
.instance
=== null) {
44 OCPPIncomingRequestService
.instance
= new this()
46 return OCPPIncomingRequestService
.instance
as T
49 protected handleIncomingRequestError
<T
extends JsonType
>(
50 chargingStation
: ChargingStation
,
51 commandName
: IncomingRequestCommand
,
53 params
: HandleErrorParams
<T
> = { throwError
: true, consoleOut
: false }
55 setDefaultErrorParams(params
)
57 `${chargingStation.logPrefix()} ${moduleName}.handleIncomingRequestError: Incoming request command '${commandName}' error:`,
60 if (params
.throwError
=== false && params
.errorResponse
!= null) {
61 return params
.errorResponse
63 if (params
.throwError
=== true && params
.errorResponse
== null) {
66 if (params
.throwError
=== true && params
.errorResponse
!= null) {
67 return params
.errorResponse
71 protected validateIncomingRequestPayload
<T
extends JsonType
>(
72 chargingStation
: ChargingStation
,
73 commandName
: IncomingRequestCommand
,
74 schema
: JSONSchemaType
<T
>,
77 if (chargingStation
.stationInfo
?.ocppStrictCompliance
=== false) {
80 const validate
= this.getJsonIncomingRequestValidateFunction
<T
>(commandName
, schema
)
81 if (validate(payload
)) {
85 `${chargingStation.logPrefix()} ${moduleName}.validateIncomingRequestPayload: Command '${commandName}' incoming request PDU is invalid: %j`,
89 OCPPServiceUtils
.ajvErrorsToErrorType(validate
.errors
),
90 'Incoming request PDU is invalid',
92 JSON
.stringify(validate
.errors
, undefined, 2)
96 protected handleRequestClearCache (chargingStation
: ChargingStation
): ClearCacheResponse
{
97 // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
98 if (chargingStation
.idTagsCache
.deleteIdTags(getIdTagsFile(chargingStation
.stationInfo
!)!)) {
99 return OCPPConstants
.OCPP_RESPONSE_ACCEPTED
101 return OCPPConstants
.OCPP_RESPONSE_REJECTED
104 private getJsonIncomingRequestValidateFunction
<T
extends JsonType
>(
105 commandName
: IncomingRequestCommand
,
106 schema
: JSONSchemaType
<T
>
107 ): ValidateFunction
<JsonType
> {
108 if (!this.jsonValidateFunctions
.has(commandName
)) {
109 this.jsonValidateFunctions
.set(commandName
, this.ajv
.compile
<T
>(schema
).bind(this))
111 // eslint-disable-next-line @typescript-eslint/no-non-null-assertion
112 return this.jsonValidateFunctions
.get(commandName
)!
115 // eslint-disable-next-line @typescript-eslint/no-unused-vars
116 public abstract incomingRequestHandler
<ReqType
extends JsonType
, ResType
extends JsonType
>(
117 chargingStation
: ChargingStation
,
119 commandName
: IncomingRequestCommand
,
120 commandPayload
: ReqType