Add Redis Sentinel based database discovery
[ric-plt/sdl.git] / src / asyncstorageimpl.cpp
1 /*
2    Copyright (c) 2018-2019 Nokia.
3
4    Licensed under the Apache License, Version 2.0 (the "License");
5    you may not use this file except in compliance with the License.
6    You may obtain a copy of the License at
7
8        http://www.apache.org/licenses/LICENSE-2.0
9
10    Unless required by applicable law or agreed to in writing, software
11    distributed under the License is distributed on an "AS IS" BASIS,
12    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13    See the License for the specific language governing permissions and
14    limitations under the License.
15 */
16
17 #include "config.h"
18 #include "private/error.hpp"
19 #include "private/abort.hpp"
20 #include "private/asyncstorageimpl.hpp"
21 #include "private/configurationreader.hpp"
22 #include "private/asyncdummystorage.hpp"
23 #include "private/engine.hpp"
24 #include "private/logger.hpp"
25 #if HAVE_REDIS
26 #include "private/redis/asyncredisstorage.hpp"
27 #endif
28
29 using namespace shareddatalayer;
30 using namespace shareddatalayer::redis;
31
32 namespace
33 {
34         std::shared_ptr<AsyncDatabaseDiscovery> asyncDatabaseDiscoveryCreator(std::shared_ptr<Engine> engine,
35                                                                               const DatabaseConfiguration& databaseConfiguration,
36                                                                               std::shared_ptr<Logger> logger)
37         {
38             return AsyncDatabaseDiscovery::create(engine,
39                                                   boost::none,
40                                                   databaseConfiguration,
41                                                   logger);
42         }
43 }
44
45 AsyncStorageImpl::AsyncStorageImpl(std::shared_ptr<Engine> engine,
46                                    const boost::optional<PublisherId>& pId,
47                                    std::shared_ptr<Logger> logger):
48     engine(engine),
49     databaseConfiguration(std::make_shared<DatabaseConfigurationImpl>()),
50     namespaceConfigurations(std::make_shared<NamespaceConfigurationsImpl>()),
51     publisherId(pId),
52     logger(logger),
53     asyncDatabaseDiscoveryCreator(::asyncDatabaseDiscoveryCreator)
54 {
55     ConfigurationReader configurationReader(logger);
56     configurationReader.readDatabaseConfiguration(std::ref(*databaseConfiguration));
57     configurationReader.readNamespaceConfigurations(std::ref(*namespaceConfigurations));
58 }
59
60 // Meant for UT usage
61 AsyncStorageImpl::AsyncStorageImpl(std::shared_ptr<Engine> engine,
62                                    const boost::optional<PublisherId>& pId,
63                                    std::shared_ptr<DatabaseConfiguration> databaseConfiguration,
64                                    std::shared_ptr<NamespaceConfigurations> namespaceConfigurations,
65                                    std::shared_ptr<Logger> logger,
66                                    const AsyncDatabaseDiscoveryCreator& asyncDatabaseDiscoveryCreator):
67     engine(engine),
68     databaseConfiguration(databaseConfiguration),
69     namespaceConfigurations(namespaceConfigurations),
70     publisherId(pId),
71     logger(logger),
72     asyncDatabaseDiscoveryCreator(asyncDatabaseDiscoveryCreator)
73 {
74 }
75
76 AsyncStorage& AsyncStorageImpl::getRedisHandler()
77 {
78 #if HAVE_REDIS
79     static AsyncRedisStorage redisHandler{engine,
80                                           asyncDatabaseDiscoveryCreator(
81                                               engine,
82                                               std::ref(*databaseConfiguration),
83                                               logger),
84                                           publisherId,
85                                           namespaceConfigurations,
86                                           logger};
87
88     return redisHandler;
89 #else
90     logger->error() << "Redis operations cannot be performed, Redis not enabled";
91     SHAREDDATALAYER_ABORT("Invalid configuration.");
92 #endif
93 }
94
95 AsyncStorage& AsyncStorageImpl::getDummyHandler()
96 {
97     static AsyncDummyStorage dummyHandler{engine};
98     return dummyHandler;
99 }
100
101 AsyncStorage& AsyncStorageImpl::getOperationHandler(const std::string& ns)
102 {
103     if (namespaceConfigurations->isDbBackendUseEnabled(ns))
104         return getRedisHandler();
105
106     return getDummyHandler();
107 }
108
109 int AsyncStorageImpl::fd() const
110 {
111     return engine->fd();
112 }
113
114 void AsyncStorageImpl::handleEvents()
115 {
116     engine->handleEvents();
117 }
118
119 void AsyncStorageImpl::waitReadyAsync(const Namespace& ns,
120                                       const ReadyAck& readyAck)
121 {
122     getOperationHandler(ns).waitReadyAsync(ns, readyAck);
123 }
124
125 void AsyncStorageImpl::setAsync(const Namespace& ns,
126                                 const DataMap& dataMap,
127                                 const ModifyAck& modifyAck)
128 {
129     getOperationHandler(ns).setAsync(ns, dataMap, modifyAck);
130 }
131
132 void AsyncStorageImpl::setIfAsync(const Namespace& ns,
133                                   const Key& key,
134                                   const Data& oldData,
135                                   const Data& newData,
136                                   const ModifyIfAck& modifyIfAck)
137 {
138     getOperationHandler(ns).setIfAsync(ns, key, oldData, newData, modifyIfAck);
139 }
140
141 void AsyncStorageImpl::removeIfAsync(const Namespace& ns,
142                                      const Key& key,
143                                      const Data& data,
144                                      const ModifyIfAck& modifyIfAck)
145 {
146     getOperationHandler(ns).removeIfAsync(ns, key, data, modifyIfAck);
147 }
148
149 void AsyncStorageImpl::setIfNotExistsAsync(const Namespace& ns,
150                                            const Key& key,
151                                            const Data& data,
152                                            const ModifyIfAck& modifyIfAck)
153 {
154     getOperationHandler(ns).setIfNotExistsAsync(ns, key, data, modifyIfAck);
155 }
156
157 void AsyncStorageImpl::getAsync(const Namespace& ns,
158                                 const Keys& keys,
159                                 const GetAck& getAck)
160 {
161     getOperationHandler(ns).getAsync(ns, keys, getAck);
162 }
163
164 void AsyncStorageImpl::removeAsync(const Namespace& ns,
165                                    const Keys& keys,
166                                    const ModifyAck& modifyAck)
167 {
168     getOperationHandler(ns).removeAsync(ns, keys, modifyAck);
169 }
170
171 void AsyncStorageImpl::findKeysAsync(const Namespace& ns,
172                                      const std::string& keyPrefix,
173                                      const FindKeysAck& findKeysAck)
174 {
175     getOperationHandler(ns).findKeysAsync(ns, keyPrefix, findKeysAck);
176 }
177
178 void AsyncStorageImpl::removeAllAsync(const Namespace& ns,
179                                        const ModifyAck& modifyAck)
180 {
181     getOperationHandler(ns).removeAllAsync(ns, modifyAck);
182 }