CppServer 1.0.5.0
C++ Server Library
Loading...
Searching...
No Matches
timer.cpp
Go to the documentation of this file.
1
9#include "server/asio/timer.h"
10
11namespace CppServer {
12namespace Asio {
13
14Timer::Timer(const std::shared_ptr<Service>& service)
15 : _service(service),
16 _io_service(_service->GetAsioService()),
17 _strand(*_io_service),
18 _strand_required(_service->IsStrandRequired()),
19 _timer(*_io_service)
20{
21 assert((service != nullptr) && "Asio service is invalid!");
22 if (service == nullptr)
23 throw CppCommon::ArgumentException("Asio service is invalid!");
24}
25
26Timer::Timer(const std::shared_ptr<Service>& service, const CppCommon::UtcTime& time)
27 : _service(service),
28 _io_service(_service->GetAsioService()),
29 _strand(*_io_service),
30 _strand_required(_service->IsStrandRequired()),
31 _timer(*_io_service, time.chrono())
32{
33 assert((service != nullptr) && "Asio service is invalid!");
34 if (service == nullptr)
35 throw CppCommon::ArgumentException("Asio service is invalid!");
36}
37
38Timer::Timer(const std::shared_ptr<Service>& service, const CppCommon::Timespan& timespan)
39 : _service(service),
40 _io_service(_service->GetAsioService()),
41 _strand(*_io_service),
42 _strand_required(_service->IsStrandRequired()),
43 _timer(*_io_service, timespan.chrono())
44{
45 assert((service != nullptr) && "Asio service is invalid!");
46 if (service == nullptr)
47 throw CppCommon::ArgumentException("Asio service is invalid!");
48}
49
50Timer::Timer(const std::shared_ptr<Service>& service, const std::function<void(bool)>& action)
51 : _service(service),
52 _io_service(_service->GetAsioService()),
53 _strand(*_io_service),
54 _strand_required(_service->IsStrandRequired()),
55 _timer(*_io_service),
56 _action(action)
57{
58 assert((service != nullptr) && "Asio service is invalid!");
59 if (service == nullptr)
60 throw CppCommon::ArgumentException("Asio service is invalid!");
61 assert((action) && "Action function is invalid!");
62 if (!action)
63 throw CppCommon::ArgumentException("Action function is invalid!");
64}
65
66Timer::Timer(const std::shared_ptr<Service>& service, const std::function<void(bool)>& action, const CppCommon::UtcTime& time)
67 : _service(service),
68 _io_service(_service->GetAsioService()),
69 _strand(*_io_service),
70 _strand_required(_service->IsStrandRequired()),
71 _timer(*_io_service, time.chrono()),
72 _action(action)
73{
74 assert((service != nullptr) && "Asio service is invalid!");
75 if (service == nullptr)
76 throw CppCommon::ArgumentException("Asio service is invalid!");
77 assert((action) && "Action function is invalid!");
78 if (!action)
79 throw CppCommon::ArgumentException("Action function is invalid!");
80}
81
82Timer::Timer(const std::shared_ptr<Service>& service, const std::function<void(bool)>& action, const CppCommon::Timespan& timespan)
83 : _service(service),
84 _io_service(_service->GetAsioService()),
85 _strand(*_io_service),
86 _strand_required(_service->IsStrandRequired()),
87 _timer(*_io_service, timespan.chrono()),
88 _action(action)
89{
90 assert((service != nullptr) && "Asio service is invalid!");
91 if (service == nullptr)
92 throw CppCommon::ArgumentException("Asio service is invalid!");
93 assert((action) && "Action function is invalid!");
94 if (!action)
95 throw CppCommon::ArgumentException("Action function is invalid!");
96}
97
98CppCommon::UtcTime Timer::expire_time() const
99{
100 return CppCommon::UtcTime(_timer.expires_at());
101}
102
103CppCommon::Timespan Timer::expire_timespan() const
104{
105 return CppCommon::Timespan(_timer.expires_from_now());
106}
107
108bool Timer::Setup(const CppCommon::UtcTime& time)
109{
110 asio::error_code ec;
111 _timer.expires_at(time.chrono(), ec);
112
113 // Check for error
114 if (ec)
115 {
116 SendError(ec);
117 return false;
118 }
119
120 return true;
121}
122
123bool Timer::Setup(const CppCommon::Timespan& timespan)
124{
125 asio::error_code ec;
126 _timer.expires_from_now(timespan.chrono(), ec);
127
128 // Check for error
129 if (ec)
130 {
131 SendError(ec);
132 return false;
133 }
134
135 return true;
136}
137
138bool Timer::Setup(const std::function<void(bool)>& action)
139{
140 assert((action) && "Action function is invalid!");
141 if (!action)
142 return false;
143
144 _action = action;
145 return true;
146}
147
148bool Timer::Setup(const std::function<void(bool)>& action, const CppCommon::UtcTime& time)
149{
150 assert((action) && "Action function is invalid!");
151 if (!action)
152 return false;
153
154 _action = action;
155 return Setup(time);
156}
157
158bool Timer::Setup(const std::function<void(bool)>& action, const CppCommon::Timespan& timespan)
159{
160 assert((action) && "Action function is invalid!");
161 if (!action)
162 return false;
163
164 _action = action;
165 return Setup(timespan);
166}
167
169{
170 auto self(this->shared_from_this());
171 auto async_wait_handler = [this, self](const std::error_code& ec)
172 {
173 // Call the timer aborted handler
174 if (ec == asio::error::operation_aborted)
175 SendTimer(true);
176
177 // Check for error
178 if (ec)
179 {
180 SendError(ec);
181 return;
182 }
183
184 // Call the timer expired handler
185 SendTimer(false);
186 };
187 if (_strand_required)
188 _timer.async_wait(bind_executor(_strand, async_wait_handler));
189 else
190 _timer.async_wait(async_wait_handler);
191
192 return true;
193}
194
196{
197 asio::error_code ec;
198 _timer.wait(ec);
199
200 // Call the timer aborted handler
201 if (ec == asio::error::operation_aborted)
202 SendTimer(true);
203
204 // Check for error
205 if (ec)
206 {
207 SendError(ec);
208 return false;
209 }
210
211 // Call the timer expired handler
212 SendTimer(false);
213
214 return true;
215}
216
218{
219 asio::error_code ec;
220 _timer.cancel(ec);
221
222 // Check for error
223 if (ec)
224 {
225 SendError(ec);
226 return false;
227 }
228
229 return true;
230}
231
232void Timer::SendError(std::error_code ec)
233{
234 // Skip Asio abort error
235 if (ec == asio::error::operation_aborted)
236 return;
237
238 onError(ec.value(), ec.category().name(), ec.message());
239}
240
241void Timer::SendTimer(bool canceled)
242{
243 // Call the timer handler
244 onTimer(canceled);
245
246 // Call the timer action
247 if (_action)
248 _action(canceled);
249}
250
251} // namespace Asio
252} // namespace CppServer
Asio allocate handler wrapper.
Definition memory.h:133
virtual bool Cancel()
Cancel any wait operation on the timer.
Definition timer.cpp:217
std::shared_ptr< Service > & service() noexcept
Get the Asio service.
Definition timer.h:77
virtual bool WaitSync()
Wait for the timer (synchronous)
Definition timer.cpp:195
CppCommon::UtcTime expire_time() const
Get the timer's expiry time as an absolute time.
Definition timer.cpp:98
Timer(const std::shared_ptr< Service > &service)
Initialize timer with a given Asio service.
Definition timer.cpp:14
virtual void onTimer(bool canceled)
Handle timer notification.
Definition timer.h:140
CppCommon::Timespan expire_timespan() const
Get the timer's expiry time relative to now.
Definition timer.cpp:103
virtual bool Setup(const CppCommon::UtcTime &time)
Setup the timer with absolute expiry time.
Definition timer.cpp:108
virtual bool WaitAsync()
Wait for the timer (asynchronous)
Definition timer.cpp:168
virtual void onError(int error, const std::string &category, const std::string &message)
Handle error notification.
Definition timer.h:148
C++ Server project definitions.
Definition asio.h:56
Timer definition.