BeeeOn Gateway  v2020.3.1-2-g6f737dc
Platform to interconnect the IoT world
DeviceManager.h
1 #pragma once
2 
3 #include <set>
4 #include <typeindex>
5 
6 #include <Poco/AtomicCounter.h>
7 #include <Poco/Clock.h>
8 #include <Poco/Mutex.h>
9 #include <Poco/SharedPtr.h>
10 
11 #include "commands/DeviceAcceptCommand.h"
12 #include "commands/DeviceSetValueCommand.h"
13 #include "commands/DeviceUnpairCommand.h"
14 #include "commands/DeviceSearchCommand.h"
15 #include "commands/GatewayListenCommand.h"
16 #include "core/AnswerQueue.h"
17 #include "core/CommandHandler.h"
18 #include "core/CommandSender.h"
19 #include "core/DeviceCache.h"
20 #include "core/DeviceStatusHandler.h"
21 #include "core/Distributor.h"
22 #include "loop/StoppableRunnable.h"
23 #include "loop/StopControl.h"
24 #include "model/DeviceID.h"
25 #include "model/DevicePrefix.h"
26 #include "model/ModuleID.h"
27 #include "util/AsyncWork.h"
28 #include "util/CancellableSet.h"
29 #include "util/Loggable.h"
30 
31 namespace BeeeOn {
32 
49  public CommandHandler,
50  public CommandSender,
51  public DeviceStatusHandler,
52  protected Loggable,
53  public StoppableRunnable {
54 public:
55  typedef Poco::SharedPtr<DeviceManager> Ptr;
56 
58  const std::initializer_list<std::type_index> &acceptable = {});
59  virtual ~DeviceManager();
60 
64  DevicePrefix prefix() const override;
65 
70  void stop() override;
71 
72  void setDeviceCache(DeviceCache::Ptr cache);
73  void setDistributor(Poco::SharedPtr<Distributor> distributor);
74 
80  bool accept(const Command::Ptr cmd) override;
81 
90  void handle(Command::Ptr cmd, Answer::Ptr answer) override;
91 
98  void handleRemoteStatus(
99  const DevicePrefix &prefix,
100  const std::set<DeviceID> &devices,
101  const DeviceStatusHandler::DeviceValues &values) override;
102 
103 protected:
110  std::set<DeviceID> waitRemoteStatus(const Poco::Timespan &timeout);
111 
117  virtual void handleGeneric(const Command::Ptr cmd, Result::Ptr result);
118 
125  virtual void handleAccept(const DeviceAcceptCommand::Ptr);
126 
138  virtual AsyncWork<>::Ptr startDiscovery(const Poco::Timespan &timeout);
139 
150  void handleListen(const GatewayListenCommand::Ptr cmd);
151 
164  const Poco::Timespan &timeout,
165  const Poco::Net::IPAddress &address);
166 
179  const Poco::Timespan &timeout,
180  const MACAddress &address);
181 
194  const Poco::Timespan &timeout,
195  const uint64_t serialNumber);
196 
202  void handleSearch(const DeviceSearchCommand::Ptr cmd);
203 
214  const DeviceID &id,
215  const Poco::Timespan &timeout);
216 
225  std::set<DeviceID> handleUnpair(const DeviceUnpairCommand::Ptr cmd);
226 
237  virtual AsyncWork<double>::Ptr startSetValue(
238  const DeviceID &id,
239  const ModuleID &module,
240  const double value,
241  const Poco::Timespan &timeout);
242 
247  AsyncWork<double>::Ptr startSetValueByMode(
248  const DeviceID &id,
249  const ModuleID &module,
250  const double value,
251  const OpMode &mode,
252  const Poco::Timespan &timeout);
253 
257  virtual AsyncWork<double>::Ptr startSetValueTryHarder(
258  const DeviceID &id,
259  const ModuleID &module,
260  const double value,
261  const Poco::Timespan &timeout);
262 
269  virtual AsyncWork<double>::Ptr startSetValueRepeatOnFail(
270  const DeviceID &id,
271  const ModuleID &module,
272  const double value,
273  const Poco::Timespan &timeout);
274 
284  void handleSetValue(const DeviceSetValueCommand::Ptr cmd);
285 
289  void ship(const SensorData &sensorData);
290 
294  DeviceCache::Ptr deviceCache() const;
295 
302 
313  Poco::Timespan checkDelayedOperation(
314  const std::string &opname,
315  const Poco::Clock &started,
316  const Poco::Timespan &duration) const;
317 
324  bool manageUntilFinished(
325  const std::string &opname,
326  AnyAsyncWork::Ptr work,
327  const Poco::Timespan &timeout);
328 
329 protected:
330  StopControl m_stopControl;
331 
332 private:
333  DevicePrefix m_prefix;
334  DeviceCache::Ptr m_deviceCache;
335  Poco::FastMutex m_listenLock;
336  Poco::FastMutex m_unpairLock;
337  Poco::FastMutex m_setValueLock;
338  Poco::SharedPtr<Distributor> m_distributor;
339  std::set<std::type_index> m_acceptable;
340  CancellableSet m_cancellable;
341  Poco::AtomicCounter m_remoteStatusDelivered;
342 };
343 
344 }
void handleSetValue(const DeviceSetValueCommand::Ptr cmd)
Implements handling of the set-value command in a generic way. The method ensures that only 1 thread ...
Definition: DeviceManager.cpp:328
Definition: SensorData.h:20
virtual AsyncWork::Ptr startSearch(const Poco::Timespan &timeout, const Poco::Net::IPAddress &address)
Start searching a device by IP address in a technology-specific way. This method is always called ins...
void ship(const SensorData &sensorData)
Definition: DeviceManager.cpp:367
CancellableSet & cancellable()
Definition: DeviceManager.cpp:54
virtual AsyncWork< double >::Ptr startSetValueRepeatOnFail(const DeviceID &id, const ModuleID &module, const double value, const Poco::Timespan &timeout)
Default implementation calls startSetValue() again if a Poco::IOException is thrown until timeout exc...
Definition: DeviceManager.cpp:293
void handle(Command::Ptr cmd, Answer::Ptr answer) override
Definition: DeviceManager.cpp:77
virtual AsyncWork< double >::Ptr startSetValue(const DeviceID &id, const ModuleID &module, const double value, const Poco::Timespan &timeout)
Starts set-value operation in a technology specific way. The method is always called inside a critica...
Definition: DeviceManager.cpp:275
DeviceStatusHandler represents a class that can process status of a set of devices. This is useful when fetching pairing state from a remote server.
Definition: DeviceStatusHandler.h:19
Definition: CommandHandler.h:18
virtual AsyncWork::Ptr startDiscovery(const Poco::Timespan &timeout)
Starts device discovery process in a technology-specific way. This method is always called inside a c...
Definition: DeviceManager.cpp:122
AsyncWork< double >::Ptr startSetValueByMode(const DeviceID &id, const ModuleID &module, const double value, const OpMode &mode, const Poco::Timespan &timeout)
Call an implementation of startSetValue() based on the given operation mode.
Definition: DeviceManager.cpp:248
std::set< DeviceID > handleUnpair(const DeviceUnpairCommand::Ptr cmd)
Implements handling of the unpair command in a generic way. The method ensures that only 1 thread can...
Definition: DeviceManager.cpp:207
void handleListen(const GatewayListenCommand::Ptr cmd)
Implements handling of the listen command in a generic way. The method ensures that only 1 thread can...
Definition: DeviceManager.cpp:127
DeviceCache::Ptr deviceCache() const
Definition: DeviceManager.cpp:49
AsyncWork is an interface allowing to wait until an asynchronous operation finishes. It is also possible to force-stop it by calling cancel().
Definition: AsyncWork.h:21
bool accept(const Command::Ptr cmd) override
Definition: DeviceManager.cpp:64
Definition: MACAddress.h:8
Poco::Timespan checkDelayedOperation(const std::string &opname, const Poco::Clock &started, const Poco::Timespan &duration) const
When starting an asynchronous operation, it might happen we sleep too long on a lock because the prev...
Definition: DeviceManager.cpp:372
void handleRemoteStatus(const DevicePrefix &prefix, const std::set< DeviceID > &devices, const DeviceStatusHandler::DeviceValues &values) override
Called when devices from a remote server are fetched and so the pairing status of them can be reconsi...
Definition: DeviceManager.cpp:415
virtual void handleGeneric(const Command::Ptr cmd, Result::Ptr result)
Definition: DeviceManager.cpp:90
StopControl implements the stop mechanism generically.
Definition: StopControl.h:12
Definition: ModuleID.h:12
Definition: DeviceManager.h:48
Definition: CommandSender.h:20
Definition: Loggable.h:19
bool manageUntilFinished(const std::string &opname, AnyAsyncWork::Ptr work, const Poco::Timespan &timeout)
Manage an AsyncWork after it is started. If it does not finish in the given timeout, it is cancelled explicitly.
Definition: DeviceManager.cpp:393
virtual AsyncWork< double >::Ptr startSetValueTryHarder(const DeviceID &id, const ModuleID &module, const double value, const Poco::Timespan &timeout)
Default implementation just calls startSetValue().
Definition: DeviceManager.cpp:284
Definition: StoppableRunnable.h:8
virtual AsyncWork< std::set< DeviceID > >::Ptr startUnpair(const DeviceID &id, const Poco::Timespan &timeout)
Starts device unpair process in a technology-specific way. This method is always called inside a crit...
Definition: DeviceManager.cpp:200
std::set< DeviceID > waitRemoteStatus(const Poco::Timespan &timeout)
Wait until the remote status is delivered or timeout exceeds. DO NOT USE this method, it is intended as a transition mechanism from calling of the deprecated method deviceList().
Definition: DeviceManager.cpp:433
Definition: DeviceID.h:17
void stop() override
Definition: DeviceManager.cpp:38
virtual void handleAccept(const DeviceAcceptCommand::Ptr)
Generic handler of the DeviceAcceptCommand. It might be helpful to override this method in case we ne...
Definition: DeviceManager.cpp:112
DevicePrefix prefix() const override
Definition: DeviceManager.cpp:33
void handleSearch(const DeviceSearchCommand::Ptr cmd)
Implements handling of the search command in a generic way. The method ensures that only 1 thread can...
Definition: DeviceManager.cpp:169
Definition: CancellableSet.h:12