Mercurial > hg > orthanc
annotate Core/JobsEngine/JobsRegistry.cpp @ 2656:a6d3e45eeff5 jobs
SerializationToolbox
author | Sebastien Jodogne <s.jodogne@gmail.com> |
---|---|
date | Tue, 05 Jun 2018 18:25:23 +0200 |
parents | c196d76cb8fa |
children | 228e2783ce83 |
rev | line source |
---|---|
2569 | 1 /** |
2 * Orthanc - A Lightweight, RESTful DICOM Store | |
3 * Copyright (C) 2012-2016 Sebastien Jodogne, Medical Physics | |
4 * Department, University Hospital of Liege, Belgium | |
5 * Copyright (C) 2017-2018 Osimis S.A., Belgium | |
6 * | |
7 * This program is free software: you can redistribute it and/or | |
8 * modify it under the terms of the GNU General Public License as | |
9 * published by the Free Software Foundation, either version 3 of the | |
10 * License, or (at your option) any later version. | |
11 * | |
12 * In addition, as a special exception, the copyright holders of this | |
13 * program give permission to link the code of its release with the | |
14 * OpenSSL project's "OpenSSL" library (or with modified versions of it | |
15 * that use the same license as the "OpenSSL" library), and distribute | |
16 * the linked executables. You must obey the GNU General Public License | |
17 * in all respects for all of the code used other than "OpenSSL". If you | |
18 * modify file(s) with this exception, you may extend this exception to | |
19 * your version of the file(s), but you are not obligated to do so. If | |
20 * you do not wish to do so, delete this exception statement from your | |
21 * version. If you delete this exception statement from all source files | |
22 * in the program, then also delete it here. | |
23 * | |
24 * This program is distributed in the hope that it will be useful, but | |
25 * WITHOUT ANY WARRANTY; without even the implied warranty of | |
26 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
27 * General Public License for more details. | |
28 * | |
29 * You should have received a copy of the GNU General Public License | |
30 * along with this program. If not, see <http://www.gnu.org/licenses/>. | |
31 **/ | |
32 | |
33 | |
34 #include "../PrecompiledHeaders.h" | |
35 #include "JobsRegistry.h" | |
36 | |
37 #include "../Logging.h" | |
38 #include "../OrthancException.h" | |
39 #include "../Toolbox.h" | |
2656
a6d3e45eeff5
SerializationToolbox
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2655
diff
changeset
|
40 #include "../SerializationToolbox.h" |
2569 | 41 |
42 namespace Orthanc | |
43 { | |
44 class JobsRegistry::JobHandler : public boost::noncopyable | |
45 { | |
46 private: | |
47 std::string id_; | |
48 JobState state_; | |
2648
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
49 std::string jobType_; |
2569 | 50 std::auto_ptr<IJob> job_; |
51 int priority_; // "+inf()" means highest priority | |
52 boost::posix_time::ptime creationTime_; | |
53 boost::posix_time::ptime lastStateChangeTime_; | |
54 boost::posix_time::time_duration runtime_; | |
55 boost::posix_time::ptime retryTime_; | |
56 bool pauseScheduled_; | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
57 bool cancelScheduled_; |
2569 | 58 JobStatus lastStatus_; |
59 | |
60 void Touch() | |
61 { | |
62 const boost::posix_time::ptime now = boost::posix_time::microsec_clock::universal_time(); | |
63 | |
64 if (state_ == JobState_Running) | |
65 { | |
66 runtime_ += (now - lastStateChangeTime_); | |
67 } | |
68 | |
69 lastStateChangeTime_ = now; | |
70 } | |
71 | |
72 void SetStateInternal(JobState state) | |
73 { | |
74 state_ = state; | |
75 pauseScheduled_ = false; | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
76 cancelScheduled_ = false; |
2569 | 77 Touch(); |
78 } | |
79 | |
80 public: | |
81 JobHandler(IJob* job, | |
82 int priority) : | |
83 id_(Toolbox::GenerateUuid()), | |
84 state_(JobState_Pending), | |
85 job_(job), | |
86 priority_(priority), | |
87 creationTime_(boost::posix_time::microsec_clock::universal_time()), | |
88 lastStateChangeTime_(creationTime_), | |
89 runtime_(boost::posix_time::milliseconds(0)), | |
90 retryTime_(creationTime_), | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
91 pauseScheduled_(false), |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
92 cancelScheduled_(false) |
2569 | 93 { |
94 if (job == NULL) | |
95 { | |
96 throw OrthancException(ErrorCode_NullPointer); | |
97 } | |
98 | |
2648
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
99 job->GetJobType(jobType_); |
2630
00327e989458
creating archives/medias is now a job
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2620
diff
changeset
|
100 job->Start(); |
00327e989458
creating archives/medias is now a job
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2620
diff
changeset
|
101 |
2648
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
102 lastStatus_ = JobStatus(ErrorCode_Success, *job_); |
2569 | 103 } |
104 | |
105 const std::string& GetId() const | |
106 { | |
107 return id_; | |
108 } | |
109 | |
110 IJob& GetJob() const | |
111 { | |
112 assert(job_.get() != NULL); | |
113 return *job_; | |
114 } | |
115 | |
116 void SetPriority(int priority) | |
117 { | |
118 priority_ = priority; | |
119 } | |
120 | |
121 int GetPriority() const | |
122 { | |
123 return priority_; | |
124 } | |
125 | |
126 JobState GetState() const | |
127 { | |
128 return state_; | |
129 } | |
130 | |
131 void SetState(JobState state) | |
132 { | |
133 if (state == JobState_Retry) | |
134 { | |
135 // Use "SetRetryState()" | |
136 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
137 } | |
138 else | |
139 { | |
140 SetStateInternal(state); | |
141 } | |
142 } | |
143 | |
144 void SetRetryState(unsigned int timeout) | |
145 { | |
146 if (state_ == JobState_Running) | |
147 { | |
148 SetStateInternal(JobState_Retry); | |
149 retryTime_ = (boost::posix_time::microsec_clock::universal_time() + | |
150 boost::posix_time::milliseconds(timeout)); | |
151 } | |
152 else | |
153 { | |
154 // Only valid for running jobs | |
155 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
156 } | |
157 } | |
158 | |
159 void SchedulePause() | |
160 { | |
161 if (state_ == JobState_Running) | |
162 { | |
163 pauseScheduled_ = true; | |
164 } | |
165 else | |
166 { | |
167 // Only valid for running jobs | |
168 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
169 } | |
170 } | |
171 | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
172 void ScheduleCancel() |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
173 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
174 if (state_ == JobState_Running) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
175 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
176 cancelScheduled_ = true; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
177 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
178 else |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
179 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
180 // Only valid for running jobs |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
181 throw OrthancException(ErrorCode_BadSequenceOfCalls); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
182 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
183 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
184 |
2569 | 185 bool IsPauseScheduled() |
186 { | |
187 return pauseScheduled_; | |
188 } | |
189 | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
190 bool IsCancelScheduled() |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
191 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
192 return cancelScheduled_; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
193 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
194 |
2569 | 195 bool IsRetryReady(const boost::posix_time::ptime& now) const |
196 { | |
197 if (state_ != JobState_Retry) | |
198 { | |
199 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
200 } | |
201 else | |
202 { | |
203 return retryTime_ <= now; | |
204 } | |
205 } | |
206 | |
207 const boost::posix_time::ptime& GetCreationTime() const | |
208 { | |
209 return creationTime_; | |
210 } | |
211 | |
212 const boost::posix_time::ptime& GetLastStateChangeTime() const | |
213 { | |
214 return lastStateChangeTime_; | |
215 } | |
216 | |
217 const boost::posix_time::time_duration& GetRuntime() const | |
218 { | |
219 return runtime_; | |
220 } | |
221 | |
222 const JobStatus& GetLastStatus() const | |
223 { | |
224 return lastStatus_; | |
225 } | |
226 | |
227 void SetLastStatus(const JobStatus& status) | |
228 { | |
229 lastStatus_ = status; | |
230 Touch(); | |
231 } | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
232 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
233 void SetLastErrorCode(ErrorCode code) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
234 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
235 lastStatus_.SetErrorCode(code); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
236 } |
2648
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
237 |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
238 void Serialize(Json::Value& target) const |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
239 { |
2655 | 240 target = Json::objectValue; |
241 target["ID"] = id_; | |
2648
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
242 target["State"] = EnumerationToString(state_); |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
243 target["JobType"] = jobType_; |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
244 target["Priority"] = priority_; |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
245 target["CreationTime"] = boost::posix_time::to_iso_string(creationTime_); |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
246 target["Runtime"] = static_cast<unsigned int>(runtime_.total_milliseconds()); |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
247 |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
248 if (state_ == JobState_Running) |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
249 { |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
250 // WARNING: Cannot directly access the "job_" member, as long |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
251 // as a "RunningJob" instance is running. We do not use a |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
252 // mutex at the "JobHandler" level, as serialization would be |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
253 // blocked while a step in the job is running. Instead, we |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
254 // save a snapshot of the serialized job. |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
255 target["Job"] = lastStatus_.GetSerialized(); |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
256 } |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
257 else |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
258 { |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
259 job_->Serialize(target["Job"]); |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
260 } |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
261 } |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
262 |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
263 JobHandler(IJobUnserializer& unserializer, |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
264 const Json::Value& serialized) : |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
265 lastStateChangeTime_(boost::posix_time::microsec_clock::universal_time()), |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
266 pauseScheduled_(false), |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
267 cancelScheduled_(false) |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
268 { |
2656
a6d3e45eeff5
SerializationToolbox
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2655
diff
changeset
|
269 id_ = StringToJobState(SerializationToolbox::ReadString(serialized, "ID")); |
a6d3e45eeff5
SerializationToolbox
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2655
diff
changeset
|
270 state_ = StringToJobState(SerializationToolbox::ReadString(serialized, "State")); |
a6d3e45eeff5
SerializationToolbox
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2655
diff
changeset
|
271 priority_ = SerializationToolbox::ReadInteger(serialized, "Priority"); |
2648
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
272 creationTime_ = boost::posix_time::from_iso_string |
2656
a6d3e45eeff5
SerializationToolbox
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2655
diff
changeset
|
273 (SerializationToolbox::ReadString(serialized, "CreationTime")); |
a6d3e45eeff5
SerializationToolbox
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2655
diff
changeset
|
274 runtime_ = boost::posix_time::milliseconds(SerializationToolbox::ReadInteger(serialized, "Runtime")); |
2648
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
275 |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
276 retryTime_ = creationTime_; |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
277 |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
278 if (state_ == JobState_Retry || |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
279 state_ == JobState_Running) |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
280 { |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
281 state_ = JobState_Pending; |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
282 } |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
283 |
2652 | 284 job_.reset(unserializer.UnserializeJob(serialized["Job"])); |
285 job_->GetJobType(jobType_); | |
286 job_->Start(); | |
2648
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
287 |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
288 lastStatus_ = JobStatus(ErrorCode_Success, *job_); |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
289 } |
2569 | 290 }; |
291 | |
292 | |
293 bool JobsRegistry::PriorityComparator::operator() (JobHandler*& a, | |
294 JobHandler*& b) const | |
295 { | |
296 return a->GetPriority() < b->GetPriority(); | |
297 } | |
298 | |
299 | |
300 #if defined(NDEBUG) | |
301 void JobsRegistry::CheckInvariants() const | |
302 { | |
303 } | |
304 | |
305 #else | |
306 bool JobsRegistry::IsPendingJob(const JobHandler& job) const | |
307 { | |
308 PendingJobs copy = pendingJobs_; | |
309 while (!copy.empty()) | |
310 { | |
311 if (copy.top() == &job) | |
312 { | |
313 return true; | |
314 } | |
315 | |
316 copy.pop(); | |
317 } | |
318 | |
319 return false; | |
320 } | |
321 | |
322 bool JobsRegistry::IsCompletedJob(JobHandler& job) const | |
323 { | |
324 for (CompletedJobs::const_iterator it = completedJobs_.begin(); | |
325 it != completedJobs_.end(); ++it) | |
326 { | |
327 if (*it == &job) | |
328 { | |
329 return true; | |
330 } | |
331 } | |
332 | |
333 return false; | |
334 } | |
335 | |
336 bool JobsRegistry::IsRetryJob(JobHandler& job) const | |
337 { | |
338 return retryJobs_.find(&job) != retryJobs_.end(); | |
339 } | |
340 | |
341 void JobsRegistry::CheckInvariants() const | |
342 { | |
343 { | |
344 PendingJobs copy = pendingJobs_; | |
345 while (!copy.empty()) | |
346 { | |
347 assert(copy.top()->GetState() == JobState_Pending); | |
348 copy.pop(); | |
349 } | |
350 } | |
351 | |
352 assert(completedJobs_.size() <= maxCompletedJobs_); | |
353 | |
354 for (CompletedJobs::const_iterator it = completedJobs_.begin(); | |
355 it != completedJobs_.end(); ++it) | |
356 { | |
357 assert((*it)->GetState() == JobState_Success || | |
358 (*it)->GetState() == JobState_Failure); | |
359 } | |
360 | |
361 for (RetryJobs::const_iterator it = retryJobs_.begin(); | |
362 it != retryJobs_.end(); ++it) | |
363 { | |
364 assert((*it)->GetState() == JobState_Retry); | |
365 } | |
366 | |
367 for (JobsIndex::const_iterator it = jobsIndex_.begin(); | |
368 it != jobsIndex_.end(); ++it) | |
369 { | |
370 JobHandler& job = *it->second; | |
371 | |
372 assert(job.GetId() == it->first); | |
373 | |
374 switch (job.GetState()) | |
375 { | |
376 case JobState_Pending: | |
377 assert(!IsRetryJob(job) && IsPendingJob(job) && !IsCompletedJob(job)); | |
378 break; | |
379 | |
380 case JobState_Success: | |
381 case JobState_Failure: | |
382 assert(!IsRetryJob(job) && !IsPendingJob(job) && IsCompletedJob(job)); | |
383 break; | |
384 | |
385 case JobState_Retry: | |
386 assert(IsRetryJob(job) && !IsPendingJob(job) && !IsCompletedJob(job)); | |
387 break; | |
388 | |
389 case JobState_Running: | |
390 case JobState_Paused: | |
391 assert(!IsRetryJob(job) && !IsPendingJob(job) && !IsCompletedJob(job)); | |
392 break; | |
393 | |
394 default: | |
395 throw OrthancException(ErrorCode_InternalError); | |
396 } | |
397 } | |
398 } | |
399 #endif | |
400 | |
401 | |
402 void JobsRegistry::ForgetOldCompletedJobs() | |
403 { | |
404 if (maxCompletedJobs_ != 0) | |
405 { | |
406 while (completedJobs_.size() > maxCompletedJobs_) | |
407 { | |
408 assert(completedJobs_.front() != NULL); | |
409 | |
410 std::string id = completedJobs_.front()->GetId(); | |
411 assert(jobsIndex_.find(id) != jobsIndex_.end()); | |
412 | |
413 jobsIndex_.erase(id); | |
414 delete(completedJobs_.front()); | |
415 completedJobs_.pop_front(); | |
416 } | |
417 } | |
418 } | |
419 | |
420 | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
421 void JobsRegistry::SetCompletedJob(JobHandler& job, |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
422 bool success) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
423 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
424 job.SetState(success ? JobState_Success : JobState_Failure); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
425 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
426 completedJobs_.push_back(&job); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
427 ForgetOldCompletedJobs(); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
428 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
429 someJobComplete_.notify_all(); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
430 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
431 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
432 |
2569 | 433 void JobsRegistry::MarkRunningAsCompleted(JobHandler& job, |
434 bool success) | |
435 { | |
436 LOG(INFO) << "Job has completed with " << (success ? "success" : "failure") | |
437 << ": " << job.GetId(); | |
438 | |
439 CheckInvariants(); | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
440 |
2569 | 441 assert(job.GetState() == JobState_Running); |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
442 SetCompletedJob(job, success); |
2570
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
443 |
2569 | 444 CheckInvariants(); |
445 } | |
446 | |
447 | |
448 void JobsRegistry::MarkRunningAsRetry(JobHandler& job, | |
449 unsigned int timeout) | |
450 { | |
451 LOG(INFO) << "Job scheduled for retry in " << timeout << "ms: " << job.GetId(); | |
452 | |
453 CheckInvariants(); | |
454 | |
455 assert(job.GetState() == JobState_Running && | |
456 retryJobs_.find(&job) == retryJobs_.end()); | |
457 | |
458 retryJobs_.insert(&job); | |
459 job.SetRetryState(timeout); | |
460 | |
461 CheckInvariants(); | |
462 } | |
463 | |
464 | |
465 void JobsRegistry::MarkRunningAsPaused(JobHandler& job) | |
466 { | |
467 LOG(INFO) << "Job paused: " << job.GetId(); | |
468 | |
469 CheckInvariants(); | |
470 assert(job.GetState() == JobState_Running); | |
471 | |
472 job.SetState(JobState_Paused); | |
473 | |
474 CheckInvariants(); | |
475 } | |
476 | |
477 | |
2570
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
478 bool JobsRegistry::GetStateInternal(JobState& state, |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
479 const std::string& id) |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
480 { |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
481 CheckInvariants(); |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
482 |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
483 JobsIndex::const_iterator it = jobsIndex_.find(id); |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
484 if (it == jobsIndex_.end()) |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
485 { |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
486 return false; |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
487 } |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
488 else |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
489 { |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
490 state = it->second->GetState(); |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
491 return true; |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
492 } |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
493 } |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
494 |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
495 |
2569 | 496 JobsRegistry::~JobsRegistry() |
497 { | |
498 for (JobsIndex::iterator it = jobsIndex_.begin(); it != jobsIndex_.end(); ++it) | |
499 { | |
500 assert(it->second != NULL); | |
501 delete it->second; | |
502 } | |
503 } | |
504 | |
505 | |
2620
1232922c8793
speeding up shutdown if Lua script is in trailing phase
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2600
diff
changeset
|
506 void JobsRegistry::SetMaxCompletedJobs(size_t n) |
2569 | 507 { |
508 boost::mutex::scoped_lock lock(mutex_); | |
509 CheckInvariants(); | |
510 | |
2620
1232922c8793
speeding up shutdown if Lua script is in trailing phase
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2600
diff
changeset
|
511 LOG(INFO) << "The size of the history of the jobs engine is set to: " << n << " job(s)"; |
1232922c8793
speeding up shutdown if Lua script is in trailing phase
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2600
diff
changeset
|
512 |
1232922c8793
speeding up shutdown if Lua script is in trailing phase
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2600
diff
changeset
|
513 maxCompletedJobs_ = n; |
2569 | 514 ForgetOldCompletedJobs(); |
515 | |
516 CheckInvariants(); | |
517 } | |
518 | |
519 | |
520 void JobsRegistry::ListJobs(std::set<std::string>& target) | |
521 { | |
522 boost::mutex::scoped_lock lock(mutex_); | |
523 CheckInvariants(); | |
524 | |
525 for (JobsIndex::const_iterator it = jobsIndex_.begin(); | |
526 it != jobsIndex_.end(); ++it) | |
527 { | |
528 target.insert(it->first); | |
529 } | |
530 } | |
531 | |
532 | |
533 bool JobsRegistry::GetJobInfo(JobInfo& target, | |
534 const std::string& id) | |
535 { | |
536 boost::mutex::scoped_lock lock(mutex_); | |
537 CheckInvariants(); | |
538 | |
539 JobsIndex::const_iterator found = jobsIndex_.find(id); | |
540 | |
541 if (found == jobsIndex_.end()) | |
542 { | |
543 return false; | |
544 } | |
545 else | |
546 { | |
547 const JobHandler& handler = *found->second; | |
548 target = JobInfo(handler.GetId(), | |
549 handler.GetPriority(), | |
550 handler.GetState(), | |
551 handler.GetLastStatus(), | |
552 handler.GetCreationTime(), | |
553 handler.GetLastStateChangeTime(), | |
554 handler.GetRuntime()); | |
555 return true; | |
556 } | |
557 } | |
558 | |
559 | |
2648
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
560 void JobsRegistry::Serialize(Json::Value& target) |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
561 { |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
562 boost::mutex::scoped_lock lock(mutex_); |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
563 CheckInvariants(); |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
564 |
2655 | 565 target = Json::arrayValue; |
2648
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
566 |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
567 for (JobsIndex::const_iterator it = jobsIndex_.begin(); |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
568 it != jobsIndex_.end(); ++it) |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
569 { |
2655 | 570 Json::Value v; |
2648
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
571 it->second->Serialize(v); |
2655 | 572 target.append(v); |
2648
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
573 } |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
574 } |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
575 |
e1893d31652a
serialization of JobHandler
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2630
diff
changeset
|
576 |
2569 | 577 void JobsRegistry::Submit(std::string& id, |
578 IJob* job, // Takes ownership | |
579 int priority) | |
580 { | |
581 std::auto_ptr<JobHandler> handler(new JobHandler(job, priority)); | |
582 | |
583 boost::mutex::scoped_lock lock(mutex_); | |
584 CheckInvariants(); | |
585 | |
586 id = handler->GetId(); | |
587 | |
588 pendingJobs_.push(handler.get()); | |
589 pendingJobAvailable_.notify_one(); | |
590 | |
591 jobsIndex_.insert(std::make_pair(id, handler.release())); | |
592 | |
593 LOG(INFO) << "New job submitted with priority " << priority << ": " << id; | |
594 | |
595 CheckInvariants(); | |
596 } | |
597 | |
598 | |
599 void JobsRegistry::Submit(IJob* job, // Takes ownership | |
600 int priority) | |
601 { | |
602 std::string id; | |
603 Submit(id, job, priority); | |
604 } | |
605 | |
606 | |
2570
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
607 bool JobsRegistry::SubmitAndWait(IJob* job, // Takes ownership |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
608 int priority) |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
609 { |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
610 std::string id; |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
611 Submit(id, job, priority); |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
612 |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
613 JobState state; |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
614 |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
615 { |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
616 boost::mutex::scoped_lock lock(mutex_); |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
617 |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
618 while (GetStateInternal(state, id) && |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
619 state != JobState_Success && |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
620 state != JobState_Failure) |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
621 { |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
622 someJobComplete_.wait(lock); |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
623 } |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
624 } |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
625 |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
626 return (state == JobState_Success); |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
627 } |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
628 |
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
629 |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
630 bool JobsRegistry::SetPriority(const std::string& id, |
2569 | 631 int priority) |
632 { | |
633 LOG(INFO) << "Changing priority to " << priority << " for job: " << id; | |
634 | |
635 boost::mutex::scoped_lock lock(mutex_); | |
636 CheckInvariants(); | |
637 | |
638 JobsIndex::iterator found = jobsIndex_.find(id); | |
639 | |
640 if (found == jobsIndex_.end()) | |
641 { | |
642 LOG(WARNING) << "Unknown job: " << id; | |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
643 return false; |
2569 | 644 } |
645 else | |
646 { | |
647 found->second->SetPriority(priority); | |
648 | |
649 if (found->second->GetState() == JobState_Pending) | |
650 { | |
651 // If the job is pending, we need to reconstruct the | |
652 // priority queue, as the heap condition has changed | |
653 | |
654 PendingJobs copy; | |
655 std::swap(copy, pendingJobs_); | |
656 | |
657 assert(pendingJobs_.empty()); | |
658 while (!copy.empty()) | |
659 { | |
660 pendingJobs_.push(copy.top()); | |
661 copy.pop(); | |
662 } | |
663 } | |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
664 |
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
665 CheckInvariants(); |
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
666 return true; |
2569 | 667 } |
668 } | |
669 | |
670 | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
671 void JobsRegistry::RemovePendingJob(const std::string& id) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
672 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
673 // If the job is pending, we need to reconstruct the priority |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
674 // queue to remove it |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
675 PendingJobs copy; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
676 std::swap(copy, pendingJobs_); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
677 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
678 assert(pendingJobs_.empty()); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
679 while (!copy.empty()) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
680 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
681 if (copy.top()->GetId() != id) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
682 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
683 pendingJobs_.push(copy.top()); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
684 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
685 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
686 copy.pop(); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
687 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
688 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
689 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
690 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
691 void JobsRegistry::RemoveRetryJob(JobHandler* handler) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
692 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
693 RetryJobs::iterator item = retryJobs_.find(handler); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
694 assert(item != retryJobs_.end()); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
695 retryJobs_.erase(item); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
696 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
697 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
698 |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
699 bool JobsRegistry::Pause(const std::string& id) |
2569 | 700 { |
701 LOG(INFO) << "Pausing job: " << id; | |
702 | |
703 boost::mutex::scoped_lock lock(mutex_); | |
704 CheckInvariants(); | |
705 | |
706 JobsIndex::iterator found = jobsIndex_.find(id); | |
707 | |
708 if (found == jobsIndex_.end()) | |
709 { | |
710 LOG(WARNING) << "Unknown job: " << id; | |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
711 return false; |
2569 | 712 } |
713 else | |
714 { | |
715 switch (found->second->GetState()) | |
716 { | |
717 case JobState_Pending: | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
718 RemovePendingJob(id); |
2569 | 719 found->second->SetState(JobState_Paused); |
720 break; | |
721 | |
722 case JobState_Retry: | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
723 RemoveRetryJob(found->second); |
2569 | 724 found->second->SetState(JobState_Paused); |
725 break; | |
726 | |
727 case JobState_Paused: | |
728 case JobState_Success: | |
729 case JobState_Failure: | |
730 // Nothing to be done | |
731 break; | |
732 | |
733 case JobState_Running: | |
734 found->second->SchedulePause(); | |
735 break; | |
736 | |
737 default: | |
738 throw OrthancException(ErrorCode_InternalError); | |
739 } | |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
740 |
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
741 CheckInvariants(); |
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
742 return true; |
2569 | 743 } |
744 } | |
745 | |
746 | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
747 bool JobsRegistry::Cancel(const std::string& id) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
748 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
749 LOG(INFO) << "Canceling job: " << id; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
750 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
751 boost::mutex::scoped_lock lock(mutex_); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
752 CheckInvariants(); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
753 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
754 JobsIndex::iterator found = jobsIndex_.find(id); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
755 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
756 if (found == jobsIndex_.end()) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
757 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
758 LOG(WARNING) << "Unknown job: " << id; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
759 return false; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
760 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
761 else |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
762 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
763 switch (found->second->GetState()) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
764 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
765 case JobState_Pending: |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
766 RemovePendingJob(id); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
767 SetCompletedJob(*found->second, false); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
768 found->second->SetLastErrorCode(ErrorCode_CanceledJob); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
769 break; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
770 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
771 case JobState_Retry: |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
772 RemoveRetryJob(found->second); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
773 SetCompletedJob(*found->second, false); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
774 found->second->SetLastErrorCode(ErrorCode_CanceledJob); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
775 break; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
776 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
777 case JobState_Paused: |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
778 SetCompletedJob(*found->second, false); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
779 found->second->SetLastErrorCode(ErrorCode_CanceledJob); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
780 break; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
781 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
782 case JobState_Success: |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
783 case JobState_Failure: |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
784 // Nothing to be done |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
785 break; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
786 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
787 case JobState_Running: |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
788 found->second->ScheduleCancel(); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
789 break; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
790 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
791 default: |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
792 throw OrthancException(ErrorCode_InternalError); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
793 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
794 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
795 CheckInvariants(); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
796 return true; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
797 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
798 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
799 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
800 |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
801 bool JobsRegistry::Resume(const std::string& id) |
2569 | 802 { |
803 LOG(INFO) << "Resuming job: " << id; | |
804 | |
805 boost::mutex::scoped_lock lock(mutex_); | |
806 CheckInvariants(); | |
807 | |
808 JobsIndex::iterator found = jobsIndex_.find(id); | |
809 | |
810 if (found == jobsIndex_.end()) | |
811 { | |
812 LOG(WARNING) << "Unknown job: " << id; | |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
813 return false; |
2569 | 814 } |
815 else if (found->second->GetState() != JobState_Paused) | |
816 { | |
817 LOG(WARNING) << "Cannot resume a job that is not paused: " << id; | |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
818 return false; |
2569 | 819 } |
820 else | |
821 { | |
822 found->second->SetState(JobState_Pending); | |
823 pendingJobs_.push(found->second); | |
824 pendingJobAvailable_.notify_one(); | |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
825 CheckInvariants(); |
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
826 return true; |
2569 | 827 } |
828 } | |
829 | |
830 | |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
831 bool JobsRegistry::Resubmit(const std::string& id) |
2569 | 832 { |
833 LOG(INFO) << "Resubmitting failed job: " << id; | |
834 | |
835 boost::mutex::scoped_lock lock(mutex_); | |
836 CheckInvariants(); | |
837 | |
838 JobsIndex::iterator found = jobsIndex_.find(id); | |
839 | |
840 if (found == jobsIndex_.end()) | |
841 { | |
842 LOG(WARNING) << "Unknown job: " << id; | |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
843 return false; |
2569 | 844 } |
845 else if (found->second->GetState() != JobState_Failure) | |
846 { | |
2600
140a539b4eba
SequenceOfOperationsJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2583
diff
changeset
|
847 printf("%s\n", EnumerationToString(found->second->GetState())); |
2569 | 848 LOG(WARNING) << "Cannot resubmit a job that has not failed: " << id; |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
849 return false; |
2569 | 850 } |
851 else | |
852 { | |
2583
1b6a6d80b6f2
OrthancPeerStoreJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2581
diff
changeset
|
853 found->second->GetJob().SignalResubmit(); |
1b6a6d80b6f2
OrthancPeerStoreJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2581
diff
changeset
|
854 |
2569 | 855 bool ok = false; |
856 for (CompletedJobs::iterator it = completedJobs_.begin(); | |
857 it != completedJobs_.end(); ++it) | |
858 { | |
859 if (*it == found->second) | |
860 { | |
861 ok = true; | |
862 completedJobs_.erase(it); | |
863 break; | |
864 } | |
865 } | |
866 | |
867 assert(ok); | |
868 | |
869 found->second->SetState(JobState_Pending); | |
870 pendingJobs_.push(found->second); | |
871 pendingJobAvailable_.notify_one(); | |
2573
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
872 |
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
873 CheckInvariants(); |
3372c5255333
StoreScuJob, Orthanc Explorer for jobs
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2570
diff
changeset
|
874 return true; |
2569 | 875 } |
876 } | |
877 | |
878 | |
879 void JobsRegistry::ScheduleRetries() | |
880 { | |
881 boost::mutex::scoped_lock lock(mutex_); | |
882 CheckInvariants(); | |
883 | |
884 RetryJobs copy; | |
885 std::swap(copy, retryJobs_); | |
886 | |
887 const boost::posix_time::ptime now = boost::posix_time::microsec_clock::universal_time(); | |
888 | |
889 assert(retryJobs_.empty()); | |
890 for (RetryJobs::iterator it = copy.begin(); it != copy.end(); ++it) | |
891 { | |
892 if ((*it)->IsRetryReady(now)) | |
893 { | |
894 LOG(INFO) << "Retrying job: " << (*it)->GetId(); | |
895 (*it)->SetState(JobState_Pending); | |
896 pendingJobs_.push(*it); | |
897 pendingJobAvailable_.notify_one(); | |
898 } | |
899 else | |
900 { | |
901 retryJobs_.insert(*it); | |
902 } | |
903 } | |
904 | |
905 CheckInvariants(); | |
906 } | |
907 | |
908 | |
909 bool JobsRegistry::GetState(JobState& state, | |
910 const std::string& id) | |
911 { | |
912 boost::mutex::scoped_lock lock(mutex_); | |
2570
2e879c796ec7
JobsRegistry::SubmitAndWait(), StoreScuJob
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2569
diff
changeset
|
913 return GetStateInternal(state, id); |
2569 | 914 } |
915 | |
916 | |
917 JobsRegistry::RunningJob::RunningJob(JobsRegistry& registry, | |
918 unsigned int timeout) : | |
919 registry_(registry), | |
920 handler_(NULL), | |
921 targetState_(JobState_Failure), | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
922 targetRetryTimeout_(0), |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
923 canceled_(false) |
2569 | 924 { |
925 { | |
926 boost::mutex::scoped_lock lock(registry_.mutex_); | |
927 | |
928 while (registry_.pendingJobs_.empty()) | |
929 { | |
930 if (timeout == 0) | |
931 { | |
932 registry_.pendingJobAvailable_.wait(lock); | |
933 } | |
934 else | |
935 { | |
936 bool success = registry_.pendingJobAvailable_.timed_wait | |
937 (lock, boost::posix_time::milliseconds(timeout)); | |
938 if (!success) | |
939 { | |
940 // No pending job | |
941 return; | |
942 } | |
943 } | |
944 } | |
945 | |
946 handler_ = registry_.pendingJobs_.top(); | |
947 registry_.pendingJobs_.pop(); | |
948 | |
949 assert(handler_->GetState() == JobState_Pending); | |
950 handler_->SetState(JobState_Running); | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
951 handler_->SetLastErrorCode(ErrorCode_Success); |
2569 | 952 |
953 job_ = &handler_->GetJob(); | |
954 id_ = handler_->GetId(); | |
955 priority_ = handler_->GetPriority(); | |
956 } | |
957 } | |
958 | |
959 | |
960 JobsRegistry::RunningJob::~RunningJob() | |
961 { | |
962 if (IsValid()) | |
963 { | |
964 boost::mutex::scoped_lock lock(registry_.mutex_); | |
965 | |
966 switch (targetState_) | |
967 { | |
968 case JobState_Failure: | |
969 registry_.MarkRunningAsCompleted(*handler_, false); | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
970 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
971 if (canceled_) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
972 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
973 handler_->SetLastErrorCode(ErrorCode_CanceledJob); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
974 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
975 |
2569 | 976 break; |
977 | |
978 case JobState_Success: | |
979 registry_.MarkRunningAsCompleted(*handler_, true); | |
980 break; | |
981 | |
982 case JobState_Paused: | |
983 registry_.MarkRunningAsPaused(*handler_); | |
984 break; | |
985 | |
986 case JobState_Retry: | |
987 registry_.MarkRunningAsRetry(*handler_, targetRetryTimeout_); | |
988 break; | |
989 | |
990 default: | |
991 assert(0); | |
992 } | |
993 } | |
994 } | |
995 | |
996 | |
997 bool JobsRegistry::RunningJob::IsValid() const | |
998 { | |
999 return (handler_ != NULL && | |
1000 job_ != NULL); | |
1001 } | |
1002 | |
1003 | |
1004 const std::string& JobsRegistry::RunningJob::GetId() const | |
1005 { | |
1006 if (!IsValid()) | |
1007 { | |
1008 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
1009 } | |
1010 else | |
1011 { | |
1012 return id_; | |
1013 } | |
1014 } | |
1015 | |
1016 | |
1017 int JobsRegistry::RunningJob::GetPriority() const | |
1018 { | |
1019 if (!IsValid()) | |
1020 { | |
1021 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
1022 } | |
1023 else | |
1024 { | |
1025 return priority_; | |
1026 } | |
1027 } | |
1028 | |
1029 | |
1030 IJob& JobsRegistry::RunningJob::GetJob() | |
1031 { | |
1032 if (!IsValid()) | |
1033 { | |
1034 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
1035 } | |
1036 else | |
1037 { | |
1038 return *job_; | |
1039 } | |
1040 } | |
1041 | |
1042 | |
1043 bool JobsRegistry::RunningJob::IsPauseScheduled() | |
1044 { | |
1045 if (!IsValid()) | |
1046 { | |
1047 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
1048 } | |
1049 else | |
1050 { | |
1051 boost::mutex::scoped_lock lock(registry_.mutex_); | |
1052 registry_.CheckInvariants(); | |
1053 assert(handler_->GetState() == JobState_Running); | |
1054 | |
1055 return handler_->IsPauseScheduled(); | |
1056 } | |
1057 } | |
1058 | |
1059 | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1060 bool JobsRegistry::RunningJob::IsCancelScheduled() |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1061 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1062 if (!IsValid()) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1063 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1064 throw OrthancException(ErrorCode_BadSequenceOfCalls); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1065 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1066 else |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1067 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1068 boost::mutex::scoped_lock lock(registry_.mutex_); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1069 registry_.CheckInvariants(); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1070 assert(handler_->GetState() == JobState_Running); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1071 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1072 return handler_->IsCancelScheduled(); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1073 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1074 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1075 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1076 |
2569 | 1077 void JobsRegistry::RunningJob::MarkSuccess() |
1078 { | |
1079 if (!IsValid()) | |
1080 { | |
1081 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
1082 } | |
1083 else | |
1084 { | |
1085 targetState_ = JobState_Success; | |
1086 } | |
1087 } | |
1088 | |
1089 | |
1090 void JobsRegistry::RunningJob::MarkFailure() | |
1091 { | |
1092 if (!IsValid()) | |
1093 { | |
1094 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
1095 } | |
1096 else | |
1097 { | |
1098 targetState_ = JobState_Failure; | |
1099 } | |
1100 } | |
1101 | |
1102 | |
2581
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1103 void JobsRegistry::RunningJob::MarkCanceled() |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1104 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1105 if (!IsValid()) |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1106 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1107 throw OrthancException(ErrorCode_BadSequenceOfCalls); |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1108 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1109 else |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1110 { |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1111 targetState_ = JobState_Failure; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1112 canceled_ = true; |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1113 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1114 } |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1115 |
8da2cffc2378
JobsRegistry::Cancel()
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
2573
diff
changeset
|
1116 |
2569 | 1117 void JobsRegistry::RunningJob::MarkPause() |
1118 { | |
1119 if (!IsValid()) | |
1120 { | |
1121 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
1122 } | |
1123 else | |
1124 { | |
1125 targetState_ = JobState_Paused; | |
1126 } | |
1127 } | |
1128 | |
1129 | |
1130 void JobsRegistry::RunningJob::MarkRetry(unsigned int timeout) | |
1131 { | |
1132 if (!IsValid()) | |
1133 { | |
1134 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
1135 } | |
1136 else | |
1137 { | |
1138 targetState_ = JobState_Retry; | |
1139 targetRetryTimeout_ = timeout; | |
1140 } | |
1141 } | |
1142 | |
1143 | |
1144 void JobsRegistry::RunningJob::UpdateStatus(ErrorCode code) | |
1145 { | |
1146 if (!IsValid()) | |
1147 { | |
1148 throw OrthancException(ErrorCode_BadSequenceOfCalls); | |
1149 } | |
1150 else | |
1151 { | |
1152 JobStatus status(code, *job_); | |
1153 | |
1154 boost::mutex::scoped_lock lock(registry_.mutex_); | |
1155 registry_.CheckInvariants(); | |
1156 assert(handler_->GetState() == JobState_Running); | |
1157 | |
1158 handler_->SetLastStatus(status); | |
1159 } | |
1160 } | |
1161 } |