Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Transaction event changes to get remote start / stop working and compliant to octt #138

Merged
merged 4 commits into from
Aug 17, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion include/ocpp/v201/charge_point.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -90,6 +90,8 @@ class ChargePoint : ocpp::ChargingStationBase {
data_transfer_callbacks;
std::mutex data_transfer_callbacks_mutex;

std::map<int32_t, std::pair<IdToken, int32_t>> remote_start_id_per_evse;

// timers
Everest::SteadyTimer heartbeat_timer;
Everest::SteadyTimer boot_notification_timer;
Expand Down Expand Up @@ -297,7 +299,7 @@ class ChargePoint : ocpp::ChargingStationBase {
/// \param signed_meter_value
void on_transaction_finished(const int32_t evse_id, const DateTime& timestamp, const MeterValue& meter_stop,
const ReasonEnum reason, const std::optional<std::string>& id_token,
const std::optional<std::string>& signed_meter_value);
const std::optional<std::string>& signed_meter_value, const ChargingStateEnum charging_state);

/// \brief Event handler that should be called when a session has finished
/// \param evse_id
Expand Down
53 changes: 49 additions & 4 deletions lib/ocpp/v201/charge_point.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -146,6 +146,7 @@ void ChargePoint::on_transaction_started(const int32_t evse_id, const int32_t co
ControllerComponentVariables::SampledDataTxStartedMeasurands)));

Transaction transaction{enhanced_transaction->transactionId};
transaction.chargingState = charging_state;
if (remote_start_id.has_value()) {
transaction.remoteStartId = remote_start_id.value();
enhanced_transaction->remoteStartId = remote_start_id.value();
Expand All @@ -162,8 +163,10 @@ void ChargePoint::on_transaction_started(const int32_t evse_id, const int32_t co
void ChargePoint::on_transaction_finished(const int32_t evse_id, const DateTime& timestamp,
const MeterValue& meter_stop, const ReasonEnum reason,
const std::optional<std::string>& id_token,
const std::optional<std::string>& signed_meter_value) {
const auto& enhanced_transaction = this->evses.at(evse_id)->get_transaction();
const std::optional<std::string>& signed_meter_value,
const ChargingStateEnum charging_state) {
auto& enhanced_transaction = this->evses.at(evse_id)->get_transaction();
enhanced_transaction->chargingState = charging_state;
if (enhanced_transaction == nullptr) {
EVLOG_warning << "Received notification of finished transaction while no transaction was active";
return;
Expand Down Expand Up @@ -231,6 +234,14 @@ bool ChargePoint::on_charging_state_changed(const uint32_t evse_id,
this->evses.at(static_cast<int32_t>(evse_id))->get_transaction();
if (transaction != nullptr) {
transaction->chargingState = charging_state;
this->transaction_event_req(
TransactionEventEnum::Updated, DateTime(),
transaction->get_transaction(),
TriggerReasonEnum::ChargingStateChanged,
transaction->get_seq_no(), std::nullopt,
this->evses.at(static_cast<int32_t>(evse_id))->get_evse_info(),
std::nullopt, std::nullopt, std::nullopt, std::nullopt,
std::nullopt);
return true;
} else {
EVLOG_warning
Expand Down Expand Up @@ -845,12 +856,43 @@ void ChargePoint::transaction_event_req(const TransactionEventEnum& event_type,

ocpp::Call<TransactionEventRequest> call(req, this->message_queue->createMessageId());

// Check if id token is in the remote start map, because when a remote
// start request is done, the first transaction event request should
// always contain trigger reason 'RemoteStart'.
auto it = std::find_if(
remote_start_id_per_evse.begin(), remote_start_id_per_evse.end(),
[&id_token, &evse](const std::pair<int32_t, std::pair<IdToken, int32_t>>& remote_start_per_evse) {
if (id_token.has_value() &&
remote_start_per_evse.second.first.idToken == id_token.value().idToken) {

if (remote_start_per_evse.first == 0) {
return true;
}

if (evse.has_value() &&
evse.value().id == remote_start_per_evse.first) {
return true;
}
}
return false;
}
);

if (it != remote_start_id_per_evse.end()) {
// Found remote start. Set remote start id and the trigger reason.
call.msg.triggerReason = TriggerReasonEnum::RemoteStart;
call.msg.transactionInfo.remoteStartId = it->second.second;

remote_start_id_per_evse.erase(it);
}

if (event_type == TransactionEventEnum::Started) {
if (!evse.has_value() or !id_token.has_value()) {
EVLOG_error << "Request to send TransactionEvent(Started) without given evse or id_token. These properties "
"are required for this eventType \"Started\"!";
return;
}

auto future = this->send_async<TransactionEventRequest>(call);
const auto enhanced_message = future.get();
if (enhanced_message.messageType == MessageType::TransactionEventResponse) {
Expand Down Expand Up @@ -1246,12 +1288,15 @@ void ChargePoint::handle_remote_start_transaction_request(Call<RequestStartTrans
} else {
// F02: No active transaction yet and there is an available connector, so just send 'accepted'.
response.status = RequestStartStopStatusEnum::Accepted;

remote_start_id_per_evse[evse_id] = {msg.idToken, msg.remoteStartId};
}
}
} else {
// F01.FR.07 RequestStartTransactionRequest does not contain an evseId.The Charging Station MAY reject the
// F01.FR.07 RequestStartTransactionRequest does not contain an evseId. The Charging Station MAY reject the
// RequestStartTransactionRequest. We do this for now (send rejected) (TODO: eventually support the charging
// station to )
// station to accept no evse id. If so: add token and remote start id for evse id 0 to remote_start_id_per_evse,
// so we know for '0' it means 'all evse id's').
EVLOG_warning << "No evse id given. Can not remote start transaction.";
}

Expand Down