From ff181a89dee541f59535b0cd6a16647180f959da Mon Sep 17 00:00:00 2001 From: Konrad Breitsprecher Date: Fri, 20 Dec 2024 18:05:23 +0100 Subject: [PATCH 1/3] dev: public API to get parameters from a participant --- Demos/CMakeLists.txt | 1 + SilKit/IntegrationTests/CMakeLists.txt | 4 + .../IntegrationTests/Hourglass/MockCapi.cpp | 7 ++ .../IntegrationTests/Hourglass/MockCapi.hpp | 3 + .../IntegrationTests/ITest_GetParameter.cpp | 34 +++++++++ SilKit/include/silkit/capi/Parameters.h | 29 ++++++++ SilKit/include/silkit/capi/Participant.h | 19 +++++ SilKit/include/silkit/capi/SilKit.h | 1 + .../impl/participant/ParameterProvider.hpp | 74 +++++++++++++++++++ .../detail/impl/participant/Participant.hpp | 13 ++++ .../silkit/participant/IParticipant.hpp | 5 ++ .../include/silkit/participant/parameters.hpp | 23 ++++++ SilKit/source/capi/CMakeLists.txt | 1 + SilKit/source/capi/CapiParticipant.cpp | 15 ++++ SilKit/source/capi/Test_CapiGetParameter.cpp | 51 +++++++++++++ .../core/internal/IParticipantInternal.hpp | 3 + .../core/mock/participant/MockParticipant.hpp | 5 ++ .../source/core/participant/Participant.hpp | 4 + .../core/participant/Participant_impl.hpp | 17 +++++ 19 files changed, 309 insertions(+) create mode 100644 SilKit/IntegrationTests/ITest_GetParameter.cpp create mode 100644 SilKit/include/silkit/capi/Parameters.h create mode 100644 SilKit/include/silkit/detail/impl/participant/ParameterProvider.hpp create mode 100644 SilKit/include/silkit/participant/parameters.hpp create mode 100644 SilKit/source/capi/Test_CapiGetParameter.cpp diff --git a/Demos/CMakeLists.txt b/Demos/CMakeLists.txt index 86f910101..7f1d601c8 100755 --- a/Demos/CMakeLists.txt +++ b/Demos/CMakeLists.txt @@ -145,6 +145,7 @@ add_subdirectory(PubSub) add_subdirectory(Rpc) add_subdirectory(Benchmark) add_subdirectory(NetworkSimulator) +add_subdirectory(TimeSyncTest) message(STATUS "Demos available: ${demo_list}") ####################################################################################################################### diff --git a/SilKit/IntegrationTests/CMakeLists.txt b/SilKit/IntegrationTests/CMakeLists.txt index d0170b6d3..5a095edf7 100644 --- a/SilKit/IntegrationTests/CMakeLists.txt +++ b/SilKit/IntegrationTests/CMakeLists.txt @@ -127,6 +127,10 @@ add_silkit_test_to_executable(SilKitIntegrationTests SOURCES ITest_SimTask.cpp ) +add_silkit_test_to_executable(SilKitIntegrationTests + SOURCES ITest_GetParameter.cpp +) + add_silkit_test_to_executable(SilKitFunctionalTests SOURCES FTest_WallClockCoupling.cpp ) diff --git a/SilKit/IntegrationTests/Hourglass/MockCapi.cpp b/SilKit/IntegrationTests/Hourglass/MockCapi.cpp index 0ab83ff4b..24860a70e 100644 --- a/SilKit/IntegrationTests/Hourglass/MockCapi.cpp +++ b/SilKit/IntegrationTests/Hourglass/MockCapi.cpp @@ -770,6 +770,13 @@ extern "C" return globalCapi->SilKit_Participant_GetLogger(outLogger, participant); } + SilKit_ReturnCode SilKitCALL SilKit_Participant_GetParameter(const char** outParameterValue, + SilKit_Parameter parameter, + SilKit_Participant* participant) + { + return globalCapi->SilKit_Participant_GetParameter(outParameterValue, parameter, participant); + } + // ParticipantConfiguration SilKit_ReturnCode SilKitCALL SilKit_ParticipantConfiguration_FromString( diff --git a/SilKit/IntegrationTests/Hourglass/MockCapi.hpp b/SilKit/IntegrationTests/Hourglass/MockCapi.hpp index a348cd3e0..4d54b211e 100644 --- a/SilKit/IntegrationTests/Hourglass/MockCapi.hpp +++ b/SilKit/IntegrationTests/Hourglass/MockCapi.hpp @@ -415,6 +415,9 @@ class MockCapi MOCK_METHOD(SilKit_ReturnCode, SilKit_Participant_GetLogger, (SilKit_Logger * *outLogger, SilKit_Participant* participant)); + + MOCK_METHOD(SilKit_ReturnCode, SilKit_Participant_GetParameter, + (const char** outParameterValue, SilKit_Parameter parameter, SilKit_Participant* participant)); // ParticipantConfiguration diff --git a/SilKit/IntegrationTests/ITest_GetParameter.cpp b/SilKit/IntegrationTests/ITest_GetParameter.cpp new file mode 100644 index 000000000..fff541d65 --- /dev/null +++ b/SilKit/IntegrationTests/ITest_GetParameter.cpp @@ -0,0 +1,34 @@ +// SPDX-FileCopyrightText: 2023 Vector Informatik GmbH +// +// SPDX-License-Identifier: MIT + +#include +#include + +#include "gtest/gtest.h" +#include "SimTestHarness.hpp" + +namespace { +using namespace SilKit::Tests; + +struct ITest_GetParameter : public testing::Test +{ +}; + + +TEST_F(ITest_GetParameter, get_parameter_set_by_api) +{ + const std::string participantName = "P1"; + + SimTestHarnessArgs args; + args.deferParticipantCreation = true; + args.asyncParticipantNames = {participantName}; + //args.registry.listenUri = "silkit://127.0.0.1:0" + auto simTestHarness = std::make_unique(args); + + auto participant = simTestHarness->GetParticipant(participantName)->Participant(); + auto participantNameByGetParameter = participant->GetParameter(SilKit::Parameter::ParticipantName); + EXPECT_EQ(participantName, participantNameByGetParameter); +} + +} //end namespace diff --git a/SilKit/include/silkit/capi/Parameters.h b/SilKit/include/silkit/capi/Parameters.h new file mode 100644 index 000000000..06063b504 --- /dev/null +++ b/SilKit/include/silkit/capi/Parameters.h @@ -0,0 +1,29 @@ +// SPDX-FileCopyrightText: 2024 Vector Informatik GmbH +// +// SPDX-License-Identifier: MIT + +#pragma once +#include +#include "SilKitMacros.h" + +#pragma pack(push) +#pragma pack(8) + +SILKIT_BEGIN_DECLS + +/*! Internal parameter provider. */ +typedef struct SilKit_ParamterProvider SilKit_ParamterProvider; + +/*! A parameter set by an API call and/or the participant configuration. */ +typedef int16_t SilKit_Parameter; + +/*! An undefined parameter */ +#define SilKit_Parameter_Undefined ((SilKit_Parameter)0) +/*! The name of the participant */ +#define SilKit_Parameter_ParticipantName ((SilKit_Parameter)1) +/*! The registry URI */ +#define SilKit_Parameter_ReistryUri ((SilKit_Parameter)2) + +SILKIT_END_DECLS + +#pragma pack(pop) diff --git a/SilKit/include/silkit/capi/Participant.h b/SilKit/include/silkit/capi/Participant.h index f048b4294..7f1cc5e89 100644 --- a/SilKit/include/silkit/capi/Participant.h +++ b/SilKit/include/silkit/capi/Participant.h @@ -25,6 +25,7 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include "silkit/capi/SilKitMacros.h" #include "silkit/capi/Types.h" #include "silkit/capi/Logger.h" +#include "silkit/capi/Parameters.h" #pragma pack(push) #pragma pack(8) @@ -80,6 +81,24 @@ SilKitAPI SilKit_ReturnCode SilKitCALL SilKit_Participant_GetLogger(SilKit_Logge typedef SilKit_ReturnCode(SilKitFPTR* SilKit_Participant_GetLogger_t)(SilKit_Logger** outLogger, SilKit_Participant* participant); + +/*! \brief Retrieve a parameter from a participant. + * + * \param outParameterValue The string value of the parameter (out parameter). + * \param parameter The parameter to get. + * \param participant The participant to get the parameter from. + * + * Returns the current value of the given parameter. + * Useful for parameters that are passed to the participant via the API and the participant configuration. + */ +SilKitAPI SilKit_ReturnCode SilKitCALL SilKit_Participant_GetParameter(const char** outParameterValue, + SilKit_Parameter parameter, + SilKit_Participant* participant); + +typedef SilKit_ReturnCode(SilKitFPTR* SilKit_Participant_GetParameter_t)(const char** outParameterValue, + SilKit_Parameter parameter, + SilKit_Participant* participant); + SILKIT_END_DECLS #pragma pack(pop) diff --git a/SilKit/include/silkit/capi/SilKit.h b/SilKit/include/silkit/capi/SilKit.h index 039021d99..1e864b8c1 100644 --- a/SilKit/include/silkit/capi/SilKit.h +++ b/SilKit/include/silkit/capi/SilKit.h @@ -37,6 +37,7 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include "silkit/capi/Version.h" #include "silkit/capi/NetworkSimulator.h" #include "silkit/capi/EventProducer.h" +#include "silkit/capi/Parameters.h" SILKIT_BEGIN_DECLS diff --git a/SilKit/include/silkit/detail/impl/participant/ParameterProvider.hpp b/SilKit/include/silkit/detail/impl/participant/ParameterProvider.hpp new file mode 100644 index 000000000..55fb5d4a1 --- /dev/null +++ b/SilKit/include/silkit/detail/impl/participant/ParameterProvider.hpp @@ -0,0 +1,74 @@ +// Copyright (c) 2023 Vector Informatik GmbH +// +// Permission is hereby granted, free of charge, to any person obtaining +// a copy of this software and associated documentation files (the +// "Software"), to deal in the Software without restriction, including +// without limitation the rights to use, copy, modify, merge, publish, +// distribute, sublicense, and/or sell copies of the Software, and to +// permit persons to whom the Software is furnished to do so, subject to +// the following conditions: +// +// The above copyright notice and this permission notice shall be +// included in all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE +// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION +// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION +// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. + +#pragma once + +#include +#include "silkit/capi/Parameters.h" + +namespace SilKit { +DETAIL_SILKIT_DETAIL_VN_NAMESPACE_BEGIN +namespace Impl { + +class ParameterProvider +{ +public: + inline ParameterProvider(); + + inline ~ParameterProvider() = default; + + inline auto GetParameter(SilKit_Participant* participant, Parameter parameter) -> std::string; + +private: + SilKit_ParamterProvider* _parameterProvider{nullptr}; +}; + +} // namespace Impl +DETAIL_SILKIT_DETAIL_VN_NAMESPACE_CLOSE +} // namespace SilKit + + +// ================================================================================ +// Inline Implementations +// ================================================================================ + +#include "silkit/detail/impl/ThrowOnError.hpp" + +namespace SilKit { +DETAIL_SILKIT_DETAIL_VN_NAMESPACE_BEGIN +namespace Impl { + +ParameterProvider::ParameterProvider() +{ +} + +auto ParameterProvider::GetParameter(SilKit_Participant* participant, Parameter parameter) -> std::string +{ + const char* cParameterValue; + SilKit_Parameter cParameter = static_cast(parameter); + const auto returnCode = SilKit_Participant_GetParameter(&cParameterValue, cParameter, participant); + ThrowOnError(returnCode); + return std::string{cParameterValue}; +} + +} // namespace Impl +DETAIL_SILKIT_DETAIL_VN_NAMESPACE_CLOSE +} // namespace SilKit diff --git a/SilKit/include/silkit/detail/impl/participant/Participant.hpp b/SilKit/include/silkit/detail/impl/participant/Participant.hpp index a849ee248..19f596bf4 100644 --- a/SilKit/include/silkit/detail/impl/participant/Participant.hpp +++ b/SilKit/include/silkit/detail/impl/participant/Participant.hpp @@ -53,6 +53,8 @@ #include "silkit/detail/impl/netsim/NetworkSimulator.hpp" +#include "silkit/detail/impl/participant/ParameterProvider.hpp" + namespace SilKit { DETAIL_SILKIT_DETAIL_VN_NAMESPACE_BEGIN namespace Impl { @@ -100,6 +102,8 @@ class Participant : public SilKit::IParticipant inline auto GetLogger() -> SilKit::Services::Logging::ILogger* override; + inline auto GetParameter(SilKit::Parameter parameter) -> std::string override; + inline auto ExperimentalCreateNetworkSimulator() -> SilKit::Experimental::NetworkSimulation::INetworkSimulator*; inline auto ExperimentalCreateSystemController() @@ -141,6 +145,8 @@ class Participant : public SilKit::IParticipant std::unique_ptr _logger; std::unique_ptr _networkSimulator; + + std::unique_ptr _parameterProvider; }; } // namespace Impl @@ -160,6 +166,7 @@ Participant::Participant(SilKit_Participant* participant) : _participant{participant} { _logger = std::make_unique(_participant); + _parameterProvider = std::make_unique(); } Participant::~Participant() @@ -241,6 +248,12 @@ auto Participant::GetLogger() -> SilKit::Services::Logging::ILogger* return _logger.get(); } + +auto Participant::GetParameter(SilKit::Parameter parameter) -> std::string +{ + return _parameterProvider->GetParameter(_participant, parameter); +} + auto Participant::ExperimentalCreateSystemController() -> SilKit::Experimental::Services::Orchestration::ISystemController* { diff --git a/SilKit/include/silkit/participant/IParticipant.hpp b/SilKit/include/silkit/participant/IParticipant.hpp index bedb8ecfd..ef7f419c5 100644 --- a/SilKit/include/silkit/participant/IParticipant.hpp +++ b/SilKit/include/silkit/participant/IParticipant.hpp @@ -35,6 +35,8 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include "silkit/services/rpc/RpcSpec.hpp" #include "silkit/services/rpc/RpcDatatypes.hpp" +#include "silkit/participant/parameters.hpp" + namespace SilKit { /*! \brief Communication interface to be used by SIL Kit participants @@ -99,6 +101,9 @@ class IParticipant //! \brief Return the ILogger at this SIL Kit participant. virtual auto GetLogger() -> Services::Logging::ILogger* = 0; + + //! \brief Get a parameter set by an API call and/or the participant configuration. + virtual auto GetParameter(SilKit::Parameter parameter) -> std::string = 0; }; } // namespace SilKit diff --git a/SilKit/include/silkit/participant/parameters.hpp b/SilKit/include/silkit/participant/parameters.hpp new file mode 100644 index 000000000..e440c366c --- /dev/null +++ b/SilKit/include/silkit/participant/parameters.hpp @@ -0,0 +1,23 @@ +// SPDX-FileCopyrightText: 2024 Vector Informatik GmbH +// +// SPDX-License-Identifier: MIT + +#pragma once + +#include "silkit/capi/Parameters.h" + +namespace SilKit { + +// note: never reuse old numbers! +//! \brief Available parameters to query +enum class Parameter : SilKit_Parameter +{ + //! An undefined parameter + Undefined = SilKit_Parameter_Undefined, + //! The name of the participant + ParticipantName = SilKit_Parameter_ParticipantName, + //! The registry URI + RegistryUri = SilKit_Parameter_ReistryUri, +}; + +} // namespace SilKit diff --git a/SilKit/source/capi/CMakeLists.txt b/SilKit/source/capi/CMakeLists.txt index 08be2cf39..c55605649 100644 --- a/SilKit/source/capi/CMakeLists.txt +++ b/SilKit/source/capi/CMakeLists.txt @@ -65,4 +65,5 @@ add_silkit_test_to_executable(SilKitUnitTests SOURCES Test_CapiLin.cpp LIBS S_Si add_silkit_test_to_executable(SilKitUnitTests SOURCES Test_CapiSymbols.cpp LIBS S_SilKitImpl) add_silkit_test_to_executable(SilKitUnitTests SOURCES Test_CapiNetSim.cpp LIBS S_SilKitImpl I_SilKit_Core_Mock_Participant) add_silkit_test_to_executable(SilKitUnitTests SOURCES Test_CapiExceptions.cpp LIBS S_SilKitImpl) +add_silkit_test_to_executable(SilKitUnitTests SOURCES Test_CapiGetParameter.cpp LIBS S_SilKitImpl) diff --git a/SilKit/source/capi/CapiParticipant.cpp b/SilKit/source/capi/CapiParticipant.cpp index 86932177d..22e8b01bf 100644 --- a/SilKit/source/capi/CapiParticipant.cpp +++ b/SilKit/source/capi/CapiParticipant.cpp @@ -27,6 +27,7 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include "silkit/SilKit.hpp" #include "silkit/services/logging/ILogger.hpp" #include "silkit/services/orchestration/all.hpp" +#include "silkit/participant/parameters.hpp" #include "CapiImpl.hpp" #include "TypeConversion.hpp" @@ -102,6 +103,20 @@ try } CAPI_CATCH_EXCEPTIONS +SilKit_ReturnCode SilKitCALL SilKit_Participant_GetParameter(const char** outParameterValue, SilKit_Parameter parameter, + SilKit_Participant* participant) +try +{ + ASSERT_VALID_OUT_PARAMETER(outParameterValue); + ASSERT_VALID_POINTER_PARAMETER(participant); + + auto cppParticipant = reinterpret_cast(participant); + auto cppParameter = static_cast(parameter); + *outParameterValue = cppParticipant->GetParameter(cppParameter).c_str(); + return SilKit_ReturnCode_SUCCESS; +} +CAPI_CATCH_EXCEPTIONS + SilKit_ReturnCode SilKitCALL SilKit_ParticipantConfiguration_FromString( SilKit_ParticipantConfiguration** outParticipantConfiguration, const char* participantConfigurationString) diff --git a/SilKit/source/capi/Test_CapiGetParameter.cpp b/SilKit/source/capi/Test_CapiGetParameter.cpp new file mode 100644 index 000000000..75e34b209 --- /dev/null +++ b/SilKit/source/capi/Test_CapiGetParameter.cpp @@ -0,0 +1,51 @@ +// SPDX-FileCopyrightText: 2024 Vector Informatik GmbH +// +// SPDX-License-Identifier: MIT +#include "gtest/gtest.h" +#include "gmock/gmock.h" +#include "silkit/capi/SilKit.h" + +#include "MockParticipant.hpp" + +namespace { + +using SilKit::Core::Tests::DummyParticipant; + +class MockParticipant : public SilKit::Core::Tests::DummyParticipant +{ +public: + MOCK_METHOD(std::string, GetParameter, (SilKit::Parameter /*parameter*/), (override)); +}; + +class Test_CapiGetParameter : public testing::Test +{ +public: + MockParticipant mockParticipant; + Test_CapiGetParameter() {} +}; + +TEST_F(Test_CapiGetParameter, getparameter_bad_params) +{ + SilKit_ReturnCode returnCode; + auto cMockParticipant = (SilKit_Participant*)&mockParticipant; + const char* parameterValue{nullptr}; + + returnCode = SilKit_Participant_GetParameter(nullptr, SilKit_Parameter_ParticipantName, cMockParticipant); + EXPECT_EQ(returnCode, SilKit_ReturnCode_BADPARAMETER); + + returnCode = SilKit_Participant_GetParameter(¶meterValue, SilKit_Parameter_ParticipantName, nullptr); + EXPECT_EQ(returnCode, SilKit_ReturnCode_BADPARAMETER); +} + +TEST_F(Test_CapiGetParameter, getparameter_function_mapping) +{ + SilKit_ReturnCode returnCode; + auto cMockParticipant = (SilKit_Participant*)&mockParticipant; + const char* parameterValue{nullptr}; + + EXPECT_CALL(mockParticipant, GetParameter(SilKit::Parameter::ParticipantName)).Times(testing::Exactly(1)); + returnCode = SilKit_Participant_GetParameter(¶meterValue, SilKit_Parameter_ParticipantName, cMockParticipant); + EXPECT_EQ(returnCode, SilKit_ReturnCode_SUCCESS); +} + +} // namespace diff --git a/SilKit/source/core/internal/IParticipantInternal.hpp b/SilKit/source/core/internal/IParticipantInternal.hpp index 9940a4474..9442dd484 100644 --- a/SilKit/source/core/internal/IParticipantInternal.hpp +++ b/SilKit/source/core/internal/IParticipantInternal.hpp @@ -307,6 +307,9 @@ class IParticipantInternal : public IParticipant //! \brief Return the ILogger at this SIL Kit participant. virtual auto GetLogger() -> Services::Logging::ILogger* = 0; + //! \brief Get a parameter set by an API call and/or the participant configuration. + virtual auto GetParameter(Parameter parameter) -> std::string = 0; + //! \brief Return the LifecycleService at this SIL Kit participant. virtual auto GetLifecycleService() -> Services::Orchestration::ILifecycleService* = 0; diff --git a/SilKit/source/core/mock/participant/MockParticipant.hpp b/SilKit/source/core/mock/participant/MockParticipant.hpp index f01938470..1678f19ca 100644 --- a/SilKit/source/core/mock/participant/MockParticipant.hpp +++ b/SilKit/source/core/mock/participant/MockParticipant.hpp @@ -346,6 +346,11 @@ class DummyParticipant : public IParticipantInternal return &logger; } + auto GetParameter(Parameter) -> std::string override + { + return ""; + } + void RegisterSimulator(Core::ISimulator*, std::string, Experimental::NetworkSimulation::SimulatedNetworkType) override { diff --git a/SilKit/source/core/participant/Participant.hpp b/SilKit/source/core/participant/Participant.hpp index 47955a87e..a8feca20d 100644 --- a/SilKit/source/core/participant/Participant.hpp +++ b/SilKit/source/core/participant/Participant.hpp @@ -31,6 +31,7 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */ #include "silkit/services/all.hpp" #include "silkit/services/logging/ILogger.hpp" +#include "silkit/participant/parameters.hpp" #include "ParticipantConfiguration.hpp" #include "ReplayScheduler.hpp" @@ -165,6 +166,9 @@ class Participant : public IParticipantInternal auto GetMetricsManager() -> IMetricsManager* override; auto GetLogger() -> Services::Logging::ILogger* override; + + auto GetParameter(Parameter parameter) -> std::string override; + auto CreateLifecycleService(Services::Orchestration::LifecycleConfiguration startConfiguration) -> Services::Orchestration::ILifecycleService* override; auto GetLifecycleService() -> Services::Orchestration::ILifecycleService* override; diff --git a/SilKit/source/core/participant/Participant_impl.hpp b/SilKit/source/core/participant/Participant_impl.hpp index 2364e1b6a..d6116b424 100644 --- a/SilKit/source/core/participant/Participant_impl.hpp +++ b/SilKit/source/core/participant/Participant_impl.hpp @@ -1048,6 +1048,23 @@ auto Participant::GetLoggerInternal() -> Services::Logging::I return _logger.get(); } +template +auto Participant::GetParameter(Parameter parameter) -> std::string +{ + switch (parameter) + { + case Parameter::ParticipantName: + return GetParticipantName(); + break; + case Parameter::RegistryUri: + return GetRegistryUri(); + break; + } + + throw SilKit::SilKitError("Unknown parameter."); +} + + template void Participant::SendMsg(const IServiceEndpoint* from, const Can::WireCanFrameEvent& msg) { From e7cdd39925545dee9feae6786a5bbbfc32a9df8b Mon Sep 17 00:00:00 2001 From: Konrad Breitsprecher Date: Tue, 7 Jan 2025 11:29:02 +0100 Subject: [PATCH 2/3] dev: Hourglass storage for parameter values; integration tests --- .../IntegrationTests/ITest_GetParameter.cpp | 60 +++++++++++++++---- .../impl/participant/ParameterProvider.hpp | 9 +-- .../detail/impl/participant/Participant.hpp | 4 +- .../silkit/participant/IParticipant.hpp | 2 +- SilKit/source/capi/Test_CapiGetParameter.cpp | 2 +- .../core/internal/IParticipantInternal.hpp | 2 +- .../core/mock/participant/MockParticipant.hpp | 4 +- .../source/core/participant/Participant.hpp | 2 +- .../core/participant/Participant_impl.hpp | 2 +- 9 files changed, 62 insertions(+), 25 deletions(-) diff --git a/SilKit/IntegrationTests/ITest_GetParameter.cpp b/SilKit/IntegrationTests/ITest_GetParameter.cpp index fff541d65..aa5202694 100644 --- a/SilKit/IntegrationTests/ITest_GetParameter.cpp +++ b/SilKit/IntegrationTests/ITest_GetParameter.cpp @@ -6,29 +6,65 @@ #include #include "gtest/gtest.h" -#include "SimTestHarness.hpp" +#include "silkit/vendor/CreateSilKitRegistry.hpp" +#include "silkit/SilKit.hpp" namespace { -using namespace SilKit::Tests; struct ITest_GetParameter : public testing::Test { -}; + void checkGetParameterValues(SilKit::IParticipant* participant, std::unordered_map expected) + { + for (auto it : expected) + { + EXPECT_EQ(it.second, participant->GetParameter(it.first)); + } + } + + const std::string _registryUriAnyPort = "silkit://127.0.0.1:0"; +}; +// Check that GetParameter return the values set via api TEST_F(ITest_GetParameter, get_parameter_set_by_api) { - const std::string participantName = "P1"; + const std::string participantNameByApi = "P1"; + + auto emptyParticipantConfig = SilKit::Config::ParticipantConfigurationFromString(""); + + auto registry = SilKit::Vendor::Vector::CreateSilKitRegistry(emptyParticipantConfig); + auto registryUriByApi = registry->StartListening(_registryUriAnyPort); + + auto participant = SilKit::CreateParticipant(emptyParticipantConfig, participantNameByApi, registryUriByApi); + + checkGetParameterValues(participant.get(), {{SilKit::Parameter::ParticipantName, participantNameByApi}, + {SilKit::Parameter::RegistryUri, registryUriByApi}}); +} + +// Config values take precedence over api values +// Check that GetParameter actually return the config values if both are set +TEST_F(ITest_GetParameter, get_parameter_set_by_config) +{ + const std::string participantNameByApi = "P2"; + const std::string registryUriByApi = "silkit://127.0.0.42:0"; + + const std::string participantNameByConfig = "P1"; + + auto emptyParticipantConfig = SilKit::Config::ParticipantConfigurationFromString(""); + + auto registry = SilKit::Vendor::Vector::CreateSilKitRegistry(emptyParticipantConfig); + auto registryUriByConfig = registry->StartListening(_registryUriAnyPort); + + std::ostringstream ss; + ss << R"({ "ParticipantName": ")" << participantNameByConfig << R"(", "Middleware": { "RegistryUri": ")" + << registryUriByConfig << R"(" }})"; + auto participantConfig = SilKit::Config::ParticipantConfigurationFromString(ss.str()); + + auto participant = SilKit::CreateParticipant(participantConfig, participantNameByApi, registryUriByApi); - SimTestHarnessArgs args; - args.deferParticipantCreation = true; - args.asyncParticipantNames = {participantName}; - //args.registry.listenUri = "silkit://127.0.0.1:0" - auto simTestHarness = std::make_unique(args); + checkGetParameterValues(participant.get(), {{SilKit::Parameter::ParticipantName, participantNameByConfig}, + {SilKit::Parameter::RegistryUri, registryUriByConfig}}); - auto participant = simTestHarness->GetParticipant(participantName)->Participant(); - auto participantNameByGetParameter = participant->GetParameter(SilKit::Parameter::ParticipantName); - EXPECT_EQ(participantName, participantNameByGetParameter); } } //end namespace diff --git a/SilKit/include/silkit/detail/impl/participant/ParameterProvider.hpp b/SilKit/include/silkit/detail/impl/participant/ParameterProvider.hpp index 55fb5d4a1..c30020060 100644 --- a/SilKit/include/silkit/detail/impl/participant/ParameterProvider.hpp +++ b/SilKit/include/silkit/detail/impl/participant/ParameterProvider.hpp @@ -35,10 +35,10 @@ class ParameterProvider inline ~ParameterProvider() = default; - inline auto GetParameter(SilKit_Participant* participant, Parameter parameter) -> std::string; + inline auto GetParameter(SilKit_Participant* participant, Parameter parameter) -> const std::string&; private: - SilKit_ParamterProvider* _parameterProvider{nullptr}; + std::unordered_map _parameterValues; }; } // namespace Impl @@ -60,13 +60,14 @@ ParameterProvider::ParameterProvider() { } -auto ParameterProvider::GetParameter(SilKit_Participant* participant, Parameter parameter) -> std::string +auto ParameterProvider::GetParameter(SilKit_Participant* participant, Parameter parameter) -> const std::string& { const char* cParameterValue; SilKit_Parameter cParameter = static_cast(parameter); const auto returnCode = SilKit_Participant_GetParameter(&cParameterValue, cParameter, participant); + _parameterValues[parameter] = std::string(cParameterValue); ThrowOnError(returnCode); - return std::string{cParameterValue}; + return _parameterValues[parameter]; } } // namespace Impl diff --git a/SilKit/include/silkit/detail/impl/participant/Participant.hpp b/SilKit/include/silkit/detail/impl/participant/Participant.hpp index 19f596bf4..0f99d8992 100644 --- a/SilKit/include/silkit/detail/impl/participant/Participant.hpp +++ b/SilKit/include/silkit/detail/impl/participant/Participant.hpp @@ -102,7 +102,7 @@ class Participant : public SilKit::IParticipant inline auto GetLogger() -> SilKit::Services::Logging::ILogger* override; - inline auto GetParameter(SilKit::Parameter parameter) -> std::string override; + inline auto GetParameter(SilKit::Parameter parameter) -> const std::string& override; inline auto ExperimentalCreateNetworkSimulator() -> SilKit::Experimental::NetworkSimulation::INetworkSimulator*; @@ -249,7 +249,7 @@ auto Participant::GetLogger() -> SilKit::Services::Logging::ILogger* } -auto Participant::GetParameter(SilKit::Parameter parameter) -> std::string +auto Participant::GetParameter(SilKit::Parameter parameter) -> const std::string& { return _parameterProvider->GetParameter(_participant, parameter); } diff --git a/SilKit/include/silkit/participant/IParticipant.hpp b/SilKit/include/silkit/participant/IParticipant.hpp index ef7f419c5..de24c0366 100644 --- a/SilKit/include/silkit/participant/IParticipant.hpp +++ b/SilKit/include/silkit/participant/IParticipant.hpp @@ -103,7 +103,7 @@ class IParticipant virtual auto GetLogger() -> Services::Logging::ILogger* = 0; //! \brief Get a parameter set by an API call and/or the participant configuration. - virtual auto GetParameter(SilKit::Parameter parameter) -> std::string = 0; + virtual auto GetParameter(SilKit::Parameter parameter) -> const std::string& = 0; }; } // namespace SilKit diff --git a/SilKit/source/capi/Test_CapiGetParameter.cpp b/SilKit/source/capi/Test_CapiGetParameter.cpp index 75e34b209..296a0d66b 100644 --- a/SilKit/source/capi/Test_CapiGetParameter.cpp +++ b/SilKit/source/capi/Test_CapiGetParameter.cpp @@ -14,7 +14,7 @@ using SilKit::Core::Tests::DummyParticipant; class MockParticipant : public SilKit::Core::Tests::DummyParticipant { public: - MOCK_METHOD(std::string, GetParameter, (SilKit::Parameter /*parameter*/), (override)); + MOCK_METHOD(const std::string&, GetParameter, (SilKit::Parameter /*parameter*/), (override)); }; class Test_CapiGetParameter : public testing::Test diff --git a/SilKit/source/core/internal/IParticipantInternal.hpp b/SilKit/source/core/internal/IParticipantInternal.hpp index 9442dd484..f73f109e1 100644 --- a/SilKit/source/core/internal/IParticipantInternal.hpp +++ b/SilKit/source/core/internal/IParticipantInternal.hpp @@ -308,7 +308,7 @@ class IParticipantInternal : public IParticipant virtual auto GetLogger() -> Services::Logging::ILogger* = 0; //! \brief Get a parameter set by an API call and/or the participant configuration. - virtual auto GetParameter(Parameter parameter) -> std::string = 0; + virtual auto GetParameter(Parameter parameter) -> const std::string& = 0; //! \brief Return the LifecycleService at this SIL Kit participant. virtual auto GetLifecycleService() -> Services::Orchestration::ILifecycleService* = 0; diff --git a/SilKit/source/core/mock/participant/MockParticipant.hpp b/SilKit/source/core/mock/participant/MockParticipant.hpp index 1678f19ca..b6abfc4a1 100644 --- a/SilKit/source/core/mock/participant/MockParticipant.hpp +++ b/SilKit/source/core/mock/participant/MockParticipant.hpp @@ -346,9 +346,9 @@ class DummyParticipant : public IParticipantInternal return &logger; } - auto GetParameter(Parameter) -> std::string override + auto GetParameter(Parameter parameter) -> const std::string& override { - return ""; + return nullptr; } void RegisterSimulator(Core::ISimulator*, std::string, diff --git a/SilKit/source/core/participant/Participant.hpp b/SilKit/source/core/participant/Participant.hpp index a8feca20d..c214a5ba0 100644 --- a/SilKit/source/core/participant/Participant.hpp +++ b/SilKit/source/core/participant/Participant.hpp @@ -167,7 +167,7 @@ class Participant : public IParticipantInternal auto GetLogger() -> Services::Logging::ILogger* override; - auto GetParameter(Parameter parameter) -> std::string override; + auto GetParameter(Parameter parameter) -> const std::string& override; auto CreateLifecycleService(Services::Orchestration::LifecycleConfiguration startConfiguration) -> Services::Orchestration::ILifecycleService* override; diff --git a/SilKit/source/core/participant/Participant_impl.hpp b/SilKit/source/core/participant/Participant_impl.hpp index d6116b424..cc7d0eaae 100644 --- a/SilKit/source/core/participant/Participant_impl.hpp +++ b/SilKit/source/core/participant/Participant_impl.hpp @@ -1049,7 +1049,7 @@ auto Participant::GetLoggerInternal() -> Services::Logging::I } template -auto Participant::GetParameter(Parameter parameter) -> std::string +auto Participant::GetParameter(Parameter parameter) -> const std::string& { switch (parameter) { From 77bc301b74a6ccc06a7847693f311efd074594d8 Mon Sep 17 00:00:00 2001 From: Konrad Breitsprecher Date: Tue, 7 Jan 2025 13:02:56 +0100 Subject: [PATCH 3/3] fixup: Exclude unused demo; new license --- Demos/CMakeLists.txt | 1 - .../impl/participant/ParameterProvider.hpp | 21 ++----------------- 2 files changed, 2 insertions(+), 20 deletions(-) diff --git a/Demos/CMakeLists.txt b/Demos/CMakeLists.txt index 7f1d601c8..86f910101 100755 --- a/Demos/CMakeLists.txt +++ b/Demos/CMakeLists.txt @@ -145,7 +145,6 @@ add_subdirectory(PubSub) add_subdirectory(Rpc) add_subdirectory(Benchmark) add_subdirectory(NetworkSimulator) -add_subdirectory(TimeSyncTest) message(STATUS "Demos available: ${demo_list}") ####################################################################################################################### diff --git a/SilKit/include/silkit/detail/impl/participant/ParameterProvider.hpp b/SilKit/include/silkit/detail/impl/participant/ParameterProvider.hpp index c30020060..3bdadb5a9 100644 --- a/SilKit/include/silkit/detail/impl/participant/ParameterProvider.hpp +++ b/SilKit/include/silkit/detail/impl/participant/ParameterProvider.hpp @@ -1,23 +1,6 @@ -// Copyright (c) 2023 Vector Informatik GmbH +// SPDX-FileCopyrightText: 2024 Vector Informatik GmbH // -// Permission is hereby granted, free of charge, to any person obtaining -// a copy of this software and associated documentation files (the -// "Software"), to deal in the Software without restriction, including -// without limitation the rights to use, copy, modify, merge, publish, -// distribute, sublicense, and/or sell copies of the Software, and to -// permit persons to whom the Software is furnished to do so, subject to -// the following conditions: -// -// The above copyright notice and this permission notice shall be -// included in all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, -// EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF -// MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND -// NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE -// LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION -// OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION -// WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. +// SPDX-License-Identifier: MIT #pragma once