Skip to content

Commit 4b080f6

Browse files
authored
Improve v1.6 / v2.0.1 Tx APIs compat (#386)
* upgrade v201 compat in MicroOcpp.h * add definition for getTransactionV201() * refactor TxNotification * v201 compat for ocpp_tx C-API * port TxNotification to v201 * init with v201 in C-API directly * fix build checks * enable further v201 benchmarks * update changelog
1 parent 5761e0f commit 4b080f6

28 files changed

+584
-275
lines changed

CHANGELOG.md

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,14 @@
44

55
### Changed
66

7+
- Change `MicroOcpp::TxNotification` into C-style enum, replace `OCPP_TxNotication` ([#386](https://github.com/matth-x/MicroOcpp/pull/386))
78
- Improved UUID generation ([#383](https://github.com/matth-x/MicroOcpp/pull/383))
9+
- `beginTransaction()` returns bool for better v2.0.1 interop ([#386](https://github.com/matth-x/MicroOcpp/pull/386))
10+
11+
### Added
12+
13+
- `getTransactionV201()` exposes v201 Tx in API ([#386](https://github.com/matth-x/MicroOcpp/pull/386))
14+
- v201 support in Transaction.h C-API ([#386](https://github.com/matth-x/MicroOcpp/pull/386))
815

916
### Fixed
1017

CMakeLists.txt

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -79,7 +79,6 @@ set(MO_SRC
7979
src/MicroOcpp/Model/Certificates/CertificateService.cpp
8080
src/MicroOcpp/Model/ConnectorBase/ConnectorsCommon.cpp
8181
src/MicroOcpp/Model/ConnectorBase/Connector.cpp
82-
src/MicroOcpp/Model/ConnectorBase/Notification.cpp
8382
src/MicroOcpp/Model/Diagnostics/DiagnosticsService.cpp
8483
src/MicroOcpp/Model/FirmwareManagement/FirmwareService.cpp
8584
src/MicroOcpp/Model/Heartbeat/HeartbeatService.cpp

examples/ESP-IDF/main/main.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -160,7 +160,7 @@ void app_main(void)
160160
EXAMPLE_MO_OCPP_BACKEND,
161161
EXAMPLE_MO_CHARGEBOXID,
162162
EXAMPLE_MO_AUTHORIZATIONKEY, "", fsopt);
163-
ocpp_initialize(osock, "ESP-IDF charger", "Your brand name here", fsopt, false);
163+
ocpp_initialize(osock, "ESP-IDF charger", "Your brand name here", fsopt, false, false);
164164

165165
/* Enter infinite loop */
166166
while (1) {

src/MicroOcpp.cpp

Lines changed: 169 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -293,6 +293,8 @@ void mocpp_initialize(Connection& connection, const char *bootNotificationCreden
293293
new TransactionService(*context, filesystem, MO_NUM_EVSEID)));
294294
model.setRemoteControlService(std::unique_ptr<RemoteControlService>(
295295
new RemoteControlService(*context, MO_NUM_EVSEID)));
296+
model.setResetServiceV201(std::unique_ptr<Ocpp201::ResetService>(
297+
new Ocpp201::ResetService(*context)));
296298
} else
297299
#endif
298300
{
@@ -305,20 +307,24 @@ void mocpp_initialize(Connection& connection, const char *bootNotificationCreden
305307
connectors.emplace_back(new Connector(*context, filesystem, connectorId));
306308
}
307309
model.setConnectors(std::move(connectors));
308-
}
309-
model.setHeartbeatService(std::unique_ptr<HeartbeatService>(
310-
new HeartbeatService(*context)));
311310

312311
#if MO_ENABLE_LOCAL_AUTH
313-
model.setAuthorizationService(std::unique_ptr<AuthorizationService>(
314-
new AuthorizationService(*context, filesystem)));
312+
model.setAuthorizationService(std::unique_ptr<AuthorizationService>(
313+
new AuthorizationService(*context, filesystem)));
315314
#endif //MO_ENABLE_LOCAL_AUTH
316315

317316
#if MO_ENABLE_RESERVATION
318-
model.setReservationService(std::unique_ptr<ReservationService>(
319-
new ReservationService(*context, MO_NUMCONNECTORS)));
317+
model.setReservationService(std::unique_ptr<ReservationService>(
318+
new ReservationService(*context, MO_NUMCONNECTORS)));
320319
#endif
321320

321+
model.setResetService(std::unique_ptr<ResetService>(
322+
new ResetService(*context)));
323+
}
324+
325+
model.setHeartbeatService(std::unique_ptr<HeartbeatService>(
326+
new HeartbeatService(*context)));
327+
322328
#if MO_ENABLE_CERT_MGMT && MO_ENABLE_CERT_STORE_MBEDTLS
323329
std::unique_ptr<CertificateStore> certStore = makeCertificateStoreMbedTLS(filesystem);
324330
if (certStore) {
@@ -330,18 +336,6 @@ void mocpp_initialize(Connection& connection, const char *bootNotificationCreden
330336
}
331337
#endif
332338

333-
#if MO_ENABLE_V201
334-
if (version.major == 2) {
335-
//depends on VariableService
336-
model.setResetServiceV201(std::unique_ptr<Ocpp201::ResetService>(
337-
new Ocpp201::ResetService(*context)));
338-
} else
339-
#endif
340-
{
341-
model.setResetService(std::unique_ptr<ResetService>(
342-
new ResetService(*context)));
343-
}
344-
345339
#if !defined(MO_CUSTOM_UPDATER)
346340
#if MO_PLATFORM == MO_PLATFORM_ARDUINO && defined(ESP32) && MO_ENABLE_MBEDTLS
347341
model.setFirmwareService(
@@ -376,6 +370,12 @@ void mocpp_initialize(Connection& connection, const char *bootNotificationCreden
376370

377371
configuration_load();
378372

373+
#if MO_ENABLE_V201
374+
if (version.major == 2) {
375+
model.getVariableService()->load();
376+
}
377+
#endif //MO_ENABLE_V201
378+
379379
MO_DBG_INFO("initialized MicroOcpp v" MO_VERSION " running OCPP %i.%i.%i", version.major, version.minor, version.patch);
380380
}
381381

@@ -422,48 +422,105 @@ void mocpp_loop() {
422422
context->loop();
423423
}
424424

425-
std::shared_ptr<Transaction> beginTransaction(const char *idTag, unsigned int connectorId) {
425+
bool beginTransaction(const char *idTag, unsigned int connectorId) {
426426
if (!context) {
427427
MO_DBG_ERR("OCPP uninitialized"); //need to call mocpp_initialize before
428-
return nullptr;
428+
return false;
429429
}
430+
431+
#if MO_ENABLE_V201
432+
if (context->getVersion().major == 2) {
433+
if (!idTag || strnlen(idTag, MO_IDTOKEN_LEN_MAX + 2) > MO_IDTOKEN_LEN_MAX) {
434+
MO_DBG_ERR("idTag format violation. Expect c-style string with at most %u characters", MO_IDTOKEN_LEN_MAX);
435+
return false;
436+
}
437+
TransactionService::Evse *evse = nullptr;
438+
if (auto txService = context->getModel().getTransactionService()) {
439+
evse = txService->getEvse(connectorId);
440+
}
441+
if (!evse) {
442+
MO_DBG_ERR("could not find EVSE");
443+
return false;
444+
}
445+
return evse->beginAuthorization(idTag, true);
446+
}
447+
#endif
448+
430449
if (!idTag || strnlen(idTag, IDTAG_LEN_MAX + 2) > IDTAG_LEN_MAX) {
431450
MO_DBG_ERR("idTag format violation. Expect c-style string with at most %u characters", IDTAG_LEN_MAX);
432-
return nullptr;
451+
return false;
433452
}
434453
auto connector = context->getModel().getConnector(connectorId);
435454
if (!connector) {
436455
MO_DBG_ERR("could not find connector");
437-
return nullptr;
456+
return false;
438457
}
439458

440-
return connector->beginTransaction(idTag);
459+
return connector->beginTransaction(idTag) != nullptr;
441460
}
442461

443-
std::shared_ptr<Transaction> beginTransaction_authorized(const char *idTag, const char *parentIdTag, unsigned int connectorId) {
462+
bool beginTransaction_authorized(const char *idTag, const char *parentIdTag, unsigned int connectorId) {
444463
if (!context) {
445464
MO_DBG_ERR("OCPP uninitialized"); //need to call mocpp_initialize before
446-
return nullptr;
465+
return false;
447466
}
467+
468+
#if MO_ENABLE_V201
469+
if (context->getVersion().major == 2) {
470+
if (!idTag || strnlen(idTag, MO_IDTOKEN_LEN_MAX + 2) > MO_IDTOKEN_LEN_MAX) {
471+
MO_DBG_ERR("idTag format violation. Expect c-style string with at most %u characters", MO_IDTOKEN_LEN_MAX);
472+
return false;
473+
}
474+
TransactionService::Evse *evse = nullptr;
475+
if (auto txService = context->getModel().getTransactionService()) {
476+
evse = txService->getEvse(connectorId);
477+
}
478+
if (!evse) {
479+
MO_DBG_ERR("could not find EVSE");
480+
return false;
481+
}
482+
return evse->beginAuthorization(idTag, false);
483+
}
484+
#endif
485+
448486
if (!idTag || strnlen(idTag, IDTAG_LEN_MAX + 2) > IDTAG_LEN_MAX ||
449487
(parentIdTag && strnlen(parentIdTag, IDTAG_LEN_MAX + 2) > IDTAG_LEN_MAX)) {
450488
MO_DBG_ERR("(parent)idTag format violation. Expect c-style string with at most %u characters", IDTAG_LEN_MAX);
451-
return nullptr;
489+
return false;
452490
}
453491
auto connector = context->getModel().getConnector(connectorId);
454492
if (!connector) {
455493
MO_DBG_ERR("could not find connector");
456-
return nullptr;
494+
return false;
457495
}
458496

459-
return connector->beginTransaction_authorized(idTag, parentIdTag);
497+
return connector->beginTransaction_authorized(idTag, parentIdTag) != nullptr;
460498
}
461499

462500
bool endTransaction(const char *idTag, const char *reason, unsigned int connectorId) {
463501
if (!context) {
464502
MO_DBG_ERR("OCPP uninitialized"); //need to call mocpp_initialize before
465503
return false;
466504
}
505+
506+
#if MO_ENABLE_V201
507+
if (context->getVersion().major == 2) {
508+
if (!idTag || strnlen(idTag, MO_IDTOKEN_LEN_MAX + 2) > MO_IDTOKEN_LEN_MAX) {
509+
MO_DBG_ERR("idTag format violation. Expect c-style string with at most %u characters", MO_IDTOKEN_LEN_MAX);
510+
return false;
511+
}
512+
TransactionService::Evse *evse = nullptr;
513+
if (auto txService = context->getModel().getTransactionService()) {
514+
evse = txService->getEvse(connectorId);
515+
}
516+
if (!evse) {
517+
MO_DBG_ERR("could not find EVSE");
518+
return false;
519+
}
520+
return evse->endAuthorization(idTag, true);
521+
}
522+
#endif
523+
467524
bool res = false;
468525
if (isTransactionActive(connectorId) && getTransactionIdTag(connectorId)) {
469526
//end transaction now if either idTag is nullptr (i.e. force stop) or the idTag matches beginTransaction
@@ -486,7 +543,7 @@ bool endTransaction(const char *idTag, const char *reason, unsigned int connecto
486543
MO_DBG_DEBUG("Authorize rejected (%s), continue transaction", idTag_capture.c_str());
487544
auto connector = context->getModel().getConnector(connectorId);
488545
if (connector) {
489-
connector->updateTxNotification(TxNotification::AuthorizationRejected);
546+
connector->updateTxNotification(TxNotification_AuthorizationRejected);
490547
}
491548
return;
492549
}
@@ -501,7 +558,7 @@ bool endTransaction(const char *idTag, const char *reason, unsigned int connecto
501558
MO_DBG_DEBUG("Authorization timeout (%s), continue transaction", idTag_capture.c_str());
502559
auto connector = context->getModel().getConnector(connectorId);
503560
if (connector) {
504-
connector->updateTxNotification(TxNotification::AuthorizationTimeout);
561+
connector->updateTxNotification(TxNotification_AuthorizationTimeout);
505562
}
506563
});
507564

@@ -524,6 +581,25 @@ bool endTransaction_authorized(const char *idTag, const char *reason, unsigned i
524581
MO_DBG_ERR("OCPP uninitialized"); //need to call mocpp_initialize before
525582
return false;
526583
}
584+
585+
#if MO_ENABLE_V201
586+
if (context->getVersion().major == 2) {
587+
if (!idTag || strnlen(idTag, MO_IDTOKEN_LEN_MAX + 2) > MO_IDTOKEN_LEN_MAX) {
588+
MO_DBG_ERR("idTag format violation. Expect c-style string with at most %u characters", MO_IDTOKEN_LEN_MAX);
589+
return false;
590+
}
591+
TransactionService::Evse *evse = nullptr;
592+
if (auto txService = context->getModel().getTransactionService()) {
593+
evse = txService->getEvse(connectorId);
594+
}
595+
if (!evse) {
596+
MO_DBG_ERR("could not find EVSE");
597+
return false;
598+
}
599+
return evse->endAuthorization(idTag, false);
600+
}
601+
#endif
602+
527603
auto connector = context->getModel().getConnector(connectorId);
528604
if (!connector) {
529605
MO_DBG_ERR("could not find connector");
@@ -628,6 +704,12 @@ std::shared_ptr<Transaction>& getTransaction(unsigned int connectorId) {
628704
MO_DBG_WARN("OCPP uninitialized");
629705
return mocpp_undefinedTx;
630706
}
707+
#if MO_ENABLE_V201
708+
if (context->getVersion().major == 2) {
709+
MO_DBG_ERR("only supported in v16");
710+
return mocpp_undefinedTx;
711+
}
712+
#endif
631713
auto connector = context->getModel().getConnector(connectorId);
632714
if (!connector) {
633715
MO_DBG_ERR("could not find connector");
@@ -636,6 +718,30 @@ std::shared_ptr<Transaction>& getTransaction(unsigned int connectorId) {
636718
return connector->getTransaction();
637719
}
638720

721+
#if MO_ENABLE_V201
722+
Ocpp201::Transaction *getTransactionV201(unsigned int evseId) {
723+
if (!context) {
724+
MO_DBG_ERR("OCPP uninitialized"); //need to call mocpp_initialize before
725+
return nullptr;
726+
}
727+
728+
if (context->getVersion().major != 2) {
729+
MO_DBG_ERR("only supported in v201");
730+
return nullptr;
731+
}
732+
733+
TransactionService::Evse *evse = nullptr;
734+
if (auto txService = context->getModel().getTransactionService()) {
735+
evse = txService->getEvse(evseId);
736+
}
737+
if (!evse) {
738+
MO_DBG_ERR("could not find EVSE");
739+
return nullptr;
740+
}
741+
return evse->getTransaction();
742+
}
743+
#endif //MO_ENABLE_V201
744+
639745
bool ocppPermitsCharge(unsigned int connectorId) {
640746
if (!context) {
641747
MO_DBG_WARN("OCPP uninitialized");
@@ -1003,6 +1109,7 @@ void setOccupiedInput(std::function<bool()> occupied, unsigned int connectorId)
10031109
evse->setOccupiedInput(occupied);
10041110
}
10051111
}
1112+
return;
10061113
}
10071114
#endif
10081115
auto connector = context->getModel().getConnector(connectorId);
@@ -1039,11 +1146,17 @@ void setStopTxReadyInput(std::function<bool()> stopTxReady, unsigned int connect
10391146
connector->setStopTxReadyInput(stopTxReady);
10401147
}
10411148

1042-
void setTxNotificationOutput(std::function<void(MicroOcpp::Transaction*,MicroOcpp::TxNotification)> notificationOutput, unsigned int connectorId) {
1149+
void setTxNotificationOutput(std::function<void(MicroOcpp::Transaction*,TxNotification)> notificationOutput, unsigned int connectorId) {
10431150
if (!context) {
10441151
MO_DBG_ERR("OCPP uninitialized"); //need to call mocpp_initialize before
10451152
return;
10461153
}
1154+
#if MO_ENABLE_V201
1155+
if (context->getVersion().major == 2) {
1156+
MO_DBG_ERR("only supported in v16");
1157+
return;
1158+
}
1159+
#endif
10471160
auto connector = context->getModel().getConnector(connectorId);
10481161
if (!connector) {
10491162
MO_DBG_ERR("could not find connector");
@@ -1052,6 +1165,30 @@ void setTxNotificationOutput(std::function<void(MicroOcpp::Transaction*,MicroOcp
10521165
connector->setTxNotificationOutput(notificationOutput);
10531166
}
10541167

1168+
#if MO_ENABLE_V201
1169+
void setTxNotificationOutputV201(std::function<void(MicroOcpp::Ocpp201::Transaction*,TxNotification)> notificationOutput, unsigned int connectorId) {
1170+
if (!context) {
1171+
MO_DBG_ERR("OCPP uninitialized"); //need to call mocpp_initialize before
1172+
return;
1173+
}
1174+
1175+
if (context->getVersion().major != 2) {
1176+
MO_DBG_ERR("only supported in v201");
1177+
return;
1178+
}
1179+
1180+
TransactionService::Evse *evse = nullptr;
1181+
if (auto txService = context->getModel().getTransactionService()) {
1182+
evse = txService->getEvse(connectorId);
1183+
}
1184+
if (!evse) {
1185+
MO_DBG_ERR("could not find EVSE");
1186+
return;
1187+
}
1188+
evse->setTxNotificationOutput(notificationOutput);
1189+
}
1190+
#endif //MO_ENABLE_V201
1191+
10551192
#if MO_ENABLE_CONNECTOR_LOCK
10561193
void setOnUnlockConnectorInOut(std::function<UnlockConnectorResult()> onUnlockConnectorInOut, unsigned int connectorId) {
10571194
if (!context) {

0 commit comments

Comments
 (0)