Mercurial > hg > orthanc-databases
annotate Resources/Orthanc/Plugins/OrthancPluginCppWrapper.h @ 505:38e428f8179d
more detailed error messages
author | Alain Mazy <am@orthanc.team> |
---|---|
date | Fri, 24 May 2024 16:39:38 +0200 |
parents | 711b136e8fe8 |
children | 54d518dcd74a |
rev | line source |
---|---|
152 | 1 /** |
2 * Orthanc - A Lightweight, RESTful DICOM Store | |
3 * Copyright (C) 2012-2016 Sebastien Jodogne, Medical Physics | |
4 * Department, University Hospital of Liege, Belgium | |
459
ecd0b719cff5
update year to 2024
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
425
diff
changeset
|
5 * Copyright (C) 2017-2024 Osimis S.A., Belgium |
ecd0b719cff5
update year to 2024
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
425
diff
changeset
|
6 * Copyright (C) 2021-2024 Sebastien Jodogne, ICTEAM UCLouvain, Belgium |
152 | 7 * |
8 * This program is free software: you can redistribute it and/or | |
9 * modify it under the terms of the GNU General Public License as | |
10 * published by the Free Software Foundation, either version 3 of the | |
11 * License, or (at your option) any later version. | |
160 | 12 * |
152 | 13 * This program is distributed in the hope that it will be useful, but |
14 * WITHOUT ANY WARRANTY; without even the implied warranty of | |
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU | |
16 * General Public License for more details. | |
17 * | |
18 * You should have received a copy of the GNU General Public License | |
19 * along with this program. If not, see <http://www.gnu.org/licenses/>. | |
20 **/ | |
21 | |
22 | |
23 #pragma once | |
24 | |
25 #include "OrthancPluginException.h" | |
26 | |
27 #include <orthanc/OrthancCPlugin.h> | |
28 #include <boost/noncopyable.hpp> | |
29 #include <boost/lexical_cast.hpp> | |
30 #include <boost/date_time/posix_time/posix_time.hpp> | |
31 #include <json/value.h> | |
32 #include <vector> | |
33 #include <list> | |
34 #include <set> | |
35 #include <map> | |
36 | |
37 | |
38 | |
39 /** | |
40 * The definition of ORTHANC_PLUGINS_VERSION_IS_ABOVE below is for | |
41 * backward compatibility with Orthanc SDK <= 1.3.0. | |
42 * | |
43 * $ hg diff -r Orthanc-1.3.0:Orthanc-1.3.1 ../../../Plugins/Include/orthanc/OrthancCPlugin.h | |
44 * | |
45 **/ | |
46 #if !defined(ORTHANC_PLUGINS_VERSION_IS_ABOVE) | |
47 #define ORTHANC_PLUGINS_VERSION_IS_ABOVE(major, minor, revision) \ | |
48 (ORTHANC_PLUGINS_MINIMAL_MAJOR_NUMBER > major || \ | |
49 (ORTHANC_PLUGINS_MINIMAL_MAJOR_NUMBER == major && \ | |
50 (ORTHANC_PLUGINS_MINIMAL_MINOR_NUMBER > minor || \ | |
51 (ORTHANC_PLUGINS_MINIMAL_MINOR_NUMBER == minor && \ | |
52 ORTHANC_PLUGINS_MINIMAL_REVISION_NUMBER >= revision)))) | |
53 #endif | |
54 | |
55 | |
56 #if !defined(ORTHANC_FRAMEWORK_VERSION_IS_ABOVE) | |
57 #define ORTHANC_FRAMEWORK_VERSION_IS_ABOVE(major, minor, revision) \ | |
58 (ORTHANC_VERSION_MAJOR > major || \ | |
59 (ORTHANC_VERSION_MAJOR == major && \ | |
60 (ORTHANC_VERSION_MINOR > minor || \ | |
61 (ORTHANC_VERSION_MINOR == minor && \ | |
62 ORTHANC_VERSION_REVISION >= revision)))) | |
63 #endif | |
64 | |
65 | |
66 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 2, 0) | |
67 // The "OrthancPluginFindMatcher()" primitive was introduced in Orthanc 1.2.0 | |
68 # define HAS_ORTHANC_PLUGIN_FIND_MATCHER 1 | |
69 #else | |
70 # define HAS_ORTHANC_PLUGIN_FIND_MATCHER 0 | |
71 #endif | |
72 | |
73 | |
74 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 4, 2) | |
75 # define HAS_ORTHANC_PLUGIN_PEERS 1 | |
76 # define HAS_ORTHANC_PLUGIN_JOB 1 | |
77 #else | |
78 # define HAS_ORTHANC_PLUGIN_PEERS 0 | |
79 # define HAS_ORTHANC_PLUGIN_JOB 0 | |
80 #endif | |
81 | |
82 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 5, 0) | |
83 # define HAS_ORTHANC_PLUGIN_EXCEPTION_DETAILS 1 | |
84 #else | |
85 # define HAS_ORTHANC_PLUGIN_EXCEPTION_DETAILS 0 | |
86 #endif | |
87 | |
88 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 5, 4) | |
89 # define HAS_ORTHANC_PLUGIN_METRICS 1 | |
90 #else | |
91 # define HAS_ORTHANC_PLUGIN_METRICS 0 | |
92 #endif | |
93 | |
94 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 1, 0) | |
95 # define HAS_ORTHANC_PLUGIN_HTTP_CLIENT 1 | |
96 #else | |
97 # define HAS_ORTHANC_PLUGIN_HTTP_CLIENT 0 | |
98 #endif | |
99 | |
100 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 5, 7) | |
101 # define HAS_ORTHANC_PLUGIN_CHUNKED_HTTP_CLIENT 1 | |
102 #else | |
103 # define HAS_ORTHANC_PLUGIN_CHUNKED_HTTP_CLIENT 0 | |
104 #endif | |
105 | |
106 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 5, 7) | |
107 # define HAS_ORTHANC_PLUGIN_CHUNKED_HTTP_SERVER 1 | |
108 #else | |
109 # define HAS_ORTHANC_PLUGIN_CHUNKED_HTTP_SERVER 0 | |
110 #endif | |
111 | |
112 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 6, 0) | |
113 # define HAS_ORTHANC_PLUGIN_STORAGE_COMMITMENT_SCP 1 | |
114 #else | |
115 # define HAS_ORTHANC_PLUGIN_STORAGE_COMMITMENT_SCP 0 | |
116 #endif | |
117 | |
397 | 118 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 9, 2) |
119 # define HAS_ORTHANC_PLUGIN_GENERIC_CALL_REST_API 1 | |
120 #else | |
121 # define HAS_ORTHANC_PLUGIN_GENERIC_CALL_REST_API 0 | |
122 #endif | |
123 | |
124 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 10, 1) | |
125 # define HAS_ORTHANC_PLUGIN_WEBDAV 1 | |
126 #else | |
127 # define HAS_ORTHANC_PLUGIN_WEBDAV 0 | |
128 #endif | |
129 | |
152 | 130 |
131 | |
132 namespace OrthancPlugins | |
133 { | |
134 typedef void (*RestCallback) (OrthancPluginRestOutput* output, | |
135 const char* url, | |
136 const OrthancPluginHttpRequest* request); | |
137 | |
138 void SetGlobalContext(OrthancPluginContext* context); | |
139 | |
425 | 140 void ResetGlobalContext(); |
141 | |
152 | 142 bool HasGlobalContext(); |
143 | |
144 OrthancPluginContext* GetGlobalContext(); | |
145 | |
146 | |
147 class OrthancImage; | |
148 | |
149 | |
150 class MemoryBuffer : public boost::noncopyable | |
151 { | |
152 private: | |
153 OrthancPluginMemoryBuffer buffer_; | |
154 | |
155 void Check(OrthancPluginErrorCode code); | |
156 | |
157 bool CheckHttp(OrthancPluginErrorCode code); | |
158 | |
159 public: | |
160 MemoryBuffer(); | |
161 | |
162 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 7, 0) | |
163 // This constructor makes a copy of the given buffer in the memory | |
164 // handled by the Orthanc core | |
165 MemoryBuffer(const void* buffer, | |
166 size_t size); | |
167 #endif | |
168 | |
169 ~MemoryBuffer() | |
170 { | |
171 Clear(); | |
172 } | |
173 | |
174 OrthancPluginMemoryBuffer* operator*() | |
175 { | |
176 return &buffer_; | |
177 } | |
178 | |
179 // This transfers ownership from "other" to "this" | |
180 void Assign(OrthancPluginMemoryBuffer& other); | |
181 | |
182 void Swap(MemoryBuffer& other); | |
183 | |
184 OrthancPluginMemoryBuffer Release(); | |
185 | |
186 const char* GetData() const | |
187 { | |
188 if (buffer_.size > 0) | |
189 { | |
190 return reinterpret_cast<const char*>(buffer_.data); | |
191 } | |
192 else | |
193 { | |
194 return NULL; | |
195 } | |
196 } | |
197 | |
198 size_t GetSize() const | |
199 { | |
200 return buffer_.size; | |
201 } | |
202 | |
203 bool IsEmpty() const | |
204 { | |
205 return GetSize() == 0 || GetData() == NULL; | |
206 } | |
207 | |
208 void Clear(); | |
209 | |
210 void ToString(std::string& target) const; | |
211 | |
212 void ToJson(Json::Value& target) const; | |
213 | |
214 bool RestApiGet(const std::string& uri, | |
215 bool applyPlugins); | |
216 | |
217 bool RestApiGet(const std::string& uri, | |
218 const std::map<std::string, std::string>& httpHeaders, | |
219 bool applyPlugins); | |
220 | |
221 bool RestApiPost(const std::string& uri, | |
222 const void* body, | |
223 size_t bodySize, | |
224 bool applyPlugins); | |
225 | |
226 bool RestApiPut(const std::string& uri, | |
227 const void* body, | |
228 size_t bodySize, | |
229 bool applyPlugins); | |
230 | |
231 bool RestApiPost(const std::string& uri, | |
232 const Json::Value& body, | |
233 bool applyPlugins); | |
234 | |
397 | 235 #if HAS_ORTHANC_PLUGIN_GENERIC_CALL_REST_API == 1 |
236 bool RestApiPost(const std::string& uri, | |
237 const Json::Value& body, | |
238 const std::map<std::string, std::string>& httpHeaders, | |
239 bool applyPlugins); | |
240 | |
241 bool RestApiPost(const std::string& uri, | |
242 const void* body, | |
243 size_t bodySize, | |
244 const std::map<std::string, std::string>& httpHeaders, | |
245 bool applyPlugins); | |
246 #endif | |
247 | |
152 | 248 bool RestApiPut(const std::string& uri, |
249 const Json::Value& body, | |
250 bool applyPlugins); | |
251 | |
252 bool RestApiPost(const std::string& uri, | |
253 const std::string& body, | |
254 bool applyPlugins) | |
255 { | |
256 return RestApiPost(uri, body.empty() ? NULL : body.c_str(), body.size(), applyPlugins); | |
257 } | |
258 | |
259 bool RestApiPut(const std::string& uri, | |
260 const std::string& body, | |
261 bool applyPlugins) | |
262 { | |
263 return RestApiPut(uri, body.empty() ? NULL : body.c_str(), body.size(), applyPlugins); | |
264 } | |
265 | |
266 void CreateDicom(const Json::Value& tags, | |
267 OrthancPluginCreateDicomFlags flags); | |
268 | |
269 void CreateDicom(const Json::Value& tags, | |
270 const OrthancImage& pixelData, | |
271 OrthancPluginCreateDicomFlags flags); | |
272 | |
273 void ReadFile(const std::string& path); | |
274 | |
275 void GetDicomQuery(const OrthancPluginWorklistQuery* query); | |
276 | |
277 void DicomToJson(Json::Value& target, | |
278 OrthancPluginDicomToJsonFormat format, | |
279 OrthancPluginDicomToJsonFlags flags, | |
280 uint32_t maxStringLength); | |
281 | |
282 bool HttpGet(const std::string& url, | |
283 const std::string& username, | |
284 const std::string& password); | |
285 | |
286 bool HttpPost(const std::string& url, | |
287 const std::string& body, | |
288 const std::string& username, | |
289 const std::string& password); | |
290 | |
291 bool HttpPut(const std::string& url, | |
292 const std::string& body, | |
293 const std::string& username, | |
294 const std::string& password); | |
295 | |
296 void GetDicomInstance(const std::string& instanceId); | |
297 }; | |
298 | |
299 | |
300 class OrthancString : public boost::noncopyable | |
301 { | |
302 private: | |
303 char* str_; | |
304 | |
305 void Clear(); | |
306 | |
307 public: | |
308 OrthancString() : | |
309 str_(NULL) | |
310 { | |
311 } | |
312 | |
313 ~OrthancString() | |
314 { | |
315 Clear(); | |
316 } | |
317 | |
318 // This transfers ownership, warning: The string must have been | |
319 // allocated by the Orthanc core | |
320 void Assign(char* str); | |
321 | |
322 const char* GetContent() const | |
323 { | |
324 return str_; | |
325 } | |
326 | |
397 | 327 bool IsNullOrEmpty() const |
328 { | |
329 return str_ == NULL || str_[0] == 0; | |
330 } | |
331 | |
152 | 332 void ToString(std::string& target) const; |
333 | |
334 void ToJson(Json::Value& target) const; | |
397 | 335 |
336 void ToJsonWithoutComments(Json::Value& target) const; | |
337 }; | |
152 | 338 |
339 | |
340 class OrthancConfiguration : public boost::noncopyable | |
341 { | |
342 private: | |
343 Json::Value configuration_; // Necessarily a Json::objectValue | |
344 std::string path_; | |
345 | |
346 std::string GetPath(const std::string& key) const; | |
347 | |
348 void LoadConfiguration(); | |
349 | |
350 public: | |
397 | 351 OrthancConfiguration(); // loads the full Orthanc configuration |
152 | 352 |
353 explicit OrthancConfiguration(bool load); | |
354 | |
397 | 355 explicit OrthancConfiguration(const Json::Value& configuration, const std::string& path); // e.g. to load a section from a default json content |
356 | |
152 | 357 const Json::Value& GetJson() const |
358 { | |
359 return configuration_; | |
360 } | |
361 | |
362 bool IsSection(const std::string& key) const; | |
363 | |
364 void GetSection(OrthancConfiguration& target, | |
365 const std::string& key) const; | |
366 | |
367 bool LookupStringValue(std::string& target, | |
368 const std::string& key) const; | |
369 | |
370 bool LookupIntegerValue(int& target, | |
371 const std::string& key) const; | |
372 | |
373 bool LookupUnsignedIntegerValue(unsigned int& target, | |
374 const std::string& key) const; | |
375 | |
376 bool LookupBooleanValue(bool& target, | |
377 const std::string& key) const; | |
378 | |
379 bool LookupFloatValue(float& target, | |
380 const std::string& key) const; | |
381 | |
382 bool LookupListOfStrings(std::list<std::string>& target, | |
383 const std::string& key, | |
384 bool allowSingleString) const; | |
385 | |
386 bool LookupSetOfStrings(std::set<std::string>& target, | |
387 const std::string& key, | |
388 bool allowSingleString) const; | |
389 | |
390 std::string GetStringValue(const std::string& key, | |
391 const std::string& defaultValue) const; | |
392 | |
393 int GetIntegerValue(const std::string& key, | |
394 int defaultValue) const; | |
395 | |
396 unsigned int GetUnsignedIntegerValue(const std::string& key, | |
397 unsigned int defaultValue) const; | |
398 | |
399 bool GetBooleanValue(const std::string& key, | |
400 bool defaultValue) const; | |
401 | |
402 float GetFloatValue(const std::string& key, | |
403 float defaultValue) const; | |
404 | |
405 void GetDictionary(std::map<std::string, std::string>& target, | |
406 const std::string& key) const; | |
407 }; | |
408 | |
409 class OrthancImage : public boost::noncopyable | |
410 { | |
411 private: | |
412 OrthancPluginImage* image_; | |
413 | |
414 void Clear(); | |
415 | |
416 void CheckImageAvailable() const; | |
417 | |
418 public: | |
419 OrthancImage(); | |
420 | |
421 explicit OrthancImage(OrthancPluginImage* image); | |
422 | |
423 OrthancImage(OrthancPluginPixelFormat format, | |
424 uint32_t width, | |
425 uint32_t height); | |
426 | |
427 OrthancImage(OrthancPluginPixelFormat format, | |
428 uint32_t width, | |
429 uint32_t height, | |
430 uint32_t pitch, | |
431 void* buffer); | |
432 | |
433 ~OrthancImage() | |
434 { | |
435 Clear(); | |
436 } | |
437 | |
438 void UncompressPngImage(const void* data, | |
439 size_t size); | |
440 | |
441 void UncompressJpegImage(const void* data, | |
442 size_t size); | |
443 | |
444 void DecodeDicomImage(const void* data, | |
445 size_t size, | |
446 unsigned int frame); | |
447 | |
448 OrthancPluginPixelFormat GetPixelFormat() const; | |
449 | |
450 unsigned int GetWidth() const; | |
451 | |
452 unsigned int GetHeight() const; | |
453 | |
454 unsigned int GetPitch() const; | |
455 | |
456 void* GetBuffer() const; | |
457 | |
458 const OrthancPluginImage* GetObject() const | |
459 { | |
460 return image_; | |
461 } | |
462 | |
463 void CompressPngImage(MemoryBuffer& target) const; | |
464 | |
465 void CompressJpegImage(MemoryBuffer& target, | |
466 uint8_t quality) const; | |
467 | |
468 void AnswerPngImage(OrthancPluginRestOutput* output) const; | |
469 | |
470 void AnswerJpegImage(OrthancPluginRestOutput* output, | |
471 uint8_t quality) const; | |
472 | |
473 void* GetWriteableBuffer(); | |
474 | |
475 OrthancPluginImage* Release(); | |
476 }; | |
477 | |
478 | |
479 #if HAS_ORTHANC_PLUGIN_FIND_MATCHER == 1 | |
480 class FindMatcher : public boost::noncopyable | |
481 { | |
482 private: | |
483 OrthancPluginFindMatcher* matcher_; | |
484 const OrthancPluginWorklistQuery* worklist_; | |
485 | |
486 void SetupDicom(const void* query, | |
487 uint32_t size); | |
488 | |
489 public: | |
490 explicit FindMatcher(const OrthancPluginWorklistQuery* worklist); | |
491 | |
492 FindMatcher(const void* query, | |
493 uint32_t size) | |
494 { | |
495 SetupDicom(query, size); | |
496 } | |
497 | |
498 explicit FindMatcher(const MemoryBuffer& dicom) | |
499 { | |
500 SetupDicom(dicom.GetData(), dicom.GetSize()); | |
501 } | |
502 | |
503 ~FindMatcher(); | |
504 | |
505 bool IsMatch(const void* dicom, | |
506 uint32_t size) const; | |
507 | |
508 bool IsMatch(const MemoryBuffer& dicom) const | |
509 { | |
510 return IsMatch(dicom.GetData(), dicom.GetSize()); | |
511 } | |
512 }; | |
513 #endif | |
514 | |
515 | |
193
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
516 bool ReadJson(Json::Value& target, |
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
517 const std::string& source); |
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
518 |
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
519 bool ReadJson(Json::Value& target, |
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
520 const void* buffer, |
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
521 size_t size); |
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
522 |
272
c7dc70a0a477
upgrade to Orthanc SDK 1.9.2
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
193
diff
changeset
|
523 bool ReadJsonWithoutComments(Json::Value& target, |
c7dc70a0a477
upgrade to Orthanc SDK 1.9.2
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
193
diff
changeset
|
524 const std::string& source); |
c7dc70a0a477
upgrade to Orthanc SDK 1.9.2
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
193
diff
changeset
|
525 |
c7dc70a0a477
upgrade to Orthanc SDK 1.9.2
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
193
diff
changeset
|
526 bool ReadJsonWithoutComments(Json::Value& target, |
c7dc70a0a477
upgrade to Orthanc SDK 1.9.2
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
193
diff
changeset
|
527 const void* buffer, |
c7dc70a0a477
upgrade to Orthanc SDK 1.9.2
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
193
diff
changeset
|
528 size_t size); |
c7dc70a0a477
upgrade to Orthanc SDK 1.9.2
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
193
diff
changeset
|
529 |
193
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
530 void WriteFastJson(std::string& target, |
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
531 const Json::Value& source); |
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
532 |
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
533 void WriteStyledJson(std::string& target, |
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
534 const Json::Value& source); |
3236894320d6
upgrade to year 2021
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
170
diff
changeset
|
535 |
152 | 536 bool RestApiGet(Json::Value& result, |
537 const std::string& uri, | |
538 bool applyPlugins); | |
539 | |
397 | 540 bool RestApiGet(Json::Value& result, |
541 const std::string& uri, | |
542 const std::map<std::string, std::string>& httpHeaders, | |
543 bool applyPlugins); | |
544 | |
152 | 545 bool RestApiGetString(std::string& result, |
546 const std::string& uri, | |
547 bool applyPlugins); | |
548 | |
549 bool RestApiGetString(std::string& result, | |
550 const std::string& uri, | |
551 const std::map<std::string, std::string>& httpHeaders, | |
552 bool applyPlugins); | |
553 | |
554 bool RestApiPost(std::string& result, | |
555 const std::string& uri, | |
556 const void* body, | |
557 size_t bodySize, | |
558 bool applyPlugins); | |
559 | |
560 bool RestApiPost(Json::Value& result, | |
561 const std::string& uri, | |
562 const void* body, | |
563 size_t bodySize, | |
564 bool applyPlugins); | |
565 | |
397 | 566 #if HAS_ORTHANC_PLUGIN_GENERIC_CALL_REST_API == 1 |
567 bool RestApiPost(Json::Value& result, | |
568 const std::string& uri, | |
569 const Json::Value& body, | |
570 const std::map<std::string, std::string>& httpHeaders, | |
571 bool applyPlugins); | |
572 #endif | |
573 | |
152 | 574 bool RestApiPost(Json::Value& result, |
575 const std::string& uri, | |
576 const Json::Value& body, | |
577 bool applyPlugins); | |
578 | |
579 inline bool RestApiPost(Json::Value& result, | |
580 const std::string& uri, | |
581 const std::string& body, | |
582 bool applyPlugins) | |
583 { | |
584 return RestApiPost(result, uri, body.empty() ? NULL : body.c_str(), | |
585 body.size(), applyPlugins); | |
586 } | |
587 | |
588 inline bool RestApiPost(Json::Value& result, | |
589 const std::string& uri, | |
590 const MemoryBuffer& body, | |
591 bool applyPlugins) | |
592 { | |
593 return RestApiPost(result, uri, body.GetData(), | |
594 body.GetSize(), applyPlugins); | |
595 } | |
596 | |
597 bool RestApiPut(Json::Value& result, | |
598 const std::string& uri, | |
599 const void* body, | |
600 size_t bodySize, | |
601 bool applyPlugins); | |
602 | |
603 bool RestApiPut(Json::Value& result, | |
604 const std::string& uri, | |
605 const Json::Value& body, | |
606 bool applyPlugins); | |
607 | |
608 inline bool RestApiPut(Json::Value& result, | |
609 const std::string& uri, | |
610 const std::string& body, | |
611 bool applyPlugins) | |
612 { | |
613 return RestApiPut(result, uri, body.empty() ? NULL : body.c_str(), | |
614 body.size(), applyPlugins); | |
615 } | |
616 | |
617 bool RestApiDelete(const std::string& uri, | |
618 bool applyPlugins); | |
619 | |
620 bool HttpDelete(const std::string& url, | |
621 const std::string& username, | |
622 const std::string& password); | |
623 | |
624 void AnswerJson(const Json::Value& value, | |
625 OrthancPluginRestOutput* output); | |
626 | |
627 void AnswerString(const std::string& answer, | |
628 const char* mimeType, | |
629 OrthancPluginRestOutput* output); | |
630 | |
631 void AnswerHttpError(uint16_t httpError, | |
632 OrthancPluginRestOutput* output); | |
633 | |
634 void AnswerMethodNotAllowed(OrthancPluginRestOutput* output, const char* allowedMethods); | |
635 | |
636 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 5, 0) | |
637 const char* AutodetectMimeType(const std::string& path); | |
638 #endif | |
639 | |
640 void LogError(const std::string& message); | |
641 | |
642 void LogWarning(const std::string& message); | |
643 | |
644 void LogInfo(const std::string& message); | |
645 | |
646 void ReportMinimalOrthancVersion(unsigned int major, | |
647 unsigned int minor, | |
648 unsigned int revision); | |
649 | |
650 bool CheckMinimalOrthancVersion(unsigned int major, | |
651 unsigned int minor, | |
652 unsigned int revision); | |
653 | |
397 | 654 bool CheckMinimalVersion(const char* version, |
655 unsigned int major, | |
656 unsigned int minor, | |
657 unsigned int revision); | |
152 | 658 |
659 namespace Internals | |
660 { | |
661 template <RestCallback Callback> | |
662 static OrthancPluginErrorCode Protect(OrthancPluginRestOutput* output, | |
663 const char* url, | |
664 const OrthancPluginHttpRequest* request) | |
665 { | |
666 try | |
667 { | |
668 Callback(output, url, request); | |
669 return OrthancPluginErrorCode_Success; | |
670 } | |
671 catch (ORTHANC_PLUGINS_EXCEPTION_CLASS& e) | |
672 { | |
673 #if HAS_ORTHANC_EXCEPTION == 1 && HAS_ORTHANC_PLUGIN_EXCEPTION_DETAILS == 1 | |
674 if (HasGlobalContext() && | |
675 e.HasDetails()) | |
676 { | |
677 // The "false" instructs Orthanc not to log the detailed | |
678 // error message. This is to avoid duplicating the details, | |
679 // because "OrthancException" already does it on construction. | |
680 OrthancPluginSetHttpErrorDetails | |
681 (GetGlobalContext(), output, e.GetDetails(), false); | |
682 } | |
683 #endif | |
684 | |
685 return static_cast<OrthancPluginErrorCode>(e.GetErrorCode()); | |
686 } | |
687 catch (boost::bad_lexical_cast&) | |
688 { | |
689 return OrthancPluginErrorCode_BadFileFormat; | |
690 } | |
691 catch (...) | |
692 { | |
693 return OrthancPluginErrorCode_Plugin; | |
694 } | |
695 } | |
696 } | |
697 | |
698 | |
699 template <RestCallback Callback> | |
700 void RegisterRestCallback(const std::string& uri, | |
701 bool isThreadSafe) | |
702 { | |
703 if (isThreadSafe) | |
704 { | |
705 OrthancPluginRegisterRestCallbackNoLock | |
706 (GetGlobalContext(), uri.c_str(), Internals::Protect<Callback>); | |
707 } | |
708 else | |
709 { | |
710 OrthancPluginRegisterRestCallback | |
711 (GetGlobalContext(), uri.c_str(), Internals::Protect<Callback>); | |
712 } | |
713 } | |
714 | |
715 | |
716 #if HAS_ORTHANC_PLUGIN_PEERS == 1 | |
717 class OrthancPeers : public boost::noncopyable | |
718 { | |
719 private: | |
720 typedef std::map<std::string, uint32_t> Index; | |
721 | |
722 OrthancPluginPeers *peers_; | |
723 Index index_; | |
724 uint32_t timeout_; | |
725 | |
726 size_t GetPeerIndex(const std::string& name) const; | |
727 | |
728 public: | |
729 OrthancPeers(); | |
730 | |
731 ~OrthancPeers(); | |
732 | |
733 uint32_t GetTimeout() const | |
734 { | |
735 return timeout_; | |
736 } | |
737 | |
738 void SetTimeout(uint32_t timeout) | |
739 { | |
740 timeout_ = timeout; | |
741 } | |
742 | |
743 bool LookupName(size_t& target, | |
744 const std::string& name) const; | |
745 | |
746 std::string GetPeerName(size_t index) const; | |
747 | |
748 std::string GetPeerUrl(size_t index) const; | |
749 | |
750 std::string GetPeerUrl(const std::string& name) const; | |
751 | |
752 size_t GetPeersCount() const | |
753 { | |
754 return index_.size(); | |
755 } | |
756 | |
757 bool LookupUserProperty(std::string& value, | |
758 size_t index, | |
759 const std::string& key) const; | |
760 | |
761 bool LookupUserProperty(std::string& value, | |
762 const std::string& peer, | |
763 const std::string& key) const; | |
764 | |
765 bool DoGet(MemoryBuffer& target, | |
766 size_t index, | |
397 | 767 const std::string& uri, |
768 const std::map<std::string, std::string>& headers) const; | |
152 | 769 |
770 bool DoGet(MemoryBuffer& target, | |
771 const std::string& name, | |
397 | 772 const std::string& uri, |
773 const std::map<std::string, std::string>& headers) const; | |
152 | 774 |
775 bool DoGet(Json::Value& target, | |
776 size_t index, | |
397 | 777 const std::string& uri, |
778 const std::map<std::string, std::string>& headers) const; | |
152 | 779 |
780 bool DoGet(Json::Value& target, | |
781 const std::string& name, | |
397 | 782 const std::string& uri, |
783 const std::map<std::string, std::string>& headers) const; | |
152 | 784 |
785 bool DoPost(MemoryBuffer& target, | |
786 size_t index, | |
787 const std::string& uri, | |
397 | 788 const std::string& body, |
789 const std::map<std::string, std::string>& headers) const; | |
152 | 790 |
791 bool DoPost(MemoryBuffer& target, | |
792 const std::string& name, | |
793 const std::string& uri, | |
397 | 794 const std::string& body, |
795 const std::map<std::string, std::string>& headers) const; | |
152 | 796 |
797 bool DoPost(Json::Value& target, | |
798 size_t index, | |
799 const std::string& uri, | |
397 | 800 const std::string& body, |
801 const std::map<std::string, std::string>& headers) const; | |
152 | 802 |
803 bool DoPost(Json::Value& target, | |
804 const std::string& name, | |
805 const std::string& uri, | |
397 | 806 const std::string& body, |
807 const std::map<std::string, std::string>& headers) const; | |
152 | 808 |
809 bool DoPut(size_t index, | |
810 const std::string& uri, | |
397 | 811 const std::string& body, |
812 const std::map<std::string, std::string>& headers) const; | |
152 | 813 |
814 bool DoPut(const std::string& name, | |
815 const std::string& uri, | |
397 | 816 const std::string& body, |
817 const std::map<std::string, std::string>& headers) const; | |
152 | 818 |
819 bool DoDelete(size_t index, | |
397 | 820 const std::string& uri, |
821 const std::map<std::string, std::string>& headers) const; | |
152 | 822 |
823 bool DoDelete(const std::string& name, | |
397 | 824 const std::string& uri, |
825 const std::map<std::string, std::string>& headers) const; | |
152 | 826 }; |
827 #endif | |
828 | |
829 | |
830 | |
831 #if HAS_ORTHANC_PLUGIN_JOB == 1 | |
832 class OrthancJob : public boost::noncopyable | |
833 { | |
834 private: | |
835 std::string jobType_; | |
836 std::string content_; | |
837 bool hasSerialized_; | |
838 std::string serialized_; | |
839 float progress_; | |
840 | |
841 static void CallbackFinalize(void* job); | |
842 | |
843 static float CallbackGetProgress(void* job); | |
844 | |
397 | 845 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 11, 3) |
846 static OrthancPluginErrorCode CallbackGetContent(OrthancPluginMemoryBuffer* target, | |
847 void* job); | |
848 #else | |
152 | 849 static const char* CallbackGetContent(void* job); |
397 | 850 #endif |
152 | 851 |
397 | 852 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 11, 3) |
853 static int32_t CallbackGetSerialized(OrthancPluginMemoryBuffer* target, | |
854 void* job); | |
855 #else | |
152 | 856 static const char* CallbackGetSerialized(void* job); |
397 | 857 #endif |
152 | 858 |
859 static OrthancPluginJobStepStatus CallbackStep(void* job); | |
860 | |
861 static OrthancPluginErrorCode CallbackStop(void* job, | |
862 OrthancPluginJobStopReason reason); | |
863 | |
864 static OrthancPluginErrorCode CallbackReset(void* job); | |
865 | |
866 protected: | |
867 void ClearContent(); | |
868 | |
869 void UpdateContent(const Json::Value& content); | |
870 | |
871 void ClearSerialized(); | |
872 | |
873 void UpdateSerialized(const Json::Value& serialized); | |
874 | |
875 void UpdateProgress(float progress); | |
876 | |
877 public: | |
170 | 878 explicit OrthancJob(const std::string& jobType); |
152 | 879 |
880 virtual ~OrthancJob() | |
881 { | |
882 } | |
883 | |
884 virtual OrthancPluginJobStepStatus Step() = 0; | |
885 | |
886 virtual void Stop(OrthancPluginJobStopReason reason) = 0; | |
887 | |
888 virtual void Reset() = 0; | |
889 | |
890 static OrthancPluginJob* Create(OrthancJob* job /* takes ownership */); | |
891 | |
892 static std::string Submit(OrthancJob* job /* takes ownership */, | |
893 int priority); | |
894 | |
895 static void SubmitAndWait(Json::Value& result, | |
896 OrthancJob* job /* takes ownership */, | |
897 int priority); | |
898 | |
899 // Submit a job from a POST on the REST API with the same | |
900 // conventions as in the Orthanc core (according to the | |
901 // "Synchronous" and "Priority" options) | |
902 static void SubmitFromRestApiPost(OrthancPluginRestOutput* output, | |
903 const Json::Value& body, | |
904 OrthancJob* job); | |
905 }; | |
906 #endif | |
907 | |
908 | |
909 #if HAS_ORTHANC_PLUGIN_METRICS == 1 | |
910 inline void SetMetricsValue(char* name, | |
911 float value) | |
912 { | |
913 OrthancPluginSetMetricsValue(GetGlobalContext(), name, | |
914 value, OrthancPluginMetricsType_Default); | |
915 } | |
916 | |
917 class MetricsTimer : public boost::noncopyable | |
918 { | |
919 private: | |
920 std::string name_; | |
921 boost::posix_time::ptime start_; | |
922 | |
923 public: | |
924 explicit MetricsTimer(const char* name); | |
925 | |
926 ~MetricsTimer(); | |
927 }; | |
928 #endif | |
929 | |
930 | |
931 #if HAS_ORTHANC_PLUGIN_HTTP_CLIENT == 1 | |
932 class HttpClient : public boost::noncopyable | |
933 { | |
934 public: | |
935 typedef std::map<std::string, std::string> HttpHeaders; | |
936 | |
937 class IRequestBody : public boost::noncopyable | |
938 { | |
939 public: | |
940 virtual ~IRequestBody() | |
941 { | |
942 } | |
943 | |
944 virtual bool ReadNextChunk(std::string& chunk) = 0; | |
945 }; | |
946 | |
947 | |
948 class IAnswer : public boost::noncopyable | |
949 { | |
950 public: | |
951 virtual ~IAnswer() | |
952 { | |
953 } | |
954 | |
955 virtual void AddHeader(const std::string& key, | |
956 const std::string& value) = 0; | |
957 | |
958 virtual void AddChunk(const void* data, | |
959 size_t size) = 0; | |
960 }; | |
961 | |
962 | |
963 private: | |
964 class RequestBodyWrapper; | |
965 | |
966 uint16_t httpStatus_; | |
967 OrthancPluginHttpMethod method_; | |
968 std::string url_; | |
969 HttpHeaders headers_; | |
970 std::string username_; | |
971 std::string password_; | |
972 uint32_t timeout_; | |
973 std::string certificateFile_; | |
974 std::string certificateKeyFile_; | |
975 std::string certificateKeyPassword_; | |
976 bool pkcs11_; | |
977 std::string fullBody_; | |
978 IRequestBody* chunkedBody_; | |
979 bool allowChunkedTransfers_; | |
980 | |
981 #if HAS_ORTHANC_PLUGIN_CHUNKED_HTTP_CLIENT == 1 | |
982 void ExecuteWithStream(uint16_t& httpStatus, // out | |
983 IAnswer& answer, // out | |
984 IRequestBody& body) const; | |
985 #endif | |
986 | |
987 void ExecuteWithoutStream(uint16_t& httpStatus, // out | |
988 HttpHeaders& answerHeaders, // out | |
989 std::string& answerBody, // out | |
990 const std::string& body) const; | |
991 | |
992 public: | |
993 HttpClient(); | |
994 | |
995 uint16_t GetHttpStatus() const | |
996 { | |
997 return httpStatus_; | |
998 } | |
999 | |
1000 void SetMethod(OrthancPluginHttpMethod method) | |
1001 { | |
1002 method_ = method; | |
1003 } | |
1004 | |
1005 const std::string& GetUrl() const | |
1006 { | |
1007 return url_; | |
1008 } | |
1009 | |
1010 void SetUrl(const std::string& url) | |
1011 { | |
1012 url_ = url; | |
1013 } | |
1014 | |
1015 void SetHeaders(const HttpHeaders& headers) | |
1016 { | |
1017 headers_ = headers; | |
1018 } | |
1019 | |
1020 void AddHeader(const std::string& key, | |
1021 const std::string& value) | |
1022 { | |
1023 headers_[key] = value; | |
1024 } | |
1025 | |
1026 void AddHeaders(const HttpHeaders& headers); | |
1027 | |
1028 void SetCredentials(const std::string& username, | |
1029 const std::string& password); | |
1030 | |
1031 void ClearCredentials(); | |
1032 | |
1033 void SetTimeout(unsigned int timeout) // 0 for default timeout | |
1034 { | |
1035 timeout_ = timeout; | |
1036 } | |
1037 | |
1038 void SetCertificate(const std::string& certificateFile, | |
1039 const std::string& keyFile, | |
1040 const std::string& keyPassword); | |
1041 | |
1042 void ClearCertificate(); | |
1043 | |
1044 void SetPkcs11(bool pkcs11) | |
1045 { | |
1046 pkcs11_ = pkcs11; | |
1047 } | |
1048 | |
1049 void ClearBody(); | |
1050 | |
1051 void SwapBody(std::string& body); | |
1052 | |
1053 void SetBody(const std::string& body); | |
1054 | |
1055 void SetBody(IRequestBody& body); | |
1056 | |
1057 // This function can be used to disable chunked transfers if the | |
1058 // remote server is Orthanc with a version <= 1.5.6. | |
1059 void SetChunkedTransfersAllowed(bool allow) | |
1060 { | |
1061 allowChunkedTransfers_ = allow; | |
1062 } | |
1063 | |
1064 bool IsChunkedTransfersAllowed() const | |
1065 { | |
1066 return allowChunkedTransfers_; | |
1067 } | |
1068 | |
1069 void Execute(IAnswer& answer); | |
1070 | |
1071 void Execute(HttpHeaders& answerHeaders /* out */, | |
1072 std::string& answerBody /* out */); | |
1073 | |
1074 void Execute(HttpHeaders& answerHeaders /* out */, | |
1075 Json::Value& answerBody /* out */); | |
1076 | |
1077 void Execute(); | |
1078 }; | |
1079 #endif | |
1080 | |
1081 | |
1082 | |
1083 class IChunkedRequestReader : public boost::noncopyable | |
1084 { | |
1085 public: | |
1086 virtual ~IChunkedRequestReader() | |
1087 { | |
1088 } | |
1089 | |
1090 virtual void AddChunk(const void* data, | |
1091 size_t size) = 0; | |
1092 | |
1093 virtual void Execute(OrthancPluginRestOutput* output) = 0; | |
1094 }; | |
1095 | |
1096 | |
1097 typedef IChunkedRequestReader* (*ChunkedRestCallback) (const char* url, | |
1098 const OrthancPluginHttpRequest* request); | |
1099 | |
1100 | |
1101 namespace Internals | |
1102 { | |
1103 void NullRestCallback(OrthancPluginRestOutput* output, | |
1104 const char* url, | |
1105 const OrthancPluginHttpRequest* request); | |
1106 | |
1107 IChunkedRequestReader *NullChunkedRestCallback(const char* url, | |
1108 const OrthancPluginHttpRequest* request); | |
1109 | |
1110 | |
1111 #if HAS_ORTHANC_PLUGIN_CHUNKED_HTTP_SERVER == 1 | |
1112 template <ChunkedRestCallback Callback> | |
1113 static OrthancPluginErrorCode ChunkedProtect(OrthancPluginServerChunkedRequestReader** reader, | |
1114 const char* url, | |
1115 const OrthancPluginHttpRequest* request) | |
1116 { | |
1117 try | |
1118 { | |
1119 if (reader == NULL) | |
1120 { | |
1121 return OrthancPluginErrorCode_InternalError; | |
1122 } | |
1123 else | |
1124 { | |
1125 *reader = reinterpret_cast<OrthancPluginServerChunkedRequestReader*>(Callback(url, request)); | |
1126 if (*reader == NULL) | |
1127 { | |
1128 return OrthancPluginErrorCode_Plugin; | |
1129 } | |
1130 else | |
1131 { | |
1132 return OrthancPluginErrorCode_Success; | |
1133 } | |
1134 } | |
1135 } | |
1136 catch (ORTHANC_PLUGINS_EXCEPTION_CLASS& e) | |
1137 { | |
1138 return static_cast<OrthancPluginErrorCode>(e.GetErrorCode()); | |
1139 } | |
1140 catch (boost::bad_lexical_cast&) | |
1141 { | |
1142 return OrthancPluginErrorCode_BadFileFormat; | |
1143 } | |
1144 catch (...) | |
1145 { | |
1146 return OrthancPluginErrorCode_Plugin; | |
1147 } | |
1148 } | |
1149 | |
1150 OrthancPluginErrorCode ChunkedRequestReaderAddChunk( | |
1151 OrthancPluginServerChunkedRequestReader* reader, | |
1152 const void* data, | |
1153 uint32_t size); | |
1154 | |
1155 OrthancPluginErrorCode ChunkedRequestReaderExecute( | |
1156 OrthancPluginServerChunkedRequestReader* reader, | |
1157 OrthancPluginRestOutput* output); | |
1158 | |
1159 void ChunkedRequestReaderFinalize( | |
1160 OrthancPluginServerChunkedRequestReader* reader); | |
1161 | |
1162 #else | |
1163 | |
1164 OrthancPluginErrorCode ChunkedRestCompatibility(OrthancPluginRestOutput* output, | |
1165 const char* url, | |
1166 const OrthancPluginHttpRequest* request, | |
1167 RestCallback GetHandler, | |
1168 ChunkedRestCallback PostHandler, | |
1169 RestCallback DeleteHandler, | |
1170 ChunkedRestCallback PutHandler); | |
1171 | |
1172 template< | |
1173 RestCallback GetHandler, | |
1174 ChunkedRestCallback PostHandler, | |
1175 RestCallback DeleteHandler, | |
1176 ChunkedRestCallback PutHandler | |
1177 > | |
1178 inline OrthancPluginErrorCode ChunkedRestCompatibility(OrthancPluginRestOutput* output, | |
1179 const char* url, | |
1180 const OrthancPluginHttpRequest* request) | |
1181 { | |
1182 return ChunkedRestCompatibility(output, url, request, GetHandler, | |
1183 PostHandler, DeleteHandler, PutHandler); | |
1184 } | |
1185 #endif | |
1186 } | |
1187 | |
1188 | |
1189 | |
1190 // NB: We use a templated class instead of a templated function, because | |
1191 // default values are only available in functions since C++11 | |
1192 template< | |
1193 RestCallback GetHandler = Internals::NullRestCallback, | |
1194 ChunkedRestCallback PostHandler = Internals::NullChunkedRestCallback, | |
1195 RestCallback DeleteHandler = Internals::NullRestCallback, | |
1196 ChunkedRestCallback PutHandler = Internals::NullChunkedRestCallback | |
1197 > | |
1198 class ChunkedRestRegistration : public boost::noncopyable | |
1199 { | |
1200 public: | |
1201 static void Apply(const std::string& uri) | |
1202 { | |
1203 #if HAS_ORTHANC_PLUGIN_CHUNKED_HTTP_SERVER == 1 | |
1204 OrthancPluginRegisterChunkedRestCallback( | |
1205 GetGlobalContext(), uri.c_str(), | |
1206 GetHandler == Internals::NullRestCallback ? NULL : Internals::Protect<GetHandler>, | |
1207 PostHandler == Internals::NullChunkedRestCallback ? NULL : Internals::ChunkedProtect<PostHandler>, | |
1208 DeleteHandler == Internals::NullRestCallback ? NULL : Internals::Protect<DeleteHandler>, | |
1209 PutHandler == Internals::NullChunkedRestCallback ? NULL : Internals::ChunkedProtect<PutHandler>, | |
1210 Internals::ChunkedRequestReaderAddChunk, | |
1211 Internals::ChunkedRequestReaderExecute, | |
1212 Internals::ChunkedRequestReaderFinalize); | |
1213 #else | |
1214 OrthancPluginRegisterRestCallbackNoLock( | |
1215 GetGlobalContext(), uri.c_str(), | |
1216 Internals::ChunkedRestCompatibility<GetHandler, PostHandler, DeleteHandler, PutHandler>); | |
1217 #endif | |
1218 } | |
1219 }; | |
1220 | |
1221 | |
1222 | |
1223 #if HAS_ORTHANC_PLUGIN_STORAGE_COMMITMENT_SCP == 1 | |
1224 class IStorageCommitmentScpHandler : public boost::noncopyable | |
1225 { | |
1226 public: | |
1227 virtual ~IStorageCommitmentScpHandler() | |
1228 { | |
1229 } | |
1230 | |
1231 virtual OrthancPluginStorageCommitmentFailureReason Lookup(const std::string& sopClassUid, | |
1232 const std::string& sopInstanceUid) = 0; | |
1233 | |
1234 static OrthancPluginErrorCode Lookup(OrthancPluginStorageCommitmentFailureReason* target, | |
1235 void* rawHandler, | |
1236 const char* sopClassUid, | |
1237 const char* sopInstanceUid); | |
1238 | |
1239 static void Destructor(void* rawHandler); | |
1240 }; | |
1241 #endif | |
1242 | |
1243 | |
1244 class DicomInstance : public boost::noncopyable | |
1245 { | |
1246 private: | |
1247 bool toFree_; | |
1248 | |
1249 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 6, 1) | |
1250 const OrthancPluginDicomInstance* instance_; | |
1251 #else | |
1252 OrthancPluginDicomInstance* instance_; | |
1253 #endif | |
1254 | |
1255 public: | |
1256 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 6, 1) | |
167 | 1257 explicit DicomInstance(const OrthancPluginDicomInstance* instance); |
152 | 1258 #else |
167 | 1259 explicit DicomInstance(OrthancPluginDicomInstance* instance); |
152 | 1260 #endif |
1261 | |
1262 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 7, 0) | |
1263 DicomInstance(const void* buffer, | |
1264 size_t size); | |
1265 #endif | |
1266 | |
1267 ~DicomInstance(); | |
1268 | |
425 | 1269 const OrthancPluginDicomInstance* GetObject() const |
1270 { | |
1271 return instance_; | |
1272 } | |
1273 | |
152 | 1274 std::string GetRemoteAet() const; |
1275 | |
1276 const void* GetBuffer() const | |
1277 { | |
1278 return OrthancPluginGetInstanceData(GetGlobalContext(), instance_); | |
1279 } | |
1280 | |
1281 size_t GetSize() const | |
1282 { | |
1283 return static_cast<size_t>(OrthancPluginGetInstanceSize(GetGlobalContext(), instance_)); | |
1284 } | |
1285 | |
1286 void GetJson(Json::Value& target) const; | |
1287 | |
1288 void GetSimplifiedJson(Json::Value& target) const; | |
1289 | |
1290 OrthancPluginInstanceOrigin GetOrigin() const | |
1291 { | |
1292 return OrthancPluginGetInstanceOrigin(GetGlobalContext(), instance_); | |
1293 } | |
1294 | |
1295 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 6, 1) | |
1296 std::string GetTransferSyntaxUid() const; | |
1297 #endif | |
1298 | |
1299 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 6, 1) | |
1300 bool HasPixelData() const; | |
1301 #endif | |
1302 | |
1303 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 7, 0) | |
1304 unsigned int GetFramesCount() const | |
1305 { | |
1306 return OrthancPluginGetInstanceFramesCount(GetGlobalContext(), instance_); | |
1307 } | |
1308 #endif | |
1309 | |
1310 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 7, 0) | |
1311 void GetRawFrame(std::string& target, | |
1312 unsigned int frameIndex) const; | |
1313 #endif | |
1314 | |
1315 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 7, 0) | |
1316 OrthancImage* GetDecodedFrame(unsigned int frameIndex) const; | |
1317 #endif | |
1318 | |
1319 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 7, 0) | |
1320 void Serialize(std::string& target) const; | |
1321 #endif | |
1322 | |
1323 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 7, 0) | |
1324 static DicomInstance* Transcode(const void* buffer, | |
1325 size_t size, | |
1326 const std::string& transferSyntax); | |
1327 #endif | |
425 | 1328 |
1329 #if ORTHANC_PLUGINS_VERSION_IS_ABOVE(1, 12, 1) | |
1330 static DicomInstance* Load(const std::string& instanceId, | |
1331 OrthancPluginLoadDicomInstanceMode mode); | |
1332 #endif | |
152 | 1333 }; |
397 | 1334 |
1335 // helper method to convert Http headers from the plugin SDK to a std::map | |
1336 void GetHttpHeaders(std::map<std::string, std::string>& result, const OrthancPluginHttpRequest* request); | |
1337 | |
1338 #if HAS_ORTHANC_PLUGIN_WEBDAV == 1 | |
1339 class IWebDavCollection : public boost::noncopyable | |
1340 { | |
1341 public: | |
1342 class FileInfo | |
1343 { | |
1344 private: | |
1345 std::string name_; | |
1346 uint64_t contentSize_; | |
1347 std::string mime_; | |
1348 std::string dateTime_; | |
1349 | |
1350 public: | |
1351 FileInfo(const std::string& name, | |
1352 uint64_t contentSize, | |
1353 const std::string& dateTime) : | |
1354 name_(name), | |
1355 contentSize_(contentSize), | |
1356 dateTime_(dateTime) | |
1357 { | |
1358 } | |
1359 | |
1360 const std::string& GetName() const | |
1361 { | |
1362 return name_; | |
1363 } | |
1364 | |
1365 uint64_t GetContentSize() const | |
1366 { | |
1367 return contentSize_; | |
1368 } | |
1369 | |
1370 void SetMimeType(const std::string& mime) | |
1371 { | |
1372 mime_ = mime; | |
1373 } | |
1374 | |
1375 const std::string& GetMimeType() const | |
1376 { | |
1377 return mime_; | |
1378 } | |
1379 | |
1380 const std::string& GetDateTime() const | |
1381 { | |
1382 return dateTime_; | |
1383 } | |
1384 }; | |
1385 | |
1386 class FolderInfo | |
1387 { | |
1388 private: | |
1389 std::string name_; | |
1390 std::string dateTime_; | |
1391 | |
1392 public: | |
1393 FolderInfo(const std::string& name, | |
1394 const std::string& dateTime) : | |
1395 name_(name), | |
1396 dateTime_(dateTime) | |
1397 { | |
1398 } | |
1399 | |
1400 const std::string& GetName() const | |
1401 { | |
1402 return name_; | |
1403 } | |
1404 | |
1405 const std::string& GetDateTime() const | |
1406 { | |
1407 return dateTime_; | |
1408 } | |
1409 }; | |
1410 | |
1411 virtual ~IWebDavCollection() | |
1412 { | |
1413 } | |
1414 | |
1415 virtual bool IsExistingFolder(const std::vector<std::string>& path) = 0; | |
1416 | |
1417 virtual bool ListFolder(std::list<FileInfo>& files, | |
1418 std::list<FolderInfo>& subfolders, | |
1419 const std::vector<std::string>& path) = 0; | |
1420 | |
1421 virtual bool GetFile(std::string& content /* out */, | |
1422 std::string& mime /* out */, | |
1423 std::string& dateTime /* out */, | |
1424 const std::vector<std::string>& path) = 0; | |
1425 | |
1426 virtual bool StoreFile(const std::vector<std::string>& path, | |
1427 const void* data, | |
1428 size_t size) = 0; | |
1429 | |
1430 virtual bool CreateFolder(const std::vector<std::string>& path) = 0; | |
1431 | |
1432 virtual bool DeleteItem(const std::vector<std::string>& path) = 0; | |
1433 | |
1434 static void Register(const std::string& uri, | |
1435 IWebDavCollection& collection); | |
1436 }; | |
1437 #endif | |
491 | 1438 |
1439 void SetRootUri(const std::string& pluginIdentifier, | |
1440 const std::string& uri); | |
1441 | |
1442 void SetDescription(const std::string& pluginIdentifier, | |
1443 const std::string& description); | |
1444 | |
1445 void ExtendOrthancExplorer(const std::string& pluginIdentifier, | |
1446 const std::string& javascript); | |
152 | 1447 } |