dtlpy 1.113.10__py3-none-any.whl → 1.114.13__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- dtlpy/__init__.py +488 -488
- dtlpy/__version__.py +1 -1
- dtlpy/assets/__init__.py +26 -26
- dtlpy/assets/__pycache__/__init__.cpython-38.pyc +0 -0
- dtlpy/assets/code_server/config.yaml +2 -2
- dtlpy/assets/code_server/installation.sh +24 -24
- dtlpy/assets/code_server/launch.json +13 -13
- dtlpy/assets/code_server/settings.json +2 -2
- dtlpy/assets/main.py +53 -53
- dtlpy/assets/main_partial.py +18 -18
- dtlpy/assets/mock.json +11 -11
- dtlpy/assets/model_adapter.py +83 -83
- dtlpy/assets/package.json +61 -61
- dtlpy/assets/package_catalog.json +29 -29
- dtlpy/assets/package_gitignore +307 -307
- dtlpy/assets/service_runners/__init__.py +33 -33
- dtlpy/assets/service_runners/converter.py +96 -96
- dtlpy/assets/service_runners/multi_method.py +49 -49
- dtlpy/assets/service_runners/multi_method_annotation.py +54 -54
- dtlpy/assets/service_runners/multi_method_dataset.py +55 -55
- dtlpy/assets/service_runners/multi_method_item.py +52 -52
- dtlpy/assets/service_runners/multi_method_json.py +52 -52
- dtlpy/assets/service_runners/single_method.py +37 -37
- dtlpy/assets/service_runners/single_method_annotation.py +43 -43
- dtlpy/assets/service_runners/single_method_dataset.py +43 -43
- dtlpy/assets/service_runners/single_method_item.py +41 -41
- dtlpy/assets/service_runners/single_method_json.py +42 -42
- dtlpy/assets/service_runners/single_method_multi_input.py +45 -45
- dtlpy/assets/voc_annotation_template.xml +23 -23
- dtlpy/caches/base_cache.py +32 -32
- dtlpy/caches/cache.py +473 -473
- dtlpy/caches/dl_cache.py +201 -201
- dtlpy/caches/filesystem_cache.py +89 -89
- dtlpy/caches/redis_cache.py +84 -84
- dtlpy/dlp/__init__.py +20 -20
- dtlpy/dlp/cli_utilities.py +367 -367
- dtlpy/dlp/command_executor.py +764 -764
- dtlpy/dlp/dlp +1 -1
- dtlpy/dlp/dlp.bat +1 -1
- dtlpy/dlp/dlp.py +128 -128
- dtlpy/dlp/parser.py +651 -651
- dtlpy/entities/__init__.py +83 -83
- dtlpy/entities/analytic.py +311 -311
- dtlpy/entities/annotation.py +1879 -1879
- dtlpy/entities/annotation_collection.py +699 -699
- dtlpy/entities/annotation_definitions/__init__.py +20 -20
- dtlpy/entities/annotation_definitions/base_annotation_definition.py +100 -100
- dtlpy/entities/annotation_definitions/box.py +195 -195
- dtlpy/entities/annotation_definitions/classification.py +67 -67
- dtlpy/entities/annotation_definitions/comparison.py +72 -72
- dtlpy/entities/annotation_definitions/cube.py +204 -204
- dtlpy/entities/annotation_definitions/cube_3d.py +149 -149
- dtlpy/entities/annotation_definitions/description.py +32 -32
- dtlpy/entities/annotation_definitions/ellipse.py +124 -124
- dtlpy/entities/annotation_definitions/free_text.py +62 -62
- dtlpy/entities/annotation_definitions/gis.py +69 -69
- dtlpy/entities/annotation_definitions/note.py +139 -139
- dtlpy/entities/annotation_definitions/point.py +117 -117
- dtlpy/entities/annotation_definitions/polygon.py +182 -182
- dtlpy/entities/annotation_definitions/polyline.py +111 -111
- dtlpy/entities/annotation_definitions/pose.py +92 -92
- dtlpy/entities/annotation_definitions/ref_image.py +86 -86
- dtlpy/entities/annotation_definitions/segmentation.py +240 -240
- dtlpy/entities/annotation_definitions/subtitle.py +34 -34
- dtlpy/entities/annotation_definitions/text.py +85 -85
- dtlpy/entities/annotation_definitions/undefined_annotation.py +74 -74
- dtlpy/entities/app.py +220 -220
- dtlpy/entities/app_module.py +107 -107
- dtlpy/entities/artifact.py +174 -174
- dtlpy/entities/assignment.py +399 -399
- dtlpy/entities/base_entity.py +214 -214
- dtlpy/entities/bot.py +113 -113
- dtlpy/entities/codebase.py +296 -296
- dtlpy/entities/collection.py +38 -38
- dtlpy/entities/command.py +169 -169
- dtlpy/entities/compute.py +442 -442
- dtlpy/entities/dataset.py +1285 -1285
- dtlpy/entities/directory_tree.py +44 -44
- dtlpy/entities/dpk.py +470 -470
- dtlpy/entities/driver.py +222 -222
- dtlpy/entities/execution.py +397 -397
- dtlpy/entities/feature.py +124 -124
- dtlpy/entities/feature_set.py +145 -145
- dtlpy/entities/filters.py +641 -641
- dtlpy/entities/gis_item.py +107 -107
- dtlpy/entities/integration.py +184 -184
- dtlpy/entities/item.py +953 -953
- dtlpy/entities/label.py +123 -123
- dtlpy/entities/links.py +85 -85
- dtlpy/entities/message.py +175 -175
- dtlpy/entities/model.py +694 -691
- dtlpy/entities/node.py +1005 -1005
- dtlpy/entities/ontology.py +803 -803
- dtlpy/entities/organization.py +287 -287
- dtlpy/entities/package.py +657 -657
- dtlpy/entities/package_defaults.py +5 -5
- dtlpy/entities/package_function.py +185 -185
- dtlpy/entities/package_module.py +113 -113
- dtlpy/entities/package_slot.py +118 -118
- dtlpy/entities/paged_entities.py +290 -267
- dtlpy/entities/pipeline.py +593 -593
- dtlpy/entities/pipeline_execution.py +279 -279
- dtlpy/entities/project.py +394 -394
- dtlpy/entities/prompt_item.py +499 -499
- dtlpy/entities/recipe.py +301 -301
- dtlpy/entities/reflect_dict.py +102 -102
- dtlpy/entities/resource_execution.py +138 -138
- dtlpy/entities/service.py +958 -958
- dtlpy/entities/service_driver.py +117 -117
- dtlpy/entities/setting.py +294 -294
- dtlpy/entities/task.py +491 -491
- dtlpy/entities/time_series.py +143 -143
- dtlpy/entities/trigger.py +426 -426
- dtlpy/entities/user.py +118 -118
- dtlpy/entities/webhook.py +124 -124
- dtlpy/examples/__init__.py +19 -19
- dtlpy/examples/add_labels.py +135 -135
- dtlpy/examples/add_metadata_to_item.py +21 -21
- dtlpy/examples/annotate_items_using_model.py +65 -65
- dtlpy/examples/annotate_video_using_model_and_tracker.py +75 -75
- dtlpy/examples/annotations_convert_to_voc.py +9 -9
- dtlpy/examples/annotations_convert_to_yolo.py +9 -9
- dtlpy/examples/convert_annotation_types.py +51 -51
- dtlpy/examples/converter.py +143 -143
- dtlpy/examples/copy_annotations.py +22 -22
- dtlpy/examples/copy_folder.py +31 -31
- dtlpy/examples/create_annotations.py +51 -51
- dtlpy/examples/create_video_annotations.py +83 -83
- dtlpy/examples/delete_annotations.py +26 -26
- dtlpy/examples/filters.py +113 -113
- dtlpy/examples/move_item.py +23 -23
- dtlpy/examples/play_video_annotation.py +13 -13
- dtlpy/examples/show_item_and_mask.py +53 -53
- dtlpy/examples/triggers.py +49 -49
- dtlpy/examples/upload_batch_of_items.py +20 -20
- dtlpy/examples/upload_items_and_custom_format_annotations.py +55 -55
- dtlpy/examples/upload_items_with_modalities.py +43 -43
- dtlpy/examples/upload_segmentation_annotations_from_mask_image.py +44 -44
- dtlpy/examples/upload_yolo_format_annotations.py +70 -70
- dtlpy/exceptions.py +125 -125
- dtlpy/miscellaneous/__init__.py +20 -20
- dtlpy/miscellaneous/dict_differ.py +95 -95
- dtlpy/miscellaneous/git_utils.py +217 -217
- dtlpy/miscellaneous/json_utils.py +14 -14
- dtlpy/miscellaneous/list_print.py +105 -105
- dtlpy/miscellaneous/zipping.py +130 -130
- dtlpy/ml/__init__.py +20 -20
- dtlpy/ml/base_feature_extractor_adapter.py +27 -27
- dtlpy/ml/base_model_adapter.py +945 -940
- dtlpy/ml/metrics.py +461 -461
- dtlpy/ml/predictions_utils.py +274 -274
- dtlpy/ml/summary_writer.py +57 -57
- dtlpy/ml/train_utils.py +60 -60
- dtlpy/new_instance.py +252 -252
- dtlpy/repositories/__init__.py +56 -56
- dtlpy/repositories/analytics.py +85 -85
- dtlpy/repositories/annotations.py +916 -916
- dtlpy/repositories/apps.py +383 -383
- dtlpy/repositories/artifacts.py +452 -452
- dtlpy/repositories/assignments.py +599 -599
- dtlpy/repositories/bots.py +213 -213
- dtlpy/repositories/codebases.py +559 -559
- dtlpy/repositories/collections.py +332 -348
- dtlpy/repositories/commands.py +158 -158
- dtlpy/repositories/compositions.py +61 -61
- dtlpy/repositories/computes.py +434 -406
- dtlpy/repositories/datasets.py +1291 -1291
- dtlpy/repositories/downloader.py +895 -895
- dtlpy/repositories/dpks.py +433 -433
- dtlpy/repositories/drivers.py +266 -266
- dtlpy/repositories/executions.py +817 -817
- dtlpy/repositories/feature_sets.py +226 -226
- dtlpy/repositories/features.py +238 -238
- dtlpy/repositories/integrations.py +484 -484
- dtlpy/repositories/items.py +909 -915
- dtlpy/repositories/messages.py +94 -94
- dtlpy/repositories/models.py +877 -867
- dtlpy/repositories/nodes.py +80 -80
- dtlpy/repositories/ontologies.py +511 -511
- dtlpy/repositories/organizations.py +525 -525
- dtlpy/repositories/packages.py +1941 -1941
- dtlpy/repositories/pipeline_executions.py +448 -448
- dtlpy/repositories/pipelines.py +642 -642
- dtlpy/repositories/projects.py +539 -539
- dtlpy/repositories/recipes.py +399 -399
- dtlpy/repositories/resource_executions.py +137 -137
- dtlpy/repositories/schema.py +120 -120
- dtlpy/repositories/service_drivers.py +213 -213
- dtlpy/repositories/services.py +1704 -1704
- dtlpy/repositories/settings.py +339 -339
- dtlpy/repositories/tasks.py +1124 -1124
- dtlpy/repositories/times_series.py +278 -278
- dtlpy/repositories/triggers.py +536 -536
- dtlpy/repositories/upload_element.py +257 -257
- dtlpy/repositories/uploader.py +651 -651
- dtlpy/repositories/webhooks.py +249 -249
- dtlpy/services/__init__.py +22 -22
- dtlpy/services/aihttp_retry.py +131 -131
- dtlpy/services/api_client.py +1782 -1782
- dtlpy/services/api_reference.py +40 -40
- dtlpy/services/async_utils.py +133 -133
- dtlpy/services/calls_counter.py +44 -44
- dtlpy/services/check_sdk.py +68 -68
- dtlpy/services/cookie.py +115 -115
- dtlpy/services/create_logger.py +156 -156
- dtlpy/services/events.py +84 -84
- dtlpy/services/logins.py +235 -235
- dtlpy/services/reporter.py +256 -256
- dtlpy/services/service_defaults.py +91 -91
- dtlpy/utilities/__init__.py +20 -20
- dtlpy/utilities/annotations/__init__.py +16 -16
- dtlpy/utilities/annotations/annotation_converters.py +269 -269
- dtlpy/utilities/base_package_runner.py +264 -264
- dtlpy/utilities/converter.py +1650 -1650
- dtlpy/utilities/dataset_generators/__init__.py +1 -1
- dtlpy/utilities/dataset_generators/dataset_generator.py +670 -670
- dtlpy/utilities/dataset_generators/dataset_generator_tensorflow.py +23 -23
- dtlpy/utilities/dataset_generators/dataset_generator_torch.py +21 -21
- dtlpy/utilities/local_development/__init__.py +1 -1
- dtlpy/utilities/local_development/local_session.py +179 -179
- dtlpy/utilities/reports/__init__.py +2 -2
- dtlpy/utilities/reports/figures.py +343 -343
- dtlpy/utilities/reports/report.py +71 -71
- dtlpy/utilities/videos/__init__.py +17 -17
- dtlpy/utilities/videos/video_player.py +598 -598
- dtlpy/utilities/videos/videos.py +470 -470
- {dtlpy-1.113.10.data → dtlpy-1.114.13.data}/scripts/dlp +1 -1
- dtlpy-1.114.13.data/scripts/dlp.bat +2 -0
- {dtlpy-1.113.10.data → dtlpy-1.114.13.data}/scripts/dlp.py +128 -128
- {dtlpy-1.113.10.dist-info → dtlpy-1.114.13.dist-info}/LICENSE +200 -200
- {dtlpy-1.113.10.dist-info → dtlpy-1.114.13.dist-info}/METADATA +172 -172
- dtlpy-1.114.13.dist-info/RECORD +240 -0
- {dtlpy-1.113.10.dist-info → dtlpy-1.114.13.dist-info}/WHEEL +1 -1
- tests/features/environment.py +551 -550
- dtlpy-1.113.10.data/scripts/dlp.bat +0 -2
- dtlpy-1.113.10.dist-info/RECORD +0 -244
- tests/assets/__init__.py +0 -0
- tests/assets/models_flow/__init__.py +0 -0
- tests/assets/models_flow/failedmain.py +0 -52
- tests/assets/models_flow/main.py +0 -62
- tests/assets/models_flow/main_model.py +0 -54
- {dtlpy-1.113.10.dist-info → dtlpy-1.114.13.dist-info}/entry_points.txt +0 -0
- {dtlpy-1.113.10.dist-info → dtlpy-1.114.13.dist-info}/top_level.txt +0 -0
|
@@ -1,264 +1,264 @@
|
|
|
1
|
-
import datetime
|
|
2
|
-
import threading
|
|
3
|
-
|
|
4
|
-
from .. import entities
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
class BaseServiceRunner:
|
|
8
|
-
_do_reset = False
|
|
9
|
-
_auto_refresh_dtlpy_token = None
|
|
10
|
-
_refresh_dtlpy_token = None
|
|
11
|
-
_threads_terminated = list()
|
|
12
|
-
_threads_terminated_lock = threading.Lock()
|
|
13
|
-
_service_entity = None
|
|
14
|
-
|
|
15
|
-
def do_reset(self):
|
|
16
|
-
self._do_reset = True
|
|
17
|
-
|
|
18
|
-
@staticmethod
|
|
19
|
-
def ping(progress):
|
|
20
|
-
progress.logger.debug('received ping at: {}'.format(datetime.datetime.now().isoformat()))
|
|
21
|
-
return 'pong'
|
|
22
|
-
|
|
23
|
-
def _terminate(self, tid):
|
|
24
|
-
with self._threads_terminated_lock:
|
|
25
|
-
self._threads_terminated.append(tid)
|
|
26
|
-
|
|
27
|
-
def kill_event(self):
|
|
28
|
-
ident = threading.get_ident()
|
|
29
|
-
if ident in self._threads_terminated:
|
|
30
|
-
with self._threads_terminated_lock:
|
|
31
|
-
self._threads_terminated.pop(self._threads_terminated.index(ident))
|
|
32
|
-
raise InterruptedError('Execution received termination signal')
|
|
33
|
-
|
|
34
|
-
@property
|
|
35
|
-
def service_entity(self) -> entities.Service:
|
|
36
|
-
assert isinstance(self._service_entity, entities.Service), "service_entity must be a dl.Service object"
|
|
37
|
-
return self._service_entity
|
|
38
|
-
|
|
39
|
-
@service_entity.setter
|
|
40
|
-
def service_entity(self, value):
|
|
41
|
-
assert isinstance(value, entities.Service), "service_entity must be a dl.Service object"
|
|
42
|
-
self._service_entity = value
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
class Progress:
|
|
46
|
-
"""
|
|
47
|
-
Follow the event progress
|
|
48
|
-
"""
|
|
49
|
-
|
|
50
|
-
def update(self,
|
|
51
|
-
status=None,
|
|
52
|
-
progress=0,
|
|
53
|
-
message=None,
|
|
54
|
-
output=None,
|
|
55
|
-
duration=None,
|
|
56
|
-
action=None
|
|
57
|
-
):
|
|
58
|
-
"""
|
|
59
|
-
Update the progress flow
|
|
60
|
-
|
|
61
|
-
:param str status: the progress status to display
|
|
62
|
-
:param int progress: number of finished flow
|
|
63
|
-
:param str message: the progress message to display
|
|
64
|
-
:param dict output: json serializable object to update the event output
|
|
65
|
-
:param float duration: the event duration
|
|
66
|
-
:param str action: event action
|
|
67
|
-
"""
|
|
68
|
-
pass
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
class ItemStatusEvent:
|
|
72
|
-
def __init__(self, _json: dict):
|
|
73
|
-
if _json is None:
|
|
74
|
-
_json = dict()
|
|
75
|
-
|
|
76
|
-
self.pipeline_id = _json.get('pipelineId', None)
|
|
77
|
-
self.node_id = _json.get('nodeId', None)
|
|
78
|
-
self.action = _json.get('action', None)
|
|
79
|
-
|
|
80
|
-
status = _json.get('status', dict())
|
|
81
|
-
if status is None:
|
|
82
|
-
status = dict()
|
|
83
|
-
|
|
84
|
-
self.task_id = status.get('taskId', None)
|
|
85
|
-
self.assignment_id = status.get('assignmentId', None)
|
|
86
|
-
self.status = status.get('status', None)
|
|
87
|
-
self.creator = status.get('creator', None)
|
|
88
|
-
self.timestamp = status.get('timestamp', None)
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
class ExecutionEventContext:
|
|
92
|
-
def __init__(self, _json: dict):
|
|
93
|
-
if _json is None:
|
|
94
|
-
_json = dict()
|
|
95
|
-
|
|
96
|
-
self.resource = _json.get('resource', None)
|
|
97
|
-
self.source = _json.get('source', None)
|
|
98
|
-
self.action = _json.get('action', None)
|
|
99
|
-
self.resource_id = _json.get('resourceId', None)
|
|
100
|
-
self.user_id = _json.get('userId', None)
|
|
101
|
-
self.dataset_id = _json.get('datasetId', None)
|
|
102
|
-
self.project_id = _json.get('projectId', None)
|
|
103
|
-
self.body = _json.get('body', None)
|
|
104
|
-
self.item_status_event = ItemStatusEvent(_json.get('itemStatusEvent', dict()))
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
class Context:
|
|
108
|
-
"""
|
|
109
|
-
Contex of the service state
|
|
110
|
-
"""
|
|
111
|
-
|
|
112
|
-
def __init__(
|
|
113
|
-
self,
|
|
114
|
-
service: entities.Service = None,
|
|
115
|
-
package: entities.Package = None,
|
|
116
|
-
project: entities.Project = None,
|
|
117
|
-
event_context: dict = None,
|
|
118
|
-
execution_dict: dict = None,
|
|
119
|
-
progress: Progress = None,
|
|
120
|
-
logger=None,
|
|
121
|
-
sdk=None
|
|
122
|
-
):
|
|
123
|
-
"""
|
|
124
|
-
A Context entity use DTLPY entities for context in a service runner
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
:param dict execution_dict: the current execution dict in the state
|
|
128
|
-
:param dict service: the current service entity in th state
|
|
129
|
-
:param dict package: the current package entity in th state
|
|
130
|
-
:param dict project: the current project entity in th state
|
|
131
|
-
:param dict event_context: ExecutionEventContext json display the Execution event context
|
|
132
|
-
:param dl.Progress progress: Progress object for work flow
|
|
133
|
-
:param logger: logger object
|
|
134
|
-
:param sdk: the dtlpy package
|
|
135
|
-
"""
|
|
136
|
-
# dtlpy
|
|
137
|
-
self._logger = logger
|
|
138
|
-
self._sdk = sdk
|
|
139
|
-
self._progress = progress
|
|
140
|
-
|
|
141
|
-
self.event = ExecutionEventContext(event_context)
|
|
142
|
-
if execution_dict is None:
|
|
143
|
-
execution_dict = dict()
|
|
144
|
-
self.execution_dict = execution_dict
|
|
145
|
-
|
|
146
|
-
# ids
|
|
147
|
-
self.trigger_id = execution_dict.get('trigger_id', None)
|
|
148
|
-
self.execution_id = execution_dict.get('id', None)
|
|
149
|
-
|
|
150
|
-
# pipeline
|
|
151
|
-
pipeline = execution_dict.get('pipeline', dict())
|
|
152
|
-
if pipeline is None:
|
|
153
|
-
pipeline = dict()
|
|
154
|
-
self.pipeline_id = pipeline.get('id', None)
|
|
155
|
-
self.node_id = pipeline.get('nodeId', None)
|
|
156
|
-
self.pipeline_execution_id = pipeline.get('executionId', None)
|
|
157
|
-
|
|
158
|
-
# objects
|
|
159
|
-
self._service = service
|
|
160
|
-
self._package = package
|
|
161
|
-
self._project = project
|
|
162
|
-
self._task = None
|
|
163
|
-
self._assignment = None
|
|
164
|
-
self._pipeline = None
|
|
165
|
-
self._node = None
|
|
166
|
-
self._execution = None
|
|
167
|
-
self._pipeline_execution = None
|
|
168
|
-
|
|
169
|
-
@property
|
|
170
|
-
def package(self):
|
|
171
|
-
assert isinstance(self._package, entities.Package), "Missing `package` in context"
|
|
172
|
-
return self._package
|
|
173
|
-
|
|
174
|
-
@property
|
|
175
|
-
def project(self):
|
|
176
|
-
assert isinstance(self._project, entities.Project), "Missing `project` in context"
|
|
177
|
-
return self._project
|
|
178
|
-
|
|
179
|
-
@property
|
|
180
|
-
def service(self):
|
|
181
|
-
assert isinstance(self._service, entities.Service), "Missing `service` in context"
|
|
182
|
-
return self._service
|
|
183
|
-
|
|
184
|
-
@property
|
|
185
|
-
def item_status_creator(self):
|
|
186
|
-
return self.event.item_status_event.creator
|
|
187
|
-
|
|
188
|
-
@property
|
|
189
|
-
def item_status(self):
|
|
190
|
-
return self.event.item_status_event.status
|
|
191
|
-
|
|
192
|
-
@property
|
|
193
|
-
def item_status_operation(self):
|
|
194
|
-
return self.event.item_status_event.action
|
|
195
|
-
|
|
196
|
-
@property
|
|
197
|
-
def execution(self) -> entities.Execution:
|
|
198
|
-
if self._execution is None:
|
|
199
|
-
# noinspection PyProtectedMember
|
|
200
|
-
self._execution = self.sdk.Execution.from_json(
|
|
201
|
-
_json=self.execution_dict,
|
|
202
|
-
client_api=self.service._client_api,
|
|
203
|
-
service=self.service,
|
|
204
|
-
project=self.project
|
|
205
|
-
)
|
|
206
|
-
return self._execution
|
|
207
|
-
|
|
208
|
-
@property
|
|
209
|
-
def task_id(self) -> str:
|
|
210
|
-
return self.event.item_status_event.task_id
|
|
211
|
-
|
|
212
|
-
@property
|
|
213
|
-
def task(self) -> entities.Task:
|
|
214
|
-
if self._task is None and self.task_id is not None:
|
|
215
|
-
try:
|
|
216
|
-
self._task = self.sdk.tasks.get(task_id=self.task_id)
|
|
217
|
-
except Exception:
|
|
218
|
-
self.logger.exception('Failed to get task')
|
|
219
|
-
return self._task
|
|
220
|
-
|
|
221
|
-
@property
|
|
222
|
-
def assignment_id(self) -> str:
|
|
223
|
-
return self.event.item_status_event.assignment_id
|
|
224
|
-
|
|
225
|
-
@property
|
|
226
|
-
def assignment(self) -> entities.Assignment:
|
|
227
|
-
if self._assignment is None and self.assignment_id is not None:
|
|
228
|
-
self._assignment = self.sdk.assignments.get(assignment_id=self.assignment_id)
|
|
229
|
-
return self._assignment
|
|
230
|
-
|
|
231
|
-
@property
|
|
232
|
-
def pipeline(self) -> entities.Pipeline:
|
|
233
|
-
if self._pipeline is None and self.pipeline_id is not None:
|
|
234
|
-
self._pipeline = self.sdk.pipelines.get(pipeline_id=self.pipeline_id)
|
|
235
|
-
return self._pipeline
|
|
236
|
-
|
|
237
|
-
@property
|
|
238
|
-
def node(self):
|
|
239
|
-
if self._node is None and self.pipeline is not None and self.node_id is not None:
|
|
240
|
-
self._node = [n for n in self.pipeline.nodes if n.node_id == self.node_id][0]
|
|
241
|
-
return self._node
|
|
242
|
-
|
|
243
|
-
@property
|
|
244
|
-
def pipeline_execution(self):
|
|
245
|
-
if self._pipeline_execution is None and self.pipeline_execution_id is not None:
|
|
246
|
-
self._pipeline_execution = self.sdk.pipeline_executions.get(
|
|
247
|
-
pipeline_execution_id=self.pipeline_execution_id,
|
|
248
|
-
pipeline_id=self.pipeline_id
|
|
249
|
-
)
|
|
250
|
-
return self._pipeline_execution
|
|
251
|
-
|
|
252
|
-
@property
|
|
253
|
-
def sdk(self):
|
|
254
|
-
if self._sdk is None:
|
|
255
|
-
import dtlpy
|
|
256
|
-
self._sdk = dtlpy
|
|
257
|
-
return self._sdk
|
|
258
|
-
|
|
259
|
-
@property
|
|
260
|
-
def logger(self):
|
|
261
|
-
if self._logger is None:
|
|
262
|
-
import logging
|
|
263
|
-
self._logger = logging.getLogger("[AgentContext]")
|
|
264
|
-
return self._logger
|
|
1
|
+
import datetime
|
|
2
|
+
import threading
|
|
3
|
+
|
|
4
|
+
from .. import entities
|
|
5
|
+
|
|
6
|
+
|
|
7
|
+
class BaseServiceRunner:
|
|
8
|
+
_do_reset = False
|
|
9
|
+
_auto_refresh_dtlpy_token = None
|
|
10
|
+
_refresh_dtlpy_token = None
|
|
11
|
+
_threads_terminated = list()
|
|
12
|
+
_threads_terminated_lock = threading.Lock()
|
|
13
|
+
_service_entity = None
|
|
14
|
+
|
|
15
|
+
def do_reset(self):
|
|
16
|
+
self._do_reset = True
|
|
17
|
+
|
|
18
|
+
@staticmethod
|
|
19
|
+
def ping(progress):
|
|
20
|
+
progress.logger.debug('received ping at: {}'.format(datetime.datetime.now().isoformat()))
|
|
21
|
+
return 'pong'
|
|
22
|
+
|
|
23
|
+
def _terminate(self, tid):
|
|
24
|
+
with self._threads_terminated_lock:
|
|
25
|
+
self._threads_terminated.append(tid)
|
|
26
|
+
|
|
27
|
+
def kill_event(self):
|
|
28
|
+
ident = threading.get_ident()
|
|
29
|
+
if ident in self._threads_terminated:
|
|
30
|
+
with self._threads_terminated_lock:
|
|
31
|
+
self._threads_terminated.pop(self._threads_terminated.index(ident))
|
|
32
|
+
raise InterruptedError('Execution received termination signal')
|
|
33
|
+
|
|
34
|
+
@property
|
|
35
|
+
def service_entity(self) -> entities.Service:
|
|
36
|
+
assert isinstance(self._service_entity, entities.Service), "service_entity must be a dl.Service object"
|
|
37
|
+
return self._service_entity
|
|
38
|
+
|
|
39
|
+
@service_entity.setter
|
|
40
|
+
def service_entity(self, value):
|
|
41
|
+
assert isinstance(value, entities.Service), "service_entity must be a dl.Service object"
|
|
42
|
+
self._service_entity = value
|
|
43
|
+
|
|
44
|
+
|
|
45
|
+
class Progress:
|
|
46
|
+
"""
|
|
47
|
+
Follow the event progress
|
|
48
|
+
"""
|
|
49
|
+
|
|
50
|
+
def update(self,
|
|
51
|
+
status=None,
|
|
52
|
+
progress=0,
|
|
53
|
+
message=None,
|
|
54
|
+
output=None,
|
|
55
|
+
duration=None,
|
|
56
|
+
action=None
|
|
57
|
+
):
|
|
58
|
+
"""
|
|
59
|
+
Update the progress flow
|
|
60
|
+
|
|
61
|
+
:param str status: the progress status to display
|
|
62
|
+
:param int progress: number of finished flow
|
|
63
|
+
:param str message: the progress message to display
|
|
64
|
+
:param dict output: json serializable object to update the event output
|
|
65
|
+
:param float duration: the event duration
|
|
66
|
+
:param str action: event action
|
|
67
|
+
"""
|
|
68
|
+
pass
|
|
69
|
+
|
|
70
|
+
|
|
71
|
+
class ItemStatusEvent:
|
|
72
|
+
def __init__(self, _json: dict):
|
|
73
|
+
if _json is None:
|
|
74
|
+
_json = dict()
|
|
75
|
+
|
|
76
|
+
self.pipeline_id = _json.get('pipelineId', None)
|
|
77
|
+
self.node_id = _json.get('nodeId', None)
|
|
78
|
+
self.action = _json.get('action', None)
|
|
79
|
+
|
|
80
|
+
status = _json.get('status', dict())
|
|
81
|
+
if status is None:
|
|
82
|
+
status = dict()
|
|
83
|
+
|
|
84
|
+
self.task_id = status.get('taskId', None)
|
|
85
|
+
self.assignment_id = status.get('assignmentId', None)
|
|
86
|
+
self.status = status.get('status', None)
|
|
87
|
+
self.creator = status.get('creator', None)
|
|
88
|
+
self.timestamp = status.get('timestamp', None)
|
|
89
|
+
|
|
90
|
+
|
|
91
|
+
class ExecutionEventContext:
|
|
92
|
+
def __init__(self, _json: dict):
|
|
93
|
+
if _json is None:
|
|
94
|
+
_json = dict()
|
|
95
|
+
|
|
96
|
+
self.resource = _json.get('resource', None)
|
|
97
|
+
self.source = _json.get('source', None)
|
|
98
|
+
self.action = _json.get('action', None)
|
|
99
|
+
self.resource_id = _json.get('resourceId', None)
|
|
100
|
+
self.user_id = _json.get('userId', None)
|
|
101
|
+
self.dataset_id = _json.get('datasetId', None)
|
|
102
|
+
self.project_id = _json.get('projectId', None)
|
|
103
|
+
self.body = _json.get('body', None)
|
|
104
|
+
self.item_status_event = ItemStatusEvent(_json.get('itemStatusEvent', dict()))
|
|
105
|
+
|
|
106
|
+
|
|
107
|
+
class Context:
|
|
108
|
+
"""
|
|
109
|
+
Contex of the service state
|
|
110
|
+
"""
|
|
111
|
+
|
|
112
|
+
def __init__(
|
|
113
|
+
self,
|
|
114
|
+
service: entities.Service = None,
|
|
115
|
+
package: entities.Package = None,
|
|
116
|
+
project: entities.Project = None,
|
|
117
|
+
event_context: dict = None,
|
|
118
|
+
execution_dict: dict = None,
|
|
119
|
+
progress: Progress = None,
|
|
120
|
+
logger=None,
|
|
121
|
+
sdk=None
|
|
122
|
+
):
|
|
123
|
+
"""
|
|
124
|
+
A Context entity use DTLPY entities for context in a service runner
|
|
125
|
+
|
|
126
|
+
|
|
127
|
+
:param dict execution_dict: the current execution dict in the state
|
|
128
|
+
:param dict service: the current service entity in th state
|
|
129
|
+
:param dict package: the current package entity in th state
|
|
130
|
+
:param dict project: the current project entity in th state
|
|
131
|
+
:param dict event_context: ExecutionEventContext json display the Execution event context
|
|
132
|
+
:param dl.Progress progress: Progress object for work flow
|
|
133
|
+
:param logger: logger object
|
|
134
|
+
:param sdk: the dtlpy package
|
|
135
|
+
"""
|
|
136
|
+
# dtlpy
|
|
137
|
+
self._logger = logger
|
|
138
|
+
self._sdk = sdk
|
|
139
|
+
self._progress = progress
|
|
140
|
+
|
|
141
|
+
self.event = ExecutionEventContext(event_context)
|
|
142
|
+
if execution_dict is None:
|
|
143
|
+
execution_dict = dict()
|
|
144
|
+
self.execution_dict = execution_dict
|
|
145
|
+
|
|
146
|
+
# ids
|
|
147
|
+
self.trigger_id = execution_dict.get('trigger_id', None)
|
|
148
|
+
self.execution_id = execution_dict.get('id', None)
|
|
149
|
+
|
|
150
|
+
# pipeline
|
|
151
|
+
pipeline = execution_dict.get('pipeline', dict())
|
|
152
|
+
if pipeline is None:
|
|
153
|
+
pipeline = dict()
|
|
154
|
+
self.pipeline_id = pipeline.get('id', None)
|
|
155
|
+
self.node_id = pipeline.get('nodeId', None)
|
|
156
|
+
self.pipeline_execution_id = pipeline.get('executionId', None)
|
|
157
|
+
|
|
158
|
+
# objects
|
|
159
|
+
self._service = service
|
|
160
|
+
self._package = package
|
|
161
|
+
self._project = project
|
|
162
|
+
self._task = None
|
|
163
|
+
self._assignment = None
|
|
164
|
+
self._pipeline = None
|
|
165
|
+
self._node = None
|
|
166
|
+
self._execution = None
|
|
167
|
+
self._pipeline_execution = None
|
|
168
|
+
|
|
169
|
+
@property
|
|
170
|
+
def package(self):
|
|
171
|
+
assert isinstance(self._package, entities.Package), "Missing `package` in context"
|
|
172
|
+
return self._package
|
|
173
|
+
|
|
174
|
+
@property
|
|
175
|
+
def project(self):
|
|
176
|
+
assert isinstance(self._project, entities.Project), "Missing `project` in context"
|
|
177
|
+
return self._project
|
|
178
|
+
|
|
179
|
+
@property
|
|
180
|
+
def service(self):
|
|
181
|
+
assert isinstance(self._service, entities.Service), "Missing `service` in context"
|
|
182
|
+
return self._service
|
|
183
|
+
|
|
184
|
+
@property
|
|
185
|
+
def item_status_creator(self):
|
|
186
|
+
return self.event.item_status_event.creator
|
|
187
|
+
|
|
188
|
+
@property
|
|
189
|
+
def item_status(self):
|
|
190
|
+
return self.event.item_status_event.status
|
|
191
|
+
|
|
192
|
+
@property
|
|
193
|
+
def item_status_operation(self):
|
|
194
|
+
return self.event.item_status_event.action
|
|
195
|
+
|
|
196
|
+
@property
|
|
197
|
+
def execution(self) -> entities.Execution:
|
|
198
|
+
if self._execution is None:
|
|
199
|
+
# noinspection PyProtectedMember
|
|
200
|
+
self._execution = self.sdk.Execution.from_json(
|
|
201
|
+
_json=self.execution_dict,
|
|
202
|
+
client_api=self.service._client_api,
|
|
203
|
+
service=self.service,
|
|
204
|
+
project=self.project
|
|
205
|
+
)
|
|
206
|
+
return self._execution
|
|
207
|
+
|
|
208
|
+
@property
|
|
209
|
+
def task_id(self) -> str:
|
|
210
|
+
return self.event.item_status_event.task_id
|
|
211
|
+
|
|
212
|
+
@property
|
|
213
|
+
def task(self) -> entities.Task:
|
|
214
|
+
if self._task is None and self.task_id is not None:
|
|
215
|
+
try:
|
|
216
|
+
self._task = self.sdk.tasks.get(task_id=self.task_id)
|
|
217
|
+
except Exception:
|
|
218
|
+
self.logger.exception('Failed to get task')
|
|
219
|
+
return self._task
|
|
220
|
+
|
|
221
|
+
@property
|
|
222
|
+
def assignment_id(self) -> str:
|
|
223
|
+
return self.event.item_status_event.assignment_id
|
|
224
|
+
|
|
225
|
+
@property
|
|
226
|
+
def assignment(self) -> entities.Assignment:
|
|
227
|
+
if self._assignment is None and self.assignment_id is not None:
|
|
228
|
+
self._assignment = self.sdk.assignments.get(assignment_id=self.assignment_id)
|
|
229
|
+
return self._assignment
|
|
230
|
+
|
|
231
|
+
@property
|
|
232
|
+
def pipeline(self) -> entities.Pipeline:
|
|
233
|
+
if self._pipeline is None and self.pipeline_id is not None:
|
|
234
|
+
self._pipeline = self.sdk.pipelines.get(pipeline_id=self.pipeline_id)
|
|
235
|
+
return self._pipeline
|
|
236
|
+
|
|
237
|
+
@property
|
|
238
|
+
def node(self):
|
|
239
|
+
if self._node is None and self.pipeline is not None and self.node_id is not None:
|
|
240
|
+
self._node = [n for n in self.pipeline.nodes if n.node_id == self.node_id][0]
|
|
241
|
+
return self._node
|
|
242
|
+
|
|
243
|
+
@property
|
|
244
|
+
def pipeline_execution(self):
|
|
245
|
+
if self._pipeline_execution is None and self.pipeline_execution_id is not None:
|
|
246
|
+
self._pipeline_execution = self.sdk.pipeline_executions.get(
|
|
247
|
+
pipeline_execution_id=self.pipeline_execution_id,
|
|
248
|
+
pipeline_id=self.pipeline_id
|
|
249
|
+
)
|
|
250
|
+
return self._pipeline_execution
|
|
251
|
+
|
|
252
|
+
@property
|
|
253
|
+
def sdk(self):
|
|
254
|
+
if self._sdk is None:
|
|
255
|
+
import dtlpy
|
|
256
|
+
self._sdk = dtlpy
|
|
257
|
+
return self._sdk
|
|
258
|
+
|
|
259
|
+
@property
|
|
260
|
+
def logger(self):
|
|
261
|
+
if self._logger is None:
|
|
262
|
+
import logging
|
|
263
|
+
self._logger = logging.getLogger("[AgentContext]")
|
|
264
|
+
return self._logger
|