A CSMS that works against a well-behaved charger can still fail in the field. Real firmware refuses requests it should accept, accepts requests it never carries out, and formats numbers its own way. These cases are rarely in the specification, and they are the ones that generate support tickets. SimItNow stations take a few options on the create call that reproduce them.
curl -X PUT https://api.simitnow.com/v2/cs/CP-001 \
-H "SIMITNOW-API-KEY: $API_KEY" \
-H "Content-Type: application/json" \
-d '{"csmsUrl":"wss://csms.example.com/ocpp","protocol":"ocpp1.6",
"emulateRemoteStartRejected":true}'
The options below are described for OCPP 1.6 stations. You can combine them, and each one applies to the station from the moment it is created.
A remote start that is always refused
With emulateRemoteStartRejected set to true, the station answers every RemoteStartTransaction with Rejected and changes nothing: the connector status stays the same, no pending start is remembered, and no timer starts. A real charger answers this way when it cannot start, for example with a faulted connector.
Check that your CSMS tells the driver or the calling system, does not keep a session waiting that will never start, and does not retry in a tight loop.
A remote start that is accepted and then does nothing
The worse case is a charger that answers Accepted and never sends StartTransaction. Set emulateRemoteStartFailsToStartCharging to true and the station behaves this way, including when the vehicle is plugged in after the request.
Your CSMS has to notice that nothing happened. Look for a timeout on the pending start, a failure state that reaches the driver and no connector left waiting in Preparing. A CSMS that treats Accepted as the start of a session will show a charging session that does not exist.
Slow starts and stops
waitTimeBeforeStartStop is the number of seconds the station waits after answering a RemoteStart or RemoteStop before it starts or stops the transaction. The default is 5. Raise it to 30 or 60 to test what your CSMS does while it waits for the StartTransaction or StopTransaction that follows its request, including when a driver gives up and sends the opposite command in the gap.
Decimals with a comma
Some chargers format meter readings with the decimal separator of their locale. With useCommaInMeterValues set to true, the station sends values such as 12,5000 instead of 12.5000. A CSMS that parses readings with a plain float conversion fails on that string, and the failure can show up as missing energy on a bill, a costly place to find it. The option applies to OCPP 1.6 stations.
Temperature in its own message
Another firmware habit is to report temperature separately from the rest of the reading. With sendEmptyMeterValues set to true, the station removes Temperature from the regular MeterValues message and sends it in a second MeterValues message with the same connector and transaction id. The second message follows every regular one, whether or not your CSMS put Temperature in MeterValuesSampledData, and if Temperature is the only measurand requested the station sends nothing at all. The name is misleading: it does not send empty readings.
Check that the second message is attached to the right transaction, and that the energy total is not counted twice or dropped because the message has no energy value in it.
A meter that does not start at zero
initialMeterValue sets the energy register, in watt-hours, at the moment the station is created. Real registers have run for years, so the first transaction starts at a large number. Use it to check that your CSMS bills the difference between the start and stop readings and not the stop reading itself. On OCPP 1.6, meterStart and meterStop are integers in the specification, so the station rounds the register to whole watt-hours in those two fields. A very large value, above 2,147,483,647 Wh, also shows whether a field is a 32-bit integer anywhere in the pipeline.
A station that will not hold still
With isStable set to false, the station picks a random connector status and a random error code for each connector once a minute and reports the change. The combinations are not realistic: a connector can report Charging with no transaction, or Faulted with NoError. It tests whether your CSMS survives a stream of contradictory StatusNotification messages, and whether one bad report can lock a connector in a state it cannot leave. The option applies to OCPP 1.6 stations.
Putting it to use
Run the normal happy-path script from the CI guide once per option and compare the result with the clean run. The cases above are about how a CSMS recovers, so also look at what it does an hour later: are there stuck sessions, wrong totals or a connector that stayed unavailable? For failures that come from the network and the CSMS side, see invalid scenario testing and offline transactions and reconnects.
Create a free account and make a charger misbehave on purpose.