PLCnext API Documentation 25.0.2.69
ServiceManager.hpp
1
2//
3// Copyright Phoenix Contact GmbH & Co. KG
4//
6#pragma once
8#include "Arp/Base/Core/CommonTypeName.hxx"
9#include "Arp/Base/Rsc/Commons/Rsc.hpp"
10#include "Arp/Base/Rsc/Commons/IRscService.hpp"
11#include "Arp/Base/Commons/Exceptions/InvalidCastException.hpp"
12#include "Arp/Base/Commons/Exceptions/InvalidOperationException.hpp"
13
14// forwards
15namespace Arp::Base::Rsc::Commons::Services
16{
19}
20
21namespace Arp::Base::Rsc
22{
23
27
30class ARP_EXPORT ServiceManager
31{
32public: // forwards
33 class Impl;
34
35public: // construction
36 ServiceManager(void) = delete;
37
38public: // static service operations
39 template<class TService> static typename TService::Ptr GetService(void);
40 template<class TService> static typename TService::Ptr GetService(const char* serviceProviderName);
41 template<class TService> static bool TryGetService(typename TService::Ptr& result);
42 template<class TService> static bool TryGetService(const char* serviceProviderName, typename TService::Ptr& result);
43
44 template<class TService, class TServiceFactory> static void PublishService(void);
45 template<class TService, class TServiceFactory> static void PublishService(const char* serviceProviderName);
46
47 static void PublishComponentService(const char* componentName, const char* serviceName, IRscServiceFactory* pServiceFactory);
48
49public: // internal operations
50 static Impl& GetImpl(void);
51
52private: // methods
53 static IRscService::Ptr GetServiceInternal(IRscServiceProxyFactory& proxyFactory, const char* serviceProviderName = nullptr);
54 static void PublishServiceInternal(const char* serviceProviderName, const char* serviceName, IRscServiceFactory& serviceFactory);
55};
56
58// inline methods of class ServiceManager
59
64template<class TService>
65inline typename TService::Ptr ServiceManager::GetService()
66{
67 typename TService::Ptr result;
68 if (!ServiceManager::TryGetService<TService>(result))
69 {
70 throw InvalidOperationException("Could not retrieve service '{0}'.", TypeName<TService>());
71 }
72 return result;
73}
74
85template<class TService>
86inline typename TService::Ptr ServiceManager::GetService(const char* serviceProviderName)
87{
88 typename TService::Ptr result;
89 if (!ServiceManager::TryGetService<TService>(serviceProviderName, result))
90 {
91 throw InvalidOperationException("Could not retrieve service '{0}' from service provider '{1}'.", TypeName<TService>(), serviceProviderName);
92 }
93 return result;
94}
95
100template<class TService>
101inline bool ServiceManager::TryGetService(typename TService::Ptr& result)
102{
103 return ServiceManager::TryGetService<TService>("", result);
104}
105
115template<class TService>
116inline bool ServiceManager::TryGetService(const char* serviceProviderName, typename TService::Ptr& result)
117{
118 IRscService::Ptr servicePtr = ServiceManager::GetServiceInternal(TService::GetProxyFactory(), serviceProviderName);
119
120 if (servicePtr == nullptr)
121 {
122 return false; // not found
123 }
124 result = dynamic_pointer_cast<TService>(servicePtr);
125 if (result == nullptr)
126 {
127 // error: wrong type
128 throw InvalidCastException("The retrieved service does not implement service interface '{0}'.", TypeName<TService>());
129 }
130 // else
131 return true;
132}
133
138template<class TService, class TServiceFactory>
140{
141 String serviceProviderName = TServiceFactory::GetInstance().GetServiceProviderName();
142 ServiceManager::PublishServiceInternal(serviceProviderName, CommonTypeName<TService>().GetFullName(), TServiceFactory::GetInstance());
143}
144
153template<class TService, class TServiceFactory>
154inline void ServiceManager::PublishService(const char* serviceProviderName)
155{
156 ServiceManager::PublishServiceInternal(serviceProviderName, CommonTypeName<TService>().GetFullName(), TServiceFactory::GetInstance());
157}
158
159} // end of namespace Arp::Base::Rsc
This exception is thrown when an invalid cast occurs.
Definition: InvalidCastException.hpp:17
This exception is thrown when an operation cannot be executed because the related state is invalid.
Definition: InvalidOperationException.hpp:16
This (meta programming) class provides the type-name according the CLS (common language specification...
Definition: CommonTypeName.hxx:33
This class represents the Arp String. The implementation is based on std::string.
Definition: String.hpp:39
This (meta programming) class provides the C++ type-name of the as template argument passed type.
Definition: TypeName.hxx:20
This is the base interface of all Rsc services.
Definition: IRscService.hpp:22
std::shared_ptr< IRscService > Ptr
The shared_ptr type of IRscService.
Definition: IRscService.hpp:25
Interface for service factory classes to create instances of the service implementation,...
Definition: IRscServiceFactory.hpp:26
Interface for service proxy factories to create service proxies used by RSC clients.
Definition: IRscServiceProxyFactory.hpp:22
This class is used to publish and retrieve RSC services.
Definition: ServiceManager.hpp:31
static void PublishService(void)
Registers a RSC service.
Definition: ServiceManager.hpp:139
static bool TryGetService(typename TService::Ptr &result)
Tries to get a service of the service provider Arp.
Definition: ServiceManager.hpp:101
static TService::Ptr GetService(void)
Gets a RSC service. The service provider is determined by the proxy factory.
Definition: ServiceManager.hpp:65
ServiceManager(void)=delete
makes this class pure static