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

Auth: Trigger validation only when useful #734

Merged
merged 5 commits into from
Jun 26, 2024
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
1 change: 1 addition & 0 deletions modules/Auth/include/AuthHandler.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -219,6 +219,7 @@
int used_for_transaction(const std::vector<int>& connectors, const std::string& id_token);
bool is_token_already_in_process(const std::string& id_token, const std::vector<int>& referenced_connectors);
bool any_connector_available(const std::vector<int>& connectors);
bool any_parent_id_present(const std::vector<int> connector_ids);

Check warning on line 222 in modules/Auth/include/AuthHandler.hpp

View check run for this annotation

Codacy Production / Codacy Static Code Analysis

modules/Auth/include/AuthHandler.hpp#L222

Function parameter 'connector_ids' should be passed by const reference.
bool equals_master_pass_group_id(const std::optional<types::authorization::IdToken> parent_id_token);

TokenHandlingResult handle_token(const ProvidedIdToken& provided_token);
Expand Down
7 changes: 7 additions & 0 deletions modules/Auth/include/ReservationHandler.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,13 @@ class ReservationHandler {
bool matches_reserved_identifier(int connector, const std::string& id_token,
std::optional<std::string> parent_id_token);

/**
* @brief Functions check if reservation at the given \p connector contains a parent_id
* @param connector
* @return true if reservation for \p connector exists and reservation contains a parent_id
*/
bool has_reservation_parent_id(int connector);

/**
* @brief Function tries to reserve the given \p connector using the given \p reservation
*
Expand Down
55 changes: 52 additions & 3 deletions modules/Auth/lib/AuthHandler.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -121,7 +121,44 @@ TokenHandlingResult AuthHandler::handle_token(const ProvidedIdToken& provided_to
}
}

// validate
/** Check if validation of token shall be requested. In some situations its not useful to validate
* the token because either no connector is available anyways or the provided token does not match a present
* reservation. Yet it has to be checked if the incoming token can be used to stop an active transaction or if the
* parent id of the token (that is only known after validation) can be used to stop or start transactions
*/

/* If no connector is available AND no parent_id is deposited at any connector and no master pass group id is
configured, we can immediately respond with NO_CONNECTOR_AVAILABLE */
if (!this->any_connector_available(referenced_connectors) and
!this->any_parent_id_present(referenced_connectors) and !this->master_pass_group_id.has_value()) {
return TokenHandlingResult::NO_CONNECTOR_AVAILABLE;
}

/* If all connectors are reserved and the given identifier doesnt match any reserved identifier and no parent id is
* deposited for a reservation, we can immediately respond with NO_CONNECTOR_AVAILABLE */
bool all_connectors_reserved_and_tag_does_not_match = true;
for (const auto connector_id : referenced_connectors) {
const auto connector = this->connectors.at(connector_id)->connector;
if (!connector.reserved) {
all_connectors_reserved_and_tag_does_not_match = false;
break;
}
if (this->reservation_handler.matches_reserved_identifier(connector_id, provided_token.id_token.value,
std::nullopt)) {
all_connectors_reserved_and_tag_does_not_match = false;
break;
}
if (this->reservation_handler.has_reservation_parent_id(connector_id)) {
all_connectors_reserved_and_tag_does_not_match = false;
break;
}
}

if (all_connectors_reserved_and_tag_does_not_match) {
return TokenHandlingResult::NO_CONNECTOR_AVAILABLE;
}

// Validate the provided token using the available validators
std::vector<ValidationResult> validation_results;
// only validate if token is not prevalidated
if (provided_token.prevalidated && provided_token.prevalidated.value()) {
Expand Down Expand Up @@ -349,6 +386,18 @@ bool AuthHandler::any_connector_available(const std::vector<int>& connector_ids)
return false;
}

bool AuthHandler::any_parent_id_present(const std::vector<int> connector_ids) {
for (const auto connector_id : connector_ids) {
if (this->connectors.at(connector_id)->connector.identifier.has_value() and
this->connectors.at(connector_id)->connector.identifier.value().parent_id_token.has_value()) {
EVLOG_debug << "Parent id is currently present";
return true;
}
}
EVLOG_debug << "No parent id is currently present";
return false;
}

bool AuthHandler::equals_master_pass_group_id(const std::optional<types::authorization::IdToken> parent_id_token) {
if (!this->master_pass_group_id.has_value()) {
return false;
Expand Down Expand Up @@ -414,8 +463,8 @@ int AuthHandler::select_connector(const std::vector<int>& connectors) {
// an EV has been plugged in yet at the referenced connectors
return this->get_latest_plugin(connectors);
} else {
// no EV has been plugged in yet at the referenced connectors; choosing the first one where no transaction
// is active
// no EV has been plugged in yet at the referenced connectors; choosing the first one where no
// transaction is active
for (const auto connector_id : connectors) {
const auto connector = this->connectors.at(connector_id)->connector;
if (!connector.transaction_active) {
Expand Down
7 changes: 7 additions & 0 deletions modules/Auth/lib/ReservationHandler.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,13 @@ bool ReservationHandler::matches_reserved_identifier(int connector, const std::s
parent_id_token.value() == this->reservations[connector].parent_id_token.value());
}

bool ReservationHandler::has_reservation_parent_id(int connector) {
if (!this->reservations.count(connector)) {
return false;
}
return this->reservations.at(connector).parent_id_token.has_value();
}

types::reservation::ReservationResult ReservationHandler::reserve(int connector, const ConnectorState& state,
bool is_reservable,
const types::reservation::Reservation& reservation) {
Expand Down
Loading