annotate Sphinx/source/plugins/python.rst @ 1041:fe9c92d81082

note about python
author Sebastien Jodogne <s.jodogne@gmail.com>
date Fri, 08 Mar 2024 16:33:42 +0100
parents 0bfcdaba2be3
children 63edb430f259
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
343
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
1 .. _python-plugin:
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
2
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
3
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
4 Python plugin for Orthanc
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
5 =========================
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
6
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
7 .. contents::
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
8
371
5cb37e6b014b explicit links to the source code of python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
9
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
10 Overview
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
11 --------
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
12
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
13 This plugin can be used to write :ref:`Orthanc plugins
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
14 <creating-plugins>` using the `Python programming language
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
15 <https://en.wikipedia.org/wiki/Python_(programming_language)>`__
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
16 instead of the more complex C/C++ programming languages.
343
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
17
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
18 Python plugins have access to more features and a more consistent SDK
709
9d5e17100a8d update statistics from 2.0 to 3.2
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 708
diff changeset
19 than :ref:`Lua scripts <lua>`. The largest part of the Python API is
9d5e17100a8d update statistics from 2.0 to 3.2
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 708
diff changeset
20 automatically generated from the `Orthanc plugin SDK in C
1021
a3436ae3709c Orthanc 1.12.3
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 1018
diff changeset
21 <https://orthanc.uclouvain.be/hg/orthanc/file/Orthanc-1.12.3/OrthancServer/Plugins/Include/orthanc/OrthancCPlugin.h>`__
345
f81b533a0fd0 python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 343
diff changeset
22 using the `Clang <https://en.wikipedia.org/wiki/Clang>`__ compiler
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
23 front-end.
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
24
709
9d5e17100a8d update statistics from 2.0 to 3.2
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 708
diff changeset
25 As of release 3.2 of the plugin, the coverage of the C SDK is about
9d5e17100a8d update statistics from 2.0 to 3.2
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 708
diff changeset
26 87% (138 functions are automatically wrapped in Python out of a total
9d5e17100a8d update statistics from 2.0 to 3.2
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 708
diff changeset
27 of 158 functions from the Orthanc SDK 1.8.1).
343
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
28
371
5cb37e6b014b explicit links to the source code of python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
29
5cb37e6b014b explicit links to the source code of python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
30 Source code
5cb37e6b014b explicit links to the source code of python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
31 -----------
5cb37e6b014b explicit links to the source code of python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
32
5cb37e6b014b explicit links to the source code of python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
33 * Link to the `official releases of this plugin
993
05b106383b2a migration to UCLouvain servers
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 991
diff changeset
34 <https://orthanc.uclouvain.be/downloads/sources/orthanc-python/index.html>`__.
371
5cb37e6b014b explicit links to the source code of python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
35
5cb37e6b014b explicit links to the source code of python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
36 * Link to the `code repository
991
1316bc62b5d5 migration to UCLouvain servers
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 984
diff changeset
37 <https://orthanc.uclouvain.be/hg/orthanc-python/>`__.
371
5cb37e6b014b explicit links to the source code of python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
38
5cb37e6b014b explicit links to the source code of python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
39
353
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
40 Licensing
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
41 ---------
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
42
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
43 Pay attention to the fact that this plugin is licensed under the terms
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
44 of the `AGPL license
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
45 <https://en.wikipedia.org/wiki/GNU_Affero_General_Public_License>`__.
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
46
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
47 This has an important consequence: If you distribute Orthanc to
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
48 clients together with one Python script, or if you put an Orthanc
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
49 server equipped with one Python script on a Web portal, you **must**
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
50 disclose the source code of your Python script to the Orthanc
354
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 353
diff changeset
51 community under the terms of the AGPL license.
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 353
diff changeset
52
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 353
diff changeset
53 We suggest you to put the source code of your Python scripts on the
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 353
diff changeset
54 dedicated `"OrthancContributed" repository on GitHub
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 353
diff changeset
55 <https://github.com/jodogne/OrthancContributed/tree/master/Plugins>`__,
984
46e2941b57dd replace link to google users group by link to discourse
Alain Mazy <am@osimis.io>
parents: 978
diff changeset
56 and/or to send it to the `Orthanc Users discussion forum
46e2941b57dd replace link to google users group by link to discourse
Alain Mazy <am@osimis.io>
parents: 978
diff changeset
57 <https://discourse.orthanc-server.org>`__.
353
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
58
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
59 Check out the :ref:`FAQ about licensing <licensing>` for more context.
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
60
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
61
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
62 Usage
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
63 -----
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
64
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
65 Docker
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
66 ......
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
67
697
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
68 .. highlight:: python
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
69
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
70 The most direct way of starting Orthanc together with the Python
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
71 plugin is through :ref:`Docker <docker>`. Let's create the file
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
72 ``/tmp/hello.py`` that contains the following basic Python script::
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
73
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
74 print('Hello world!')
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
75
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
76 .. highlight:: json
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
77
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
78 Let's also create the file ``/tmp/orthanc.json`` that contains the
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
79 following minimal :ref:`configuration for Orthanc <configuration>`::
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
80
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
81 {
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
82 "StorageDirectory" : "/var/lib/orthanc/db",
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
83 "RemoteAccessAllowed" : true,
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
84 "Plugins" : [
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
85 "/usr/local/share/orthanc/plugins"
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
86 ],
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
87 "PythonScript" : "/etc/orthanc/hello.py"
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
88 }
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
89
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
90 .. highlight:: bash
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
91
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
92 Given these two files, Orthanc can be started as follows::
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
93
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
94 $ docker run -p 4242:4242 -p 8042:8042 --rm \
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
95 -v /tmp/orthanc.json:/etc/orthanc/orthanc.json:ro \
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
96 -v /tmp/hello.py:/etc/orthanc/hello.py:ro \
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
97 jodogne/orthanc-python
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
98
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
99 .. highlight:: text
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
100
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
101 You'll see the following excerpt in the log, which indicates that the Python plugin is properly loaded::
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
102
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
103 W0331 15:48:12.990661 PluginsManager.cpp:269] Registering plugin 'python' (version mainline)
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
104 W0331 15:48:12.990691 PluginsManager.cpp:168] Python plugin is initializing
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
105 W0331 15:48:12.990743 PluginsManager.cpp:168] Using Python script "hello.py" from directory: /etc/orthanc
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
106 W0331 15:48:12.990819 PluginsManager.cpp:168] Program name: /usr/local/sbin/Orthanc
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
107 Hello world!
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
108
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
109
962
5df222ddd7d1 fix links to setup-samples
Alain Mazy <am@osimis.io>
parents: 947
diff changeset
110 `Here <https://github.com/orthanc-server/orthanc-setup-samples/tree/master/docker/python/>`__ is a full example
1023
5d4701d8fe28 replaced osimis/orthanc by orthancteam/orthanc
Alain Mazy <am@osimis.io>
parents: 1021
diff changeset
111 of a more complex setup using the :ref:`orthancteam/orthanc <docker-orthancteam>` images.
405
ba486cac480a link to python sample
Alain Mazy <alain@mazy.be>
parents: 379
diff changeset
112
800
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
113
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
114 Microsoft Windows
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
115 .................
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
116
927
dfe96daba4f8 python in win installer
Alain Mazy <am@osimis.io>
parents: 914
diff changeset
117 Pre-compiled binaries for Microsoft Windows are now part of the
993
05b106383b2a migration to UCLouvain servers
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 991
diff changeset
118 `Windows installers <https://www.orthanc-server.com/download-windows.php>`__
927
dfe96daba4f8 python in win installer
Alain Mazy <am@osimis.io>
parents: 914
diff changeset
119 but not installed by default. They are also `available here
993
05b106383b2a migration to UCLouvain servers
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 991
diff changeset
120 <https://orthanc.uclouvain.be/downloads/windows-32/orthanc-python/index.html>`__.
800
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
121
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
122 Beware that one version of the Python plugin can only be run against
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
123 one version of the Python interpreter. This version is clearly
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
124 indicated in the filename of the precompiled binaries.
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
125
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
126 Pay also attention to pick the right 32/64 bits version. If you are
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
127 running Orthanc 64bits, install Python in 64bits and select the 64bits
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
128 Python plugin too.
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
129
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
130 When you install Python on your Windows machine, make sure to install
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
131 Python for ``All Users`` and select the ``Add Python to Path`` option.
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
132
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
133 Compiling from source
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
134 .....................
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
135
800
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
136 For GNU/Linux
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
137 ^^^^^^^^^^^^^
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
138
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
139 .. highlight:: bash
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
140
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
141 The procedure to compile this plugin from source is similar to that
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
142 for the :ref:`core of Orthanc <compiling>`. The following commands
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
143 should work for most UNIX-like distribution (including GNU/Linux)::
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
144
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
145 $ mkdir Build
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
146 $ cd Build
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
147 $ cmake .. -DPYTHON_VERSION=3.7 -DSTATIC_BUILD=ON -DCMAKE_BUILD_TYPE=Release
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
148 $ make
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
149
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
150 Before running CMake, make sure that the Python interpreter and its
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
151 associated development library are installed. On Ubuntu 18.04 LTS, you
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
152 would for instance install packages ``libpython3.7-dev`` and
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
153 ``python3.7``.
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
154
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
155 The compilation will produce the shared library ``OrthancPython``,
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
156 that can be loaded by properly setting the ``Plugins``
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
157 :ref:`configuration option <configuration>` of Orthanc.
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
158
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
159 **Warning:** The shared library is only compatible with the Python
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
160 interpreter whose version corresponds to the value of the
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
161 ``PYTHON_VERSION`` argument that was given to CMake.
501
98592b9e7ad5 force version of python on os x
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 490
diff changeset
162
98592b9e7ad5 force version of python on os x
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 490
diff changeset
163 **Note for OS X:** As indicated by `Stephen Douglas Scotti
98592b9e7ad5 force version of python on os x
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 490
diff changeset
164 <https://groups.google.com/g/orthanc-users/c/RnmZKFv8FaY/m/HhvOD2A2CAAJ>`__,
98592b9e7ad5 force version of python on os x
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 490
diff changeset
165 here is a sample invocation of CMake to force the version of Python to
98592b9e7ad5 force version of python on os x
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 490
diff changeset
166 be used on OS X::
98592b9e7ad5 force version of python on os x
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 490
diff changeset
167
98592b9e7ad5 force version of python on os x
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 490
diff changeset
168 $ cmake .. -DPYTHON_VERSION=3.8 -DSTATIC_BUILD=ON -DCMAKE_BUILD_TYPE=Release \
98592b9e7ad5 force version of python on os x
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 490
diff changeset
169 -DPYTHON_LIBRARY=/usr/local/Cellar/python@3.8/3.8.5/Frameworks/Python.framework/Versions/3.8/lib/libpython3.8.dylib \
98592b9e7ad5 force version of python on os x
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 490
diff changeset
170 -DPYTHON_INCLUDE_DIR=/usr/local/Cellar/python@3.8/3.8.5/Frameworks/Python.framework/Versions/3.8/include/python3.8/
98592b9e7ad5 force version of python on os x
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 490
diff changeset
171
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
172
800
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
173 For Microsoft Windows
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
174 ^^^^^^^^^^^^^^^^^^^^^
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
175
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
176 .. highlight:: text
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
177
442
8b2c648c0f46 clarifications about windows precompiled binaries
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 405
diff changeset
178 You are of course free to compile the plugin from sources. You'll have
8b2c648c0f46 clarifications about windows precompiled binaries
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 405
diff changeset
179 to explicitly specify the path to your Python installation while
8b2c648c0f46 clarifications about windows precompiled binaries
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 405
diff changeset
180 invoking CMake. For instance::
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
181
800
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
182 C:\orthanc-python\Build> cmake .. -DPYTHON_VERSION=3.8 -DPYTHON_WINDOWS_ROOT=C:/Python38 \
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
183 -DSTATIC_BUILD=ON -DCMAKE_BUILD_TYPE=Release -G "Visual Studio 15 2017"
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
184
442
8b2c648c0f46 clarifications about windows precompiled binaries
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 405
diff changeset
185 **Note about debug builds**: Usually, building Python modules such as the Python
377
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
186 plugin for Orthanc in debug mode (where ``_DEBUG`` is defined) leads to a module
442
8b2c648c0f46 clarifications about windows precompiled binaries
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 405
diff changeset
187 (``.exe`` or ``.dll``) that requires a debug build of Python, and debug versions of all
377
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
188 the Python libraries. This is quite cumbersome, for it requires building Python
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
189 on your own or downloading additional debug files.
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
190
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
191 Since using a debug build of Python is only necessary in very specific cases
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
192 (such as the debugging of code at the boundary between Python and an extension),
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
193 we have changed the default behavior to use the release Python library by default.
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
194
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
195 This means that you are able to build this plugin in debug mode with the
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
196 standard Python distribution.
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
197
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
198 In case you need to use the Python debug libraries, you can instruct the build
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
199 system to do so by setting the ``PYTHON_WINDOWS_USE_RELEASE_LIBS`` CMake option,
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
200 that is ``ON`` by default, to ``OFF``. The previous build example would then be,
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
201 should you require a full debug build::
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
202
800
83beec704c98 python windows usage
Alain Mazy <am@osimis.io>
parents: 799
diff changeset
203 C:\orthanc-python\Build> cmake .. -DPYTHON_VERSION=3.8 -DPYTHON_WINDOWS_ROOT=C:/Python38 \
377
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
204 -DSTATIC_BUILD=ON -DPYTHON_WINDOWS_USE_RELEASE_LIBS=OFF \
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
205 -DCMAKE_BUILD_TYPE=Debug -G "Visual Studio 15 2017"
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
206
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
207 Please note that this CMake option only impacts **debug** builds under Windows,
ffe62e6c086f Added a note about the debug libraries when building under Windows with Visual Studio.
Benjamin Golinvaux <bgo@osimis.io>
parents: 375
diff changeset
208 when using (any version of) the Microsoft Visual Studio compiler.
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
209
442
8b2c648c0f46 clarifications about windows precompiled binaries
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 405
diff changeset
210 The precompiled binaries all use release (i.e. non-debug) versions of Python.
8b2c648c0f46 clarifications about windows precompiled binaries
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 405
diff changeset
211
8b2c648c0f46 clarifications about windows precompiled binaries
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 405
diff changeset
212
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
213 Configuration options
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
214 ---------------------
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
215
978
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
216 The two main configuration options that are available for this plugin
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
217 are the following:
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
218
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
219 * ``PythonScript`` indicates where the Python script is located. If
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
220 this configuration option is not provided, the Python plugin is not
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
221 started.
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
222
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
223 * ``PythonVerbose`` is a Boolean value to make the Python interpreter
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
224 verbose.
978
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
225
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
226 Consequently, a minimal :ref:`configuration file <configuration>` for
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
227 Orthanc could be::
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
228
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
229 {
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
230 "Plugins" : [ "." ],
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
231 "PythonScript" : "my-plugin.py",
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
232 "PythonVerbose" : false
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
233 }
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
234
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
235 Starting with release 4.1 of the Python plugin, it is also possible to
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
236 specify the configuration of the plugin in a dedicated ``Python``
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
237 section as follows::
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
238
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
239 {
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
240 "Plugins" : [ "." ],
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
241 "Python" : {
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
242 "Path" : "my-plugin.py", // Alias for the global "PythonScript" option
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
243 "Verbose" : false, // Alias for the global "PythonVerbose" option
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
244 "DisplayMemoryUsage" : false
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
245 }
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
246 }
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
247
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
248 The option ``Python.DisplayMemoryUsage`` was introduced in release 4.1
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
249 of the plugin. If set to ``true``, Orthanc will display the memory
e7a3b3d76f1c documentation of new options in Python plugin 4.1
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 975
diff changeset
250 usage of the Python interpreter every second.
364
234de55ed125 usage of the python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 354
diff changeset
251
343
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
252
1041
fe9c92d81082 note about python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 1025
diff changeset
253 .. warning::
fe9c92d81082 note about python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 1025
diff changeset
254 Never call your Python plugin ``orthanc.py``! Otherwise, your plugin will
fe9c92d81082 note about python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 1025
diff changeset
255 conflict with the ``orthanc`` module that is installed at runtime.
fe9c92d81082 note about python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 1025
diff changeset
256
fe9c92d81082 note about python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 1025
diff changeset
257
343
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
258 Samples
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
259 -------
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
260
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
261 Extending the REST API
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
262 ......................
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
263
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
264 Here is a basic Python script that registers two new routes in the
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
265 REST API:
343
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
266
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
267 .. literalinclude:: python/extending-rest-api.py
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
268 :language: python
343
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
269
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
270 .. highlight:: json
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
271
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
272 Here is the associated minimal configuration file for Orthanc
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
273 (provided the Python script is saved as ``rest.py``)::
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
274
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
275 {
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
276 "Plugins" : [ "." ],
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
277 "PythonScript" : "rest.py",
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
278 "PythonVerbose" : false
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
279 }
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
280
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
281 .. highlight:: bash
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
282
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
283 The route can then be accessed as::
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
284
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
285 $ curl http://localhost:8042/toto
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
286 ok
fff45618262d creating the documentation of the Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents:
diff changeset
287
469
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
288
1013
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
289 Overriding the core REST API
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
290 ............................
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
291
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
292 You may also use a python plugin to replace an existing REST API route:
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
293
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
294 .. literalinclude:: python/extending-rest-api-2.py
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
295 :language: python
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
296
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
297
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
298
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
299 When calling the REST API from a python plugin, you may use e.g.
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
300 ``RestApiPost`` to call the native Orthanc REST API and must
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
301 call ``RestApiPostAfterPlugin`` to call the REST API from plugins.
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
302
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
303
1021
a3436ae3709c Orthanc 1.12.3
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 1018
diff changeset
304 Note however, that, as of Orthanc 1.12.3, the Orthanc plugin SDK
1013
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
305 does not support multiple plugins implementing the same route.
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
306 Orthanc will actually accept e.g a Python plugin that overrides
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
307 a DICOMWeb route but it is impossible to tell which route
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
308 will be called in the end since this depends on the registration
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
309 order of the plugins that is not deterministic.
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
310
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
311
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
312
ab270400aae1 python: overriding core API
Alain Mazy <am@osimis.io>
parents: 1000
diff changeset
313
469
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
314 .. _python-changes:
345
f81b533a0fd0 python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 343
diff changeset
315
f81b533a0fd0 python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 343
diff changeset
316 Listening to changes
f81b533a0fd0 python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 343
diff changeset
317 ....................
f81b533a0fd0 python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 343
diff changeset
318
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
319 This sample uploads a DICOM file as soon as Orthanc is started:
345
f81b533a0fd0 python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 343
diff changeset
320
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
321 .. literalinclude:: python/listening-changes.py
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
322 :language: python
345
f81b533a0fd0 python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 343
diff changeset
323
590
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
324
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
325 .. warning::
600
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
326 In releases <= 3.0 of the Python plugin, deadlocks might emerge if
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
327 you call other core primitives of Orthanc (such as the REST API) in
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
328 your callback function. This issue has been `fixed in release 3.1
991
1316bc62b5d5 migration to UCLouvain servers
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 984
diff changeset
329 <https://orthanc.uclouvain.be/hg/orthanc-python/rev/46fe70776d61>`__.
590
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
330
600
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
331 As a **temporary workaround** against such deadlocks in releases <=
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
332 3.0, if you have to call other primitives of Orthanc, you should make
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
333 these calls in a separate thread, passing the pending events to be
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
334 processed through a message queue. Here is the template of a possible
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
335 solution to postpone such deadlocks as much as possible by relying on
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
336 the multithreading primitives of Python:
591
2397b0e12bc8 solution to avoid deadlock in Python OnChange()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 590
diff changeset
337
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
338 .. literalinclude:: python/changes-deadlock-3.0.py
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
339 :language: python
600
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
340
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
341 Beware that **this workaround is imperfect** and deadlocks have been
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
342 observed even if using it! Make sure to upgrade your plugin to solve
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
343 this issue for good. Note that this temporary workaround is not needed
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
344 in releases >= 3.1 of the plugin.
4038ae299b18 note about deadlocks in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 591
diff changeset
345
591
2397b0e12bc8 solution to avoid deadlock in Python OnChange()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 590
diff changeset
346
590
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
347
345
f81b533a0fd0 python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 343
diff changeset
348 Accessing the content of a new instance
346
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
349 .......................................
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
350
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
351 .. literalinclude:: python/accessing-new-instance.py
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
352 :language: python
346
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
353
590
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
354 .. warning::
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
355 Your callback function will be called synchronously with
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
356 the core of Orthanc. This implies that deadlocks might emerge if
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
357 you call other core primitives of Orthanc in your callback (such
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
358 deadlocks are particular visible in the presence of other plugins
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
359 or Lua scripts). It is thus strongly advised to avoid any call to
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
360 the REST API of Orthanc in the callback. If you have to call other
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
361 primitives of Orthanc, you should make these calls in a separate
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
362 thread, passing the pending events to be processed through a
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
363 message queue.
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
364
404aca6160f0 warning about deadlock in python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 568
diff changeset
365
346
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
366 Calling pydicom
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
367 ...............
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
368
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
369 Here is a sample Python plugin that registers a REST callback to dump
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
370 the content of the dataset of one given DICOM instance stored in
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
371 Orthanc, using `pydicom <https://pydicom.github.io/>`__:
346
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
372
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
373 .. literalinclude:: python/pydicom.py
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
374 :language: python
346
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
375
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
376 .. highlight:: bash
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
377
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
378 This callback can be called as follows::
346
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
379
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
380 $ curl http://localhost:8042/pydicom/19816330-cb02e1cf-df3a8fe8-bf510623-ccefe9f5
bdf8757449e3 more python samples
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 345
diff changeset
381
347
04fae9d4b65f auto-routing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 346
diff changeset
382
04fae9d4b65f auto-routing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 346
diff changeset
383 Auto-routing studies
04fae9d4b65f auto-routing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 346
diff changeset
384 ....................
04fae9d4b65f auto-routing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 346
diff changeset
385
04fae9d4b65f auto-routing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 346
diff changeset
386 Here is a sample Python plugin that routes any :ref:`stable study
642
a76d83a00c68 definition of stable resources
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 638
diff changeset
387 <stable-resources>` to a modality named ``samples`` (as declared in the
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
388 ``DicomModalities`` configuration option):
347
04fae9d4b65f auto-routing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 346
diff changeset
389
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
390 .. literalinclude:: python/autorouting-1.py
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
391 :language: python
348
d8359cecdc89 pillow sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 347
diff changeset
392
539
fd5c1410db5b doc for RestApiPostAfterPlugins
Alain Mazy <alain@mazy.be>
parents: 528
diff changeset
393 Note that, if you want to use an orthanc plugin to transfer the study,
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
394 you should use the ``RestApiPostAfterPlugins()`` method:
539
fd5c1410db5b doc for RestApiPostAfterPlugins
Alain Mazy <alain@mazy.be>
parents: 528
diff changeset
395
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
396 .. literalinclude:: python/autorouting-2.py
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
397 :language: python
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
398
539
fd5c1410db5b doc for RestApiPostAfterPlugins
Alain Mazy <alain@mazy.be>
parents: 528
diff changeset
399
352
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 351
diff changeset
400 Rendering a thumbnail using PIL/Pillow
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 351
diff changeset
401 ......................................
348
d8359cecdc89 pillow sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 347
diff changeset
402
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
403 .. literalinclude:: python/pil.py
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
404 :language: python
351
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
405
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
406
369
181b02cea7ab inspecting Python API
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
407 .. _python-introspection:
181b02cea7ab inspecting Python API
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
408
181b02cea7ab inspecting Python API
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
409 Inspecting the available API
181b02cea7ab inspecting Python API
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
410 ............................
181b02cea7ab inspecting Python API
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
411
181b02cea7ab inspecting Python API
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
412 Thanks to Python's introspection primitives, it is possible to inspect
181b02cea7ab inspecting Python API
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
413 the API of the ``orthanc`` module in order to dump all the available
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
414 features:
369
181b02cea7ab inspecting Python API
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
415
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
416 .. literalinclude:: python/inspect-api.py
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
417 :language: python
369
181b02cea7ab inspecting Python API
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
418
703
a589668768d7 moving python samples in separate files (2)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 702
diff changeset
419
373
847996394688 Scheduling a task for periodic execution
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 369
diff changeset
420 .. _python-scheduler:
847996394688 Scheduling a task for periodic execution
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 369
diff changeset
421
847996394688 Scheduling a task for periodic execution
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 369
diff changeset
422 Scheduling a task for periodic execution
847996394688 Scheduling a task for periodic execution
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 369
diff changeset
423 ........................................
847996394688 Scheduling a task for periodic execution
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 369
diff changeset
424
847996394688 Scheduling a task for periodic execution
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 369
diff changeset
425 The following Python script will periodically (every second) run the
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
426 function ``Hello()`` thanks to the ``threading`` module:
373
847996394688 Scheduling a task for periodic execution
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 369
diff changeset
427
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
428 .. literalinclude:: python/periodic-execution.py
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
429 :language: python
373
847996394688 Scheduling a task for periodic execution
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 369
diff changeset
430
378
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
431
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
432 .. _python-metadata:
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
433
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
434 Filtering and returning metadata
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
435 ................................
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
436
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
437 Besides the main DICOM tags, Orthanc associates some metadata to each
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
438 resource it stores (this includes the date of last update, the
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
439 transfer syntax, the remote AET...). People are often interested in
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
440 getting such metadata while calling the ``/tools/find`` route in the
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
441 :ref:`REST API <rest-find>`, or even in filtering this metadata the
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
442 same way they look for DICOM tags.
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
443
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
444 This feature is not built in the core of Orthanc, as metadata is not
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
445 indexed in the Orthanc database, contrarily to the main DICOM
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
446 tags. Filtering metadata requires a linear search over all the
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
447 matching resources, which induces a cost in the performance.
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
448
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
449 Nevertheless, here is a full sample Python script that overwrites the
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
450 ``/tools/find`` route in order to give access to metadata:
378
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
451
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
452 .. literalinclude:: python/filtering-metadata.py
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
453 :language: python
378
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
454
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
455
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
456 **Warning:** In the sample above, the filtering of the metadata is
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
457 done using Python's `library for regular expressions
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
458 <https://docs.python.org/3/library/re.html>`__. It is evidently
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
459 possible to adapt this script in order to use the DICOM conventions
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
460 about `attribute matching
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
461 <http://dicom.nema.org/medical/dicom/2019e/output/chtml/part04/sect_C.2.2.2.html>`__.
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
462
469
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
463 .. highlight:: bash
378
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
464
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
465 Here is a sample call to retrieve all the studies that were last
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
466 updated in 2019 thanks to this Python script::
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
467
16dc3561b41e Filtering and returning metadata using Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 375
diff changeset
468 $ curl http://localhost:8042/tools/find -d '{"Level":"Study","Query":{},"Expand":true,"Metadata":{"LastUpdate":"^2019.*$"}}'
369
181b02cea7ab inspecting Python API
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
469
181b02cea7ab inspecting Python API
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 364
diff changeset
470
469
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
471 .. _python-paging:
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
472
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
473 Implementing basic paging
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
474 .........................
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
475
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
476 As explained in the FAQ, the :ref:`Orthanc Explorer interface is
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
477 low-level <improving-interface>`, and is not adapted for
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
478 end-users. One common need is to implement paging of studies, which
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
479 calls for server-side sorting of studies. This can be done using the
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
480 following sample Python plugin that registers a new route
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
481 ``/sort-studies`` in the REST API of Orthanc:
469
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
482
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
483 .. literalinclude:: python/paging.py
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
484 :language: python
469
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
485
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
486 .. highlight:: bash
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
487
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
488 Here is a sample call to this new REST route, that could be issued by
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
489 any JavaScript framework (the ``json_pp`` command-line pretty-prints a
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
490 JSON file)::
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
491
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
492 $ curl http://localhost:8042/sort-studies | json_pp
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
493
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
494 This route also implement paging (i.e. it can limit and offset the
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
495 returned studies)::
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
496
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
497 $ curl 'http://localhost:8042/sort-studies?offset=2&limit=2' | json_pp
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
498
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
499 Obviously, this basic sample can be improved in many ways. To improve
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
500 performance, one could for instance cache the result of
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
501 ``/studies?expand`` in memory by :ref:`listening to changes
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
502 <python-changes>` in the list of studies
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
503 (cf. ``orthanc.ChangeType.NEW_STUDY`` and
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
504 ``orthanc.ChangeType.DELETED``).
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
505
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
506
551
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
507 .. _python_excel:
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
508
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
509 Creating a Microsoft Excel report
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
510 .................................
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
511
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
512 As Orthanc plugins have access to any installed Python module, it is
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
513 very easy to implement a server-side plugin that generates a report in
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
514 the Microsoft Excel ``.xls`` format. Here is a working example:
551
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
515
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
516 .. literalinclude:: python/excel.py
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
517 :language: python
551
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
518
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
519 If opening the ``http://localhost:8042/report.xls`` URI, this Python
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
520 will generate a workbook with one sheet that contains the list of
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
521 studies, with the patient ID, the patient name and the study
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
522 description.
d0332c5a2cb8 Python plugin: excel generation example
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 539
diff changeset
523
469
46949efa5818 Implementing basic paging using a Python script
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
524
556
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
525 .. _python_authorization:
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
526
697
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
527 Forbid or allow access to REST resources (authorization, new in 3.0)
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
528 ....................................................................
556
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
529
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
530 The following Python script installs a callback that is triggered
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
531 whenever the HTTP server of Orthanc is accessed:
556
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
532
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
533 .. literalinclude:: python/authorization-1.py
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
534 :language: python
556
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
535
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
536
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
537 If access is not granted, the ``Filter`` callback must return
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
538 ``False``. As a consequence, the HTTP status code would be set to
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
539 ``403 Forbidden``. If access is granted, the ``Filter`` must return
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
540 ``true``. The ``request`` argument contains more information about the
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
541 request (such as the HTTP headers, the IP address of the caller and
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
542 the GET arguments).
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
543
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
544 Note that this is similar to the ``IncomingHttpRequestFilter()``
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
545 callback that is available in :ref:`Lua scripts <lua-filter-rest>`.
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
546
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
547 Thanks to Python, it is extremely easy to call remote Web services for
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
548 authorization. Here is an example using the ``requests`` library:
556
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
549
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
550 .. literalinclude:: python/authorization-2.py
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
551 :language: python
556
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
552
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
553 This filter could be used together with the following Web service
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
554 implemented using `Node.js
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
555 <https://en.wikipedia.org/wiki/Node.js>`__:
556
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
556
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
557 .. literalinclude:: python/authorization-node-service.js
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
558 :language: javascript
556
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
559
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
560
708
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
561 .. _python_lookup_dictionary:
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
562
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
563 Lookup DICOM dictionary (new in 3.2)
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
564 ....................................
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
565
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
566 Python plugins can access the dictionary of the DICOM tags that are
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
567 handled by Orthanc:
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
568
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
569 .. literalinclude:: python/lookup-dictionary.py
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
570 :language: python
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
571
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
572 .. highlight:: text
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
573
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
574 Note how Python introspection is used in order to map the values in
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
575 enumeration ``orthanc.ValueRepresentation`` to a string description of
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
576 the value representation. If started, the plugin above would output
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
577 the following information in the Orthanc logs::
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
578
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
579 W0611 14:04:08.563957 PluginsManager.cpp:168] Entry in the dictionary: {
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
580 "Element": 32,
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
581 "Group": 16,
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
582 "MaxMultiplicity": 1,
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
583 "MinMultiplicity": 1,
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
584 "ValueRepresentation": 11
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
585 }
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
586 W0611 14:04:08.563975 PluginsManager.cpp:168] Name of the value representation: LO
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
587
cd70d23f34bc Lookup DICOM dictionary in Python scripts
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 707
diff changeset
588
695
f4fc12ed00ee creating dicom instances in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 678
diff changeset
589 .. _python_create_dicom:
556
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
590
696
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 695
diff changeset
591 Creating DICOM instances (new in 3.2)
695
f4fc12ed00ee creating dicom instances in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 678
diff changeset
592 .....................................
f4fc12ed00ee creating dicom instances in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 678
diff changeset
593
f4fc12ed00ee creating dicom instances in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 678
diff changeset
594 The following sample Python script will write on the disk a new DICOM
f4fc12ed00ee creating dicom instances in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 678
diff changeset
595 instance including the traditional Lena sample image, and will decode
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
596 the single frame of this DICOM instance:
695
f4fc12ed00ee creating dicom instances in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 678
diff changeset
597
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
598 .. literalinclude:: python/create-dicom.py
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
599 :language: python
695
f4fc12ed00ee creating dicom instances in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 678
diff changeset
600
f4fc12ed00ee creating dicom instances in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 678
diff changeset
601
706
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
602 .. _python_pil_conversions:
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
603
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
604 Conversions between Orthanc and Python images (new in 3.2)
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
605 ..........................................................
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
606
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
607 The Python method ``orthanc.Image.GetImageBuffer()`` returns a copy of
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
608 the memory buffer of an image that is handled Orthanc. Conversely, the
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
609 Python function ``orthanc.CreateImageFromBuffer()`` can be used to
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
610 create an Orthanc image from a Python buffer. Taken together, these
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
611 two functions can be used to do bidirectional conversions between
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
612 Orthanc images and Python images.
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
613
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
614 Here is a full working example using PIL/Pillow that shows how to
707
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 706
diff changeset
615 decode one frame of a DICOM instance using Orthanc, then to modify
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 706
diff changeset
616 this image using PIL, and finally to upload the modified image as a
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 706
diff changeset
617 new DICOM instance:
706
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
618
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
619 .. literalinclude:: python/pil-conversions.py
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
620 :language: python
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
621
c62539d00251 Conversions between Orthanc and Python images
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 704
diff changeset
622
697
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
623 .. _python_dicom_scp:
695
f4fc12ed00ee creating dicom instances in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 678
diff changeset
624
697
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
625 Handling DICOM SCP requests (new in 3.2)
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
626 ........................................
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
627
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
628 Starting with release 3.2 of the Python plugin, it is possible to
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
629 replace the C-FIND SCP and C-MOVE SCP of Orthanc by a Python
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
630 script. This feature can notably be used to create a custom DICOM
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
631 proxy. Here is a minimal example:
697
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
632
704
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
633 .. literalinclude:: python/dicom-find-move-scp.py
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
634 :language: python
ba2403ebd4b7 moving python samples in separate files (3)
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 703
diff changeset
635
697
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
636
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
637 .. highlight:: text
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
638
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
639 In this sample, the C-FIND SCP will send one single answer that
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
640 reproduces the values provided by the SCU::
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
641
699
a777b9e6ef70 clarifying sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 698
diff changeset
642 $ findscu localhost 4242 -S -k QueryRetrieveLevel=STUDY -k PatientName=TEST -k SeriesDescription=
697
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
643 I: ---------------------------
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
644 I: Find Response: 1 (Pending)
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
645 I:
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
646 I: # Dicom-Data-Set
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
647 I: # Used TransferSyntax: Little Endian Explicit
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
648 I: (0008,0005) CS [ISO_IR 100] # 10, 1 SpecificCharacterSet
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
649 I: (0008,0052) CS [HELLO0-STUDY] # 12, 1 QueryRetrieveLevel
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
650 I: (0008,103e) LO [HELLO1- ] # 8, 1 SeriesDescription
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
651 I: (0010,0010) PN [HELLO2-TEST ] # 12, 1 PatientName
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
652 I:
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
653
698
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 697
diff changeset
654 A more realistic Python script could for instance call the route
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 697
diff changeset
655 ``/modalities/{...}/query`` in the :ref:`REST API <rest-find-scu>` of
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 697
diff changeset
656 Orthanc using ``orthanc.RestApiPost()``, in order to query the content
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 697
diff changeset
657 a remote modality through a second C-FIND SCU request (this time
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 697
diff changeset
658 issued by Orthanc as a SCU).
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 697
diff changeset
659
697
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
660 The C-MOVE SCP can be invoked as follows::
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
661
699
a777b9e6ef70 clarifying sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 698
diff changeset
662 $ movescu localhost 4242 -aem TARGET -aec SOURCE -aet MOVESCU -S -k QueryRetrieveLevel=IMAGE -k StudyInstanceUID=1.2.3.4
697
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
663
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
664 The C-MOVE request above would print the following information in the
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
665 Orthanc logs::
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
666
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
667 W0610 18:30:36.840865 PluginsManager.cpp:168] C-MOVE request to be handled in Python: {
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
668 "AccessionNumber": "",
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
669 "Level": "INSTANCE",
699
a777b9e6ef70 clarifying sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 698
diff changeset
670 "OriginatorAET": "MOVESCU",
697
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
671 "OriginatorID": 1,
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
672 "PatientID": "",
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
673 "SOPInstanceUID": "",
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
674 "SeriesInstanceUID": "",
699
a777b9e6ef70 clarifying sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 698
diff changeset
675 "SourceAET": "SOURCE",
697
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
676 "StudyInstanceUID": "1.2.3.4",
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
677 "TargetAET": "TARGET"
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
678 }
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
679
710
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 709
diff changeset
680 It is now up to your Python callback to process the C-MOVE SCU request,
697
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
681 for instance by calling the route ``/modalities/{...}/store`` in the
7581dc208323 Handling DICOM SCP requests using a Python plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 696
diff changeset
682 :ref:`REST API <rest-store-scu>` of Orthanc using
700
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
683 ``orthanc.RestApiPost()``. It is highly advised to create a Python
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
684 thread to handle the request, in order to avoid blocking Orthanc as
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
685 much as possible.
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
686
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
687
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
688 .. _python_worklists:
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
689
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
690 Handling worklist SCP requests (new in 3.2)
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
691 ...........................................
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
692
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
693 Starting with release 3.2 of the Python plugin, it is possible to
701
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
694 answer :ref:`worklist queries <worklist>` using a Python script. This
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
695 is especially useful to easily create a bridge between Orthanc,
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
696 HL7/FHIR messages and RIS systems. Indeed, Python provides many tools
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
697 to handle HL7 such as `python-hl7 library
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
698 <https://python-hl7.readthedocs.io/en/latest/>`__.
700
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
699
973
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
700 The following Python script reproduces features similar to the
700
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
701 :ref:`sample modality worklists plugin <worklists-plugin>`:
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
702
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
703 .. literalinclude:: python/worklist.py
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
704 :language: python
56a06ca9ec20 Handling worklist SCP requests in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 699
diff changeset
705
701
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
706 .. highlight:: text
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
707
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
708 Here is the result of this plugin on a sample call::
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
709
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
710 $ findscu -W -k "ScheduledProcedureStepSequence[0].Modality=MR" 127.0.0.1 4242
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
711 I: ---------------------------
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
712 I: Find Response: 1 (Pending)
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
713 I:
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
714 I: # Dicom-Data-Set
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
715 I: # Used TransferSyntax: Little Endian Explicit
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
716 I: (0008,0005) CS [ISO_IR 100] # 10, 1 SpecificCharacterSet
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
717 I: (0040,0100) SQ (Sequence with explicit length #=1) # 18, 1 ScheduledProcedureStepSequence
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
718 I: (fffe,e000) na (Item with explicit length #=1) # 10, 1 Item
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
719 I: (0008,0060) CS [MR] # 2, 1 Modality
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
720 I: (fffe,e00d) na (ItemDelimitationItem for re-encoding) # 0, 0 ItemDelimitationItem
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
721 I: (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) # 0, 0 SequenceDelimitationItem
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
722 I:
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
723 I: ---------------------------
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
724 I: Find Response: 2 (Pending)
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
725 I:
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
726 I: # Dicom-Data-Set
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
727 I: # Used TransferSyntax: Little Endian Explicit
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
728 I: (0008,0005) CS [ISO_IR 100] # 10, 1 SpecificCharacterSet
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
729 I: (0040,0100) SQ (Sequence with explicit length #=1) # 18, 1 ScheduledProcedureStepSequence
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
730 I: (fffe,e000) na (Item with explicit length #=1) # 10, 1 Item
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
731 I: (0008,0060) CS [MR] # 2, 1 Modality
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
732 I: (fffe,e00d) na (ItemDelimitationItem for re-encoding) # 0, 0 ItemDelimitationItem
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
733 I: (fffe,e0dd) na (SequenceDelimitationItem for re-encod.) # 0, 0 SequenceDelimitationItem
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
734 I:
f093160dd7f4 cross-references regarding worklists
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 700
diff changeset
735
727
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
736
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
737 .. _pynetdicom:
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
738
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
739 Replacing DICOM SCP of Orthanc by pynetdicom
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
740 ............................................
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
741
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
742 .. highlight:: json
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
743
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
744 Thanks to Python plugins, it is also possible to replace the built-in
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
745 DICOM SCP of Orthanc by `pynetdicom
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
746 <https://pydicom.github.io/pynetdicom/stable/examples/storage.html>`__
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
747 so as to customize how the DICOM protocol is handled. Firstly, in the
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
748 configuration file, make sure to disable the Orthanc SCP by setting
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
749 ``DicomServerEnabled`` to ``false``::
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
750
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
751 {
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
752 "Plugins" : [ "." ],
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
753 "PythonScript" : "pynetdicom.py",
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
754 "DicomServerEnabled" : false
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
755 }
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
756
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
757 Secondly, here a basic plugin illustrating how to start and stop the
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
758 pynetdicom server, and handle incoming C-STORE requests:
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
759
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
760 .. literalinclude:: python/pynetdicom.py
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
761 :language: python
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
762
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
763 As can be seen in this listing, whenever the pynetdicom receives an
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
764 incoming C-STORE request, it makes a POST call to the URI
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
765 ``/instances`` in the REST API of Orthanc in order to store the
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
766 embedded DICOM dataset into Orthanc. Obviously, one can build more
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
767 complex DICOM servers by handling more messages than C-STORE alone.
698eb280060a pynetdicom sample
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 719
diff changeset
768
747
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
769
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
770 .. _python_exception:
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
771
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
772 Catching exceptions
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
773 ...................
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
774
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
775 Starting with release 3.3 of the Python plugin, the plugin generates a
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
776 Python exception derived from class ``orthanc.OrthancException`` if an
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
777 error is encountered. This exception contains a tuple that provides
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
778 the error code and its textual description.
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
779
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
780 In releases <= 3.2, the Python plugin raised the `built-in exception
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
781 <https://docs.python.org/3/library/exceptions.html>`__ ``ValueError``.
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
782
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
783 Here is an example showing how to catch exceptions:
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
784
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
785 .. literalinclude:: python/exception.py
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
786 :language: python
56d48f6e52cc catching exceptions in python plugins
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 741
diff changeset
787
556
6a3d48510b0b Python sample: "Forbid or allow access to REST resources (authorization)", deprecating advanced authorization plugin
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 555
diff changeset
788
748
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
789 .. _python_storage_area:
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
790
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
791 Implementing a custom storage area (new in 3.3)
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
792 ...............................................
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
793
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
794 Starting with release 3.3 of the Python plugin, it is possible to
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
795 replace the built-in storage area of Orthanc (that writes
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
796 :ref:`attachments <metadata>` onto the filesystem in the
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
797 ``OrthancStorage`` folder by default), by providing 3 Python callbacks
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
798 to the ``orthanc.RegisterStorageArea()`` function:
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
799
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
800 * The first callback indicates how to **create** an attachment into
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
801 the storage area.
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
802
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
803 * The second callback indicates how to **read** an attachment from the
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
804 storage area.
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
805
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
806 * The third callback indicates how to **remove** an attachment out of
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
807 the storage area.
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
808
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
809 This feature can be used to quickly and easily interface Orthanc with
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
810 any `object-based storage
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
811 <https://en.wikipedia.org/wiki/Object_storage>`__ technology available
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
812 in Python (such as `Ceph
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
813 <https://en.wikipedia.org/wiki/Ceph_(software)>`__ or AWS S3-like
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
814 tools). The performance will not be as good as a C/C++ native plugin
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
815 (cf. the :ref:`cloud storage <object-storage>`, the :ref:`PostgreSQL
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
816 <postgresql>` and the :ref:`MySQL <mysql>` plugins), but it can be
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
817 used for prototyping or for basic setups.
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
818
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
819 Here is a full, self-explaining sample:
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
820
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
821 .. literalinclude:: python/storage-area.py
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
822 :language: python
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
823
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
824 The ``contentType`` can be used to apply a special treatment to some
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
825 types of attachments (typically, DICOM instances). This parameter
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
826 takes its values from the ``orthanc.ContentType`` enumeration.
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
827
a296fe06fd86 Implementing a custom storage area in Python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 747
diff changeset
828
799
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
829 .. _python_received_instance:
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
830
819
a67ceccebf02 releasing Python plugin 4.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 817
diff changeset
831 Modifying received instances (new in 4.0)
a67ceccebf02 releasing Python plugin 4.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 817
diff changeset
832 .........................................
799
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
833
819
a67ceccebf02 releasing Python plugin 4.0
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 817
diff changeset
834 Starting with release 4.0 of the Python plugin, it is possible to
799
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
835 modify instances received by Orthanc before they are stored in
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
836 the storage. This is usually easier to perform modification at this
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
837 stage compared to using the ``/modify`` route once the instances
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
838 has been stored.
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
839
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
840 .. literalinclude:: python/received-instance-callback.py
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
841 :language: python
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
842
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
843
852
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
844 Filtering incoming C-Store instances (new in 4.0)
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
845 .................................................
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
846
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
847 Starting with release 4.0 of the Python plugin, it is possible to
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
848 filter instances received from C-Store and return a specific error
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
849 code to the sending modality.
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
850
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
851 This can be used, e.g, to implement a quota per modality or return
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
852 an ``out-of-resources`` status if the Orthanc storage is almost full.
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
853
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
854 .. literalinclude:: python/incoming-cstore-filter.py
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
855 :language: python
450f0efebe4f FilterIncomingCStoreInstance python sample
Alain Mazy <am@osimis.io>
parents: 839
diff changeset
856
799
ecf431e1bd44 python sample for ReceivedInstanceCallback
Alain Mazy <am@osimis.io>
parents: 763
diff changeset
857
973
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
858 Storage Commitment SCP (new in 4.1)
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
859 ...................................
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
860
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
861 Starting with release 4.1 of the Python plugin, it is possible to
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
862 provide your own implementation of the :ref:`Storage Commitment <storage-commitment>`.
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
863
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
864 This can be used, e.g, to check that you have backup the orthanc data in a
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
865 long term storage.
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
866
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
867 .. literalinclude:: python/storage-commitment-default.py
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
868 :language: python
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
869
2d817288cad4 added python storage commitment
Alain Mazy <am@osimis.io>
parents: 963
diff changeset
870
975
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
871 .. _python_extend_orthanc_explorer:
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
872
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
873 Extending the Orthanc Explorer interface
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
874 ........................................
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
875
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
876 Here is a sample plugin that adds a new button to Orthanc Explorer
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
877 that triggers a Python function:
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
878
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
879 .. literalinclude:: python/sample-python-button.py
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
880 :language: python
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
881
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
882 As can be seen in this sample:
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
883
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
884 * The call to ``orthanc.ExtendOrthancExplorer()`` installs the button
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
885 with JavaScript code that uses the `jQuery Mobile framework
1021
a3436ae3709c Orthanc 1.12.3
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 1018
diff changeset
886 <https://demos.jquerymobile.com/1.1.0/>`__ (as of Orthanc 1.12.3,
975
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
887 version 1.1.0 of jQuery Mobile is used in Orthanc Explorer).
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
888
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
889 * If clicking on the button, a GET call to the REST API is made to
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
890 ``../execute-python``. The prefix ``../`` stems from the fact that
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
891 Orthanc Explorer is branched inside the ``app/`` folder of the REST
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
892 API of Orthanc.
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
893
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
894 * The GET call to ``../execute-python`` executes the
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
895 ``ExecutePython()`` callback function that is written in Python.
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
896
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
897 Note that it is only possible to extend Orthanc Explorer 1, which is
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
898 the built-in Web interface of Orthanc. It is not possible to extend
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
899 the :ref:`Orthanc Explorer 2 <orthanc-explorer-2>` interface.
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
900
eb49a4ad8fbc Python plugin: Extending the Orthanc Explorer interface
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 973
diff changeset
901
351
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
902 Performance and concurrency
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
903 ---------------------------
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
904
471
a735476a0e6e note about fork on windows
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
905 **Important:** This section only applies to UNIX-like systems. The
a735476a0e6e note about fork on windows
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
906 ``multiprocessing`` package will not work on Microsoft Windows as the
a735476a0e6e note about fork on windows
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
907 latter OS has a different model for `forking processes
a735476a0e6e note about fork on windows
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
908 <https://en.wikipedia.org/wiki/Fork_(system_call)>`__.
a735476a0e6e note about fork on windows
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 462
diff changeset
909
555
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
910 Using slave processes
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
911 .....................
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
912
351
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
913 Let us consider the following sample Python script that makes a
702
6e02cd89eb6a moving python samples in separate files
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 701
diff changeset
914 CPU-intensive computation on a REST callback:
351
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
915
702
6e02cd89eb6a moving python samples in separate files
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 701
diff changeset
916 .. literalinclude:: python/multiprocessing-1.py
6e02cd89eb6a moving python samples in separate files
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 701
diff changeset
917 :language: python
351
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
918
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
919 .. highlight:: text
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
920
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
921 Calling this REST route from the command-line returns the time that is
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
922 needed to compute 30 million times a squared root on your CPU::
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
923
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
924 $ curl http://localhost:8042/computation
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
925 computation done in 4.208 seconds
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
926
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
927 Now, let us call this route three times concurrently (we use bash)::
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
928
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
929 $ (curl http://localhost:8042/computation & curl http://localhost:8042/computation & curl http://localhost:8042/computation )
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
930 computation done in 11.262 seconds
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
931 computation done in 12.457 seconds
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
932 computation done in 13.360 seconds
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
933
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
934 As can be seen, the computation time has tripled. This means that the
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
935 computations were not distributed across the available CPU cores.
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
936 This might seem surprising, as Orthanc is a threaded server (in
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
937 Orthanc, a pool of C++ threads serves concurrent requests).
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
938
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
939 The explanation is that the Python interpreter (`CPython
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
940 <https://en.wikipedia.org/wiki/CPython>`__ actually) is built on the
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
941 top of a so-called `Global Interpreter Lock (GIL)
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
942 <https://en.wikipedia.org/wiki/Global_interpreter_lock>`__. The GIL is
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
943 basically a mutex that protects all the calls to the Python
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
944 interpreter. If multiple C++ threads from Orthanc call a Python
353
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
945 callback, only one can proceed at any given time. Note however that
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
946 the GIL only applies to the Python script: The baseline REST API of
0122c668f4ec python licensing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 352
diff changeset
947 Orthanc is not affected by the GIL.
351
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
948
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
949 The solution is to use the `multiprocessing primitives
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
950 <https://docs.python.org/3/library/multiprocessing.html>`__ of Python.
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
951 The "master" Python interpreter that is initially started by the
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
952 Orthanc plugin, can start several `children processes
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
953 <https://en.wikipedia.org/wiki/Process_(computing)>`__, each of these
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
954 processes running a separate Python interpreter. This allows to
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
955 offload intensive computations from the "master" Python interpreter of
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
956 Orthanc onto those "slave" interpreters. The ``multiprocessing``
702
6e02cd89eb6a moving python samples in separate files
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 701
diff changeset
957 library is actually quite straightforward to use:
351
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
958
702
6e02cd89eb6a moving python samples in separate files
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 701
diff changeset
959 .. literalinclude:: python/multiprocessing-2.py
6e02cd89eb6a moving python samples in separate files
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 701
diff changeset
960 :language: python
351
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
961
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
962 .. highlight:: text
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
963
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
964 Here is now the result of calling this route three times concurrently::
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
965
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
966 $ (curl http://localhost:8042/computation & curl http://localhost:8042/computation & curl http://localhost:8042/computation )
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
967 computation done in 4.211 seconds
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
968 computation done in 4.215 seconds
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
969 computation done in 4.225 seconds
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
970
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
971 As can be seen, the calls to the Python computation now fully run in
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
972 parallel (the time is cut down from 12 seconds to 4 seconds, the same
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
973 as for one isolated request).
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
974
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
975 Note also how the ``multiprocessing`` library allows to make a fine
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
976 control over the computational resources that are available to the
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
977 Python script: The number of "slave" interpreters can be easily
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
978 changed in the constructor of the ``multiprocessing.Pool`` object, and
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
979 are fully independent of the threads used by the Orthanc server.
e2863083fa30 multiprocessing
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 350
diff changeset
980
555
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
981 Obviously, an in-depth discussion about the ``multiprocessing``
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
982 library is out of the scope of this document. There are many
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
983 references available on Internet. Also, note that ``threading`` is not
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
984 useful here, as Python multithreading is also limited by the GIL, and
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
985 is more targeted at dealing with costly I/O operations or with the
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
986 :ref:`scheduling of commands <python-scheduler>`.
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
987
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
988
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
989 Slave processes and the "orthanc" module
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
990 ........................................
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
991
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
992 Very importantly, pay attention to the fact that **only the "master"
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
993 Python interpreter has access to the Orthanc SDK**. The "slave"
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
994 processes have no access to the ``orthanc`` module.
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
995
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
996 You must write your Python plugin so as that all the calls to
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
997 ``orthanc`` are moved from the slaves process to the master
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
998 process. For instance, here is how you would parse a DICOM file in a
702
6e02cd89eb6a moving python samples in separate files
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 701
diff changeset
999 slave process:
352
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 351
diff changeset
1000
702
6e02cd89eb6a moving python samples in separate files
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 701
diff changeset
1001 .. literalinclude:: python/multiprocessing-3.py
6e02cd89eb6a moving python samples in separate files
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 701
diff changeset
1002 :language: python
352
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 351
diff changeset
1003
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 351
diff changeset
1004 Communication primitives such as ``multiprocessing.Queue`` are
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 351
diff changeset
1005 available to exchange messages from the "slave" Python interpreters to
555
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
1006 the "master" Python interpreter for more advanced scenarios.
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
1007
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
1008 NB: Starting with release 3.0 of the Python plugin, it is possible to
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
1009 call the REST API of Orthanc from a slave process in a more direct
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
1010 way. The function ``orthanc.GenerateRestApiAuthorizationToken()`` can
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
1011 be used to create an authorization token that provides full access to
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
1012 the REST API of Orthanc (without have to set credentials in your
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
1013 plugin). Any HTTP client library for Python, such as `requests
6fb469a3c382 Python plugin: documentation of orthanc.GenerateRestApiAuthorizationToken()
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 554
diff changeset
1014 <https://requests.readthedocs.io/en/master/>`__, can then be used to
702
6e02cd89eb6a moving python samples in separate files
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 701
diff changeset
1015 access the REST API of Orthanc. Here is a minimal example:
352
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 351
diff changeset
1016
702
6e02cd89eb6a moving python samples in separate files
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 701
diff changeset
1017 .. literalinclude:: python/multiprocessing-4.py
6e02cd89eb6a moving python samples in separate files
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 701
diff changeset
1018 :language: python
1018
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1019
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1020 Working with virtual environments
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1021 ---------------------------------
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1022
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1023 By default, Orthanc uses the system-wide Python installation and
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1024 therefore has access to the python modules that have been installed
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1025 system-wide.
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1026
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1027 As of version 4.1 of the python plugin, there is no built-in support
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1028 for working with a `virtual environment <https://docs.python.org/3/library/venv.html>`__.
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1029 However, you may modify the python path at the very beginning of the script
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1030 to instruct python to look for modules in your environment.
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1031
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1032 **Example 1**: On a Linux system, consider that you have created a virtual environment in ``/tmp/.venv``
1024
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1033 and, you may just an environment variable to instruct the python interpreter to search for modules into
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1034 your virtual env. E.g, in a Docker container, you may implement it this way::
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1035
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1036 FROM orthancteam/orthanc-pre-release:bookworm
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1037
1025
Alain Mazy <am@osimis.io>
parents: 1024
diff changeset
1038 # This example is using a virtual env that is not mandatory when using Docker containers
Alain Mazy <am@osimis.io>
parents: 1024
diff changeset
1039 # but recommended since python 3.11 and Debian bookworm based images where you get a warning
Alain Mazy <am@osimis.io>
parents: 1024
diff changeset
1040 # when installing system-wide packages. RUN apt-get update && apt install -y python3-venv
1024
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1041 RUN python3 -m venv /.venv
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1042
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1043 RUN /.venv/bin/pip install pydicom
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1044 ENV PYTHONPATH=/.venv/lib64/python3.11/site-packages/
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1045
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1046 RUN mkdir /python
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1047 COPY * /python/
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1048
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1049
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1050
94d41b7d1aac virtual env in Docker
Alain Mazy <am@osimis.io>
parents: 1023
diff changeset
1051 **Example 2**: On a Linux system, consider that you have created a virtual environment in ``/tmp/.venv``
1018
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1052 and you want to use only the modules that have been installed in this virtual environment.
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1053 In this case, you may simply rewrite ``sys.path``:
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1054
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1055 .. literalinclude:: python/venv-linux.py
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1056 :language: python
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1057
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1058
1041
fe9c92d81082 note about python
Sebastien Jodogne <s.jodogne@gmail.com>
parents: 1025
diff changeset
1059 **Example 3**: On a Windows system, consider that you have created a virtual environment in ``C:/tmp/.venv/``.
1018
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1060 Instead of defining ``sys.path`` from scratch, it is possible to simply insert the venv-packages in
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1061 the ``sys.path``. By adding the ``venv`` to an early index (``0``), any package required by your code
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1062 will be looked up in the ``venv`` first. And, as a consequence, if the package is not present, the system-wide
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1063 installation of that package might be loaded:
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1064
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1065 .. literalinclude:: python/venv-windows.py
868552e0caf8 python venv
Alain Mazy <am@osimis.io>
parents: 1013
diff changeset
1066 :language: python